From 6b1e9efe7385df896aa79af56de4ee565789e341 Mon Sep 17 00:00:00 2001 From: Bruce Berrios <58147810+Bruception@users.noreply.github.com> Date: Fri, 25 Feb 2022 13:22:44 -0500 Subject: [PATCH] Fix quote ratings (#2586) by Bruception * Fix quote ratings * Reorder logic * Update message * Fix consistency --- backend/api/controllers/quote-ratings.js | 54 ------------------ backend/api/controllers/quotes.ts | 56 ++++++++++++++++++- backend/api/routes/quotes.ts | 5 +- backend/middlewares/error.ts | 1 + .../src/scripts/popups/quote-rate-popup.ts | 12 ++-- 5 files changed, 64 insertions(+), 64 deletions(-) delete mode 100644 backend/api/controllers/quote-ratings.js diff --git a/backend/api/controllers/quote-ratings.js b/backend/api/controllers/quote-ratings.js deleted file mode 100644 index bcd2604f4..000000000 --- a/backend/api/controllers/quote-ratings.js +++ /dev/null @@ -1,54 +0,0 @@ -import MonkeyError from "../../handlers/error"; -import UserDAO from "../../dao/user"; -import QuoteRatingsDAO from "../../dao/quote-ratings"; -import { MonkeyResponse } from "../../handlers/monkey-response"; - -class QuoteRatingsController { - static async getRating(req, _res) { - const { quoteId, language } = req.query; - const data = await QuoteRatingsDAO.get(parseInt(quoteId), language); - return new MonkeyResponse("Rating retrieved", data); - } - - static async submitRating(req, _res) { - const { uid } = req.ctx.decodedToken; - let { quoteId, rating, language } = req.body; - - quoteId = parseInt(quoteId); - rating = Math.round(parseInt(rating)); - - //check if user already submitted a rating - const user = await UserDAO.getUser(uid); - - if (!user) { - throw new MonkeyError(401, "User not found."); - } - let quoteRatings = user.quoteRatings; - - if (quoteRatings === undefined) quoteRatings = {}; - if (quoteRatings[language] === undefined) quoteRatings[language] = {}; - if (quoteRatings[language][quoteId] == undefined) - quoteRatings[language][quoteId] = undefined; - - const quoteRating = quoteRatings[language][quoteId]; - - let newRating; - let update; - if (quoteRating) { - //user already voted for this - newRating = rating - quoteRating; - update = true; - } else { - //user has not voted for this - newRating = rating; - update = false; - } - - await QuoteRatingsDAO.submit(quoteId, language, newRating, update); - quoteRatings[language][quoteId] = rating; - await UserDAO.updateQuoteRatings(uid, quoteRatings); - return new MonkeyResponse("Rating updated"); - } -} - -export default QuoteRatingsController; diff --git a/backend/api/controllers/quotes.ts b/backend/api/controllers/quotes.ts index db2609852..82f02dccb 100644 --- a/backend/api/controllers/quotes.ts +++ b/backend/api/controllers/quotes.ts @@ -1,5 +1,8 @@ +import _ from "lodash"; import { v4 as uuidv4 } from "uuid"; +import UserDAO from "../../dao/user"; import ReportDAO from "../../dao/report"; +import QuoteRatingsDAO from "../../dao/quote-ratings"; import UsersDAO from "../../dao/user"; import MonkeyError from "../../handlers/error"; import { verify } from "../../handlers/captcha"; @@ -7,6 +10,57 @@ import Logger from "../../handlers/logger"; import { MonkeyResponse } from "../../handlers/monkey-response"; class QuotesController { + static async getRating(req: MonkeyTypes.Request): Promise { + const { quoteId, language } = req.query; + + const data = await QuoteRatingsDAO.get( + parseInt(quoteId as string), + language + ); + + return new MonkeyResponse("Rating retrieved", data); + } + + static async submitRating(req: MonkeyTypes.Request): Promise { + const { uid } = req.ctx.decodedToken; + const { quoteId, rating, language } = req.body; + + const user = await UserDAO.getUser(uid); + if (!user) { + throw new MonkeyError(401, "User not found."); + } + + const normalizedQuoteId = parseInt(quoteId as string); + const normalizedRating = Math.round(parseInt(rating as string)); + + const userQuoteRatings = user.quoteRatings ?? {}; + const currentRating = userQuoteRatings[language]?.[normalizedQuoteId] ?? 0; + + const newRating = normalizedRating - currentRating; + const shouldUpdateRating = currentRating !== 0; + + await QuoteRatingsDAO.submit( + quoteId, + language, + newRating, + shouldUpdateRating + ); + + _.setWith( + userQuoteRatings, + `[${language}][${normalizedQuoteId}]`, + normalizedRating, + Object + ); + + await UserDAO.updateQuoteRatings(uid, userQuoteRatings); + + const responseMessage = `Rating ${ + shouldUpdateRating ? "updated" : "submitted" + }`; + return new MonkeyResponse(responseMessage); + } + static async reportQuote(req: MonkeyTypes.Request): Promise { const { uid } = req.ctx.decodedToken; const { @@ -43,7 +97,7 @@ class QuotesController { details: newReport.details, }); - return new MonkeyResponse("Quote reported successfully"); + return new MonkeyResponse("Quote reported"); } } diff --git a/backend/api/routes/quotes.ts b/backend/api/routes/quotes.ts index 5598f7a49..c2d23c915 100644 --- a/backend/api/routes/quotes.ts +++ b/backend/api/routes/quotes.ts @@ -2,7 +2,6 @@ import joi from "joi"; import { authenticateRequest } from "../../middlewares/auth"; import { Router } from "express"; import NewQuotesController from "../controllers/new-quotes"; -import QuoteRatingsController from "../controllers/quote-ratings"; import QuotesController from "../controllers/quotes"; import * as RateLimit from "../../middlewares/rate-limit"; import { @@ -81,7 +80,7 @@ quotesRouter.get( language: joi.string().required(), }, }), - asyncHandler(QuoteRatingsController.getRating) + asyncHandler(QuotesController.getRating) ); quotesRouter.post( @@ -95,7 +94,7 @@ quotesRouter.post( language: joi.string().required(), }, }), - asyncHandler(QuoteRatingsController.submitRating) + asyncHandler(QuotesController.submitRating) ); quotesRouter.post( diff --git a/backend/middlewares/error.ts b/backend/middlewares/error.ts index b9e09ed5b..953169cc4 100644 --- a/backend/middlewares/error.ts +++ b/backend/middlewares/error.ts @@ -58,6 +58,7 @@ async function errorHandlingMiddleware( } } else { console.error(error.message); + console.error(error.stack); } return handleMonkeyResponse(monkeyResponse, res); diff --git a/frontend/src/scripts/popups/quote-rate-popup.ts b/frontend/src/scripts/popups/quote-rate-popup.ts index 4d0c3d41d..8523ec911 100644 --- a/frontend/src/scripts/popups/quote-rate-popup.ts +++ b/frontend/src/scripts/popups/quote-rate-popup.ts @@ -164,11 +164,8 @@ async function submit(): Promise { ); } - const quoteRatings = DB.getSnapshot().quoteRatings; - - if (quoteRatings === undefined) { - return; - } + const snapshot = DB.getSnapshot(); + const quoteRatings = snapshot.quoteRatings ?? {}; if (quoteRatings?.[currentQuote.language]?.[currentQuote.id]) { const oldRating = quoteRatings[currentQuote.language][currentQuote.id]; @@ -184,7 +181,7 @@ async function submit(): Promise { } as QuoteStats; Notifications.add("Rating updated", 1); } else { - if (quoteRatings[currentQuote.language] === undefined) { + if (!quoteRatings[currentQuote.language]) { quoteRatings[currentQuote.language] = {}; } quoteRatings[currentQuote.language][currentQuote.id] = rating; @@ -202,6 +199,9 @@ async function submit(): Promise { Notifications.add("Rating submitted", 1); } + snapshot.quoteRatings = quoteRatings; + DB.setSnapshot(snapshot); + quoteStats.average = getRatingAverage(quoteStats); $(".pageTest #result #rateQuoteButton .rating").text( quoteStats.average?.toFixed(1)