From 2edd7c18e5460d55e12cbb4584cf6ebb495090e0 Mon Sep 17 00:00:00 2001 From: Ly Tuan Kiet Date: Mon, 9 Dec 2024 17:53:47 +0700 Subject: [PATCH] refactor: enhance Quiz schema with role-based access control and service ID requirement - Added role-based access control to restrict access to Quiz queries and mutations for users with the CENTER_MENTOR role. - Updated error messages for unauthorized access to improve clarity. - Introduced a required 'serviceId' argument in the quizzes query to ensure proper filtering and association with the center mentor. - Refactored existing authentication checks to maintain consistent error handling across the Quiz schema. --- src/Quiz/quiz.schema.ts | 37 +++++++++++++++++++++++++------------ 1 file changed, 25 insertions(+), 12 deletions(-) diff --git a/src/Quiz/quiz.schema.ts b/src/Quiz/quiz.schema.ts index b391d6f..06d6e41 100644 --- a/src/Quiz/quiz.schema.ts +++ b/src/Quiz/quiz.schema.ts @@ -1,5 +1,5 @@ import { Inject, Injectable } from '@nestjs/common' -import { AnswerType } from '@prisma/client' +import { AnswerType, Role } from '@prisma/client' import { QuestionType } from '@prisma/client' import { Pothos, PothosRef, PothosSchema, SchemaBuilderToken } from '@smatch-corp/nestjs-pothos' import { Builder } from '../Graphql/graphql.builder' @@ -139,28 +139,41 @@ export class QuizSchema extends PothosSchema { throw new Error('Subscription is not allowed') } if (!ctx.http.me) { - throw new Error('User is not authenticated') + throw new Error('Unauthorized') } return await this.prisma.quiz.findUnique({ ...query, where: { id: args.where.id } }) }, }), quizzes: t.prismaField({ type: [this.quiz()], - args: this.builder.generator.findManyArgs('Quiz'), + args: { + serviceId: t.arg({ + type: 'String', + required: true, + }), + }, resolve: async (query, _root, args, ctx, _info) => { if (ctx.isSubscription) { throw new Error('Subscription is not allowed') } if (!ctx.http.me) { - throw new Error('User is not authenticated') + throw new Error('Unauthorized') + } + if (ctx.http.me.role !== Role.CENTER_MENTOR) { + throw new Error('Unauthorized') + } + const centerMentor = await this.prisma.centerMentor.findUnique({ + where: { mentorId: ctx.http.me.id }, + }) + if (!centerMentor) { + throw new Error('Center mentor not found') } return await this.prisma.quiz.findMany({ ...query, - where: args.filter ?? undefined, - orderBy: args.orderBy ?? undefined, - cursor: args.cursor ?? undefined, - take: args.take ?? undefined, - skip: args.skip ?? undefined, + where: { + serviceId: args.serviceId, + centerMentorId: ctx.http.me.id, + }, }) }, }), @@ -185,7 +198,7 @@ export class QuizSchema extends PothosSchema { throw new Error('Subscription is not allowed') } if (!ctx.http.me) { - throw new Error('User is not authenticated') + throw new Error('Unauthorized') } if (!args.data) { throw new Error('Data is required') @@ -223,7 +236,7 @@ export class QuizSchema extends PothosSchema { throw new Error('Subscription is not allowed') } if (!ctx.http.me) { - throw new Error('User is not authenticated') + throw new Error('Unauthorized') } return await this.prisma.quiz.update({ ...query, @@ -252,7 +265,7 @@ export class QuizSchema extends PothosSchema { throw new Error('Subscription is not allowed') } if (!ctx.http.me) { - throw new Error('User is not authenticated') + throw new Error('Unauthorized') } if (!args.data) { throw new Error('Data is required')