mirror of
https://github.com/monkeytypegame/monkeytype.git
synced 2025-02-04 04:51:16 +08:00
Add results schema validation (#2417) by Bruception
This commit is contained in:
parent
0a3741b432
commit
bbcbc687ae
3 changed files with 87 additions and 26 deletions
|
@ -32,23 +32,27 @@ try {
|
|||
}
|
||||
|
||||
class ResultController {
|
||||
static async getResults(req, res) {
|
||||
static async getResults(req, _res) {
|
||||
const { uid } = req.ctx.decodedToken;
|
||||
const results = await ResultDAO.getResults(uid);
|
||||
return res.status(200).json(results);
|
||||
|
||||
return await ResultDAO.getResults(uid);
|
||||
}
|
||||
|
||||
static async deleteAll(req, res) {
|
||||
const { uid } = req.ctx.decodedToken;
|
||||
|
||||
await ResultDAO.deleteAll(uid);
|
||||
Logger.log("user_results_deleted", "", uid);
|
||||
|
||||
return res.sendStatus(200);
|
||||
}
|
||||
|
||||
static async updateTags(req, res) {
|
||||
const { uid } = req.ctx.decodedToken;
|
||||
const { tags, resultid } = req.body;
|
||||
|
||||
await ResultDAO.updateTags(uid, resultid, tags);
|
||||
|
||||
return res.sendStatus(200);
|
||||
}
|
||||
|
||||
|
@ -58,16 +62,7 @@ class ResultController {
|
|||
result.uid = uid;
|
||||
if (validateObjectValues(result) > 0)
|
||||
return res.status(400).json({ message: "Bad input" });
|
||||
if (
|
||||
result.wpm <= 0 ||
|
||||
result.wpm > 350 ||
|
||||
result.acc < 75 ||
|
||||
result.acc > 100 ||
|
||||
result.consistency > 100
|
||||
) {
|
||||
return res.status(400).json({ message: "Bad input" });
|
||||
}
|
||||
if (result.wpm == result.raw && result.acc != 100) {
|
||||
if (result.wpm === result.raw && result.acc !== 100) {
|
||||
return res.status(400).json({ message: "Bad input" });
|
||||
}
|
||||
if (
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
const joi = require("joi");
|
||||
const { authenticateRequest } = require("../../middlewares/auth");
|
||||
const { Router } = require("express");
|
||||
const ResultController = require("../controllers/result");
|
||||
|
@ -6,6 +7,7 @@ const {
|
|||
asyncHandlerWrapper,
|
||||
requestValidation,
|
||||
} = require("../../middlewares/api-utils");
|
||||
const resultSchema = require("../schemas/result-schema");
|
||||
|
||||
const router = Router();
|
||||
|
||||
|
@ -20,6 +22,11 @@ router.post(
|
|||
"/add",
|
||||
RateLimit.resultsAdd,
|
||||
authenticateRequest(),
|
||||
requestValidation({
|
||||
body: {
|
||||
result: resultSchema,
|
||||
},
|
||||
}),
|
||||
asyncHandlerWrapper(ResultController.addResult)
|
||||
);
|
||||
|
||||
|
@ -27,6 +34,12 @@ router.post(
|
|||
"/updateTags",
|
||||
RateLimit.resultsTagsUpdate,
|
||||
authenticateRequest(),
|
||||
requestValidation({
|
||||
body: {
|
||||
tags: joi.array().items(joi.string()).required(),
|
||||
resultid: joi.string().required(),
|
||||
},
|
||||
}),
|
||||
asyncHandlerWrapper(ResultController.updateTags)
|
||||
);
|
||||
|
||||
|
@ -37,17 +50,4 @@ router.post(
|
|||
asyncHandlerWrapper(ResultController.deleteAll)
|
||||
);
|
||||
|
||||
router.get(
|
||||
"/getLeaderboard/:type/:mode/:mode2",
|
||||
RateLimit.resultsLeaderboardGet,
|
||||
asyncHandlerWrapper(ResultController.getLeaderboard)
|
||||
);
|
||||
|
||||
router.post(
|
||||
"/checkLeaderboardQualification",
|
||||
RateLimit.resultsLeaderboardQualificationGet,
|
||||
authenticateRequest(),
|
||||
asyncHandlerWrapper(ResultController.checkLeaderboardQualification)
|
||||
);
|
||||
|
||||
module.exports = router;
|
||||
|
|
66
backend/api/schemas/result-schema.js
Normal file
66
backend/api/schemas/result-schema.js
Normal file
|
@ -0,0 +1,66 @@
|
|||
const joi = require("joi");
|
||||
|
||||
const RESULT_SCHEMA = joi
|
||||
.object({
|
||||
acc: joi.number().min(75).max(100).required(),
|
||||
afkDuration: joi.number().required(),
|
||||
bailedOut: joi.boolean().required(),
|
||||
blindMode: joi.boolean().required(),
|
||||
challenge: joi.string(),
|
||||
charStats: joi.array().items(joi.number()).required(),
|
||||
chartData: joi
|
||||
.alternatives()
|
||||
.try(
|
||||
joi.object({
|
||||
wpm: joi.array().items(joi.number()).required(),
|
||||
raw: joi.array().items(joi.number()).required(),
|
||||
err: joi.array().items(joi.number()).required(),
|
||||
}),
|
||||
joi.string().valid("toolong")
|
||||
)
|
||||
.required(),
|
||||
consistency: joi.number().max(100).required(),
|
||||
customText: joi.object({
|
||||
textLen: joi.number().required(),
|
||||
isWordRandom: joi.boolean().required(),
|
||||
isTimeRandom: joi.boolean().required(),
|
||||
word: joi.number().required().allow(null),
|
||||
time: joi.number().required().allow(null),
|
||||
}),
|
||||
difficulty: joi.string().valid("normal", "expert", "master").required(),
|
||||
funbox: joi.string().required(),
|
||||
hash: joi.string().required(),
|
||||
incompleteTestSeconds: joi.number().required(),
|
||||
keyConsistency: joi.number().required(),
|
||||
keyDuration: joi
|
||||
.alternatives()
|
||||
.try(joi.array().items(joi.number()), joi.string().valid("toolong"))
|
||||
.required(),
|
||||
keySpacing: joi
|
||||
.alternatives()
|
||||
.try(joi.array().items(joi.number()), joi.string().valid("toolong"))
|
||||
.required(),
|
||||
lang: joi.string(),
|
||||
language: joi.string().required(),
|
||||
lazyMode: joi.boolean().required(),
|
||||
mode: joi
|
||||
.string()
|
||||
.valid("time", "words", "quote", "zen", "custom")
|
||||
.required(),
|
||||
mode2: joi.alternatives().try(joi.number(), joi.string()).required(),
|
||||
numbers: joi.boolean().required(),
|
||||
punctuation: joi.boolean().required(),
|
||||
quoteLength: joi.number().required(),
|
||||
rawWpm: joi.number().required(),
|
||||
restartCount: joi.number().required(),
|
||||
smoothConsistency: joi.number().required(),
|
||||
tags: joi.array().items(joi.string()).required(),
|
||||
testDuration: joi.number().required(),
|
||||
timestamp: joi.date().timestamp().required(),
|
||||
uid: joi.string().required(),
|
||||
wpm: joi.number().min(1).max(350).required(),
|
||||
wpmConsistency: joi.number().required(),
|
||||
})
|
||||
.required();
|
||||
|
||||
module.exports = RESULT_SCHEMA;
|
Loading…
Reference in a new issue