Skip to content

Commit

Permalink
Merge branch 'master' into cyclone
Browse files Browse the repository at this point in the history
  • Loading branch information
dungwinux committed Apr 4, 2019
2 parents 3725cc3 + 68aabe8 commit c40738e
Show file tree
Hide file tree
Showing 3 changed files with 84 additions and 13 deletions.
71 changes: 61 additions & 10 deletions src/data/database.js
Original file line number Diff line number Diff line change
Expand Up @@ -244,7 +244,7 @@ async function updateUserPassword(user_id, old_pass, new_pass) {
/**
* Count number of submissions
*/
function countSubmissions() {
function countAllSubmissions() {
return new Promise((resolve, reject) => {
db.submissions.count({}, function(err, count) {
if (err) reject(err);
Expand All @@ -253,6 +253,19 @@ function countSubmissions() {
});
}

/**
* Count number of submissions from user_id
* @param {String} user_id User's ID
*/
function countUserSubmissions(user_id) {
return new Promise((resolve, reject) => {
db.submissions.count({ user_id }, function(err, count) {
if (err) reject(err);
else resolve(count);
});
});
}

/**
* Verify page, count, size value so it will work
*/
Expand All @@ -272,7 +285,7 @@ function verifySubsQuery(page, size, count, maxSize) {
* @returns {Promise<Array<ReturnSubmission>>} Array of submission if success
*/
async function readAllSubmissions(page, size, count) {
const maxSize = await countSubmissions();
const maxSize = await countAllSubmissions();
({ page, size, count } = verifySubsQuery(page, size, count, maxSize));

return new Promise((resolve, reject) => {
Expand All @@ -297,10 +310,11 @@ async function readAllSubmissions(page, size, count) {
// TODO: Decide what to do when there's invalid user
// Currently, it will throw error with invalid user_id
if (err) reject(err);
else
Promise.all(
docs.map((doc) => readUserByID(doc.user_id))
).then((usernameList) => {
else {
let usernameListPromise = docs.map((doc) =>
readUserByID(doc.user_id).catch(() => null)
);
Promise.all(usernameListPromise).then((usernameList) => {
let serialized = docs.map((doc, idx) => {
doc.username = usernameList[idx].username;
return doc;
Expand All @@ -312,6 +326,7 @@ async function readAllSubmissions(page, size, count) {
count: count
});
});
}
});
});
}
Expand Down Expand Up @@ -339,7 +354,14 @@ function readSubmission(sub_id) {
if (err) reject(err);
else if (docs === null)
reject(new Error(`Invalid Submission's ID: ${sub_id}`));
else resolve(docs);
else
readUserByID(docs.user_id)
.then((res) => {
docs.username = res.username;
})
.finally(() => {
resolve(docs);
});
}
);
});
Expand All @@ -355,8 +377,8 @@ function readSubmission(sub_id) {
* @returns {Promise<Array<ReturnSubmission>>} Array of user's submissions if success
*/
async function readUserSubmission(user_id, page, size, count) {
const username = await readUserByID(user_id);
const maxSize = await countSubmissions();
const userData = await readUserByID(user_id);
const maxSize = await countUserSubmissions(user_id);
({ page, size, count } = verifySubsQuery(page, size, count, maxSize));

return new Promise((resolve, reject) => {
Expand All @@ -381,7 +403,7 @@ async function readUserSubmission(user_id, page, size, count) {
if (err) reject(err);
else {
let serialized = docs.map((doc) => {
doc.username = username;
doc.username = userData.username;
return doc;
});
resolve({
Expand All @@ -395,6 +417,32 @@ async function readUserSubmission(user_id, page, size, count) {
});
}

/**
* Read Submission's source
* @param {String} sub_id Submission's ID
*/
function readSubmissionSrc(sub_id) {
return new Promise((resolve, reject) => {
db.submissions.findOne(
{ _id: sub_id },
{ ext: 1, user_id: 1, source_code: 1 },
(err, docs) => {
if (err) reject(err);
else if (docs === null)
reject(new Error(`Invalid Submission's ID: ${sub_id}`));
else
readUserByID(docs.user_id)
.then((res) => {
docs.username = res.username;
})
.finally(() => {
resolve(docs);
});
}
);
});
}

/**
* Add submission to database
* @param {String} source_code Source Code
Expand Down Expand Up @@ -557,9 +605,12 @@ module.exports = {
readUserPassHash,
updateUserName,
updateUserPassword,
countAllSubmissions,
countUserSubmissions,
readAllSubmissions,
readSubmission,
readUserSubmission,
readSubmissionSrc,
newSubmission,
updateSubmission,
readLastSatisfy,
Expand Down
24 changes: 22 additions & 2 deletions src/routes/subs.js
Original file line number Diff line number Diff line change
@@ -1,12 +1,14 @@
"use strict";

const express = require("express");
const { existsSync } = require("fs");

const { sendCode } = require("../controller/submitCode");
const {
readSubmission,
readAllSubmissions,
readUserSubmission
readUserSubmission,
readSubmissionSrc
} = require("../data/database");
const auth = require("../middleware/auth");
const bruteForce = require("../middleware/bruteForce");
Expand Down Expand Up @@ -56,7 +58,8 @@ router
router.get("/:id", (req, res) => {
readSubmission(req.params.id).then(
(docs) => {
if (docs.user_id === req.user._id) res.send(docs);
if (docs.user_id === req.user._id || req.user.isAdmin)
res.send(docs);
else res.sendStatus(401);
},
(err) => {
Expand All @@ -65,4 +68,21 @@ router.get("/:id", (req, res) => {
);
});

router.get("/:id/source", (req, res) => {
readSubmissionSrc(req.params.id)
.then((docs) => {
if (docs.user_id === req.user._id || req.user.isAdmin) {
if (!existsSync(docs.source_code)) res.sendStatus(404);
else
res.download(
docs.source_code,
"".concat(docs._id, docs.ext.toLowerCase())
);
} else res.sendStatus(401);
})
.catch((err) => {
res.status(400).json(err.message);
});
});

module.exports = router;
2 changes: 1 addition & 1 deletion src/util/config/contestConfig.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ function parseContainer(container) {
if (!Array.isArray(container)) throw new Error("Invalid Container");
let parsedContainer = container
.filter((x) => typeof x === "string")
.map((x) => x.trim().toUpperCase())
.map((x) => x.replace(/\s/g, "").toUpperCase())
.sort((a, b) => a.localeCompare(b));
return [...new Set(parsedContainer)];
}
Expand Down

0 comments on commit c40738e

Please sign in to comment.