feat: enhance Quiz schema with random quiz retrieval and amount argument

- Added a new 'amount' argument to the quiz retrieval query, allowing users to specify the number of quizzes to return.
- Implemented a seeded randomization mechanism to select quizzes based on the user's ID, improving the randomness of quiz selection.
- Refactored the quiz retrieval logic to utilize the new randomization and amount features, enhancing user experience and engagement.
This commit is contained in:
2024-12-09 20:07:22 +07:00
parent 4151bb6afe
commit 30f56747f7

View File

@@ -1,10 +1,10 @@
import crypto from 'crypto'
import { Inject, Injectable } from '@nestjs/common' import { Inject, Injectable } from '@nestjs/common'
import { AnswerType, Role } from '@prisma/client' import { AnswerType, Role } from '@prisma/client'
import { QuestionType } from '@prisma/client' import { QuestionType } from '@prisma/client'
import { Pothos, PothosRef, PothosSchema, SchemaBuilderToken } from '@smatch-corp/nestjs-pothos' import { Pothos, PothosRef, PothosSchema, SchemaBuilderToken } from '@smatch-corp/nestjs-pothos'
import { Builder } from '../Graphql/graphql.builder' import { Builder } from '../Graphql/graphql.builder'
import { PrismaService } from '../Prisma/prisma.service' import { PrismaService } from '../Prisma/prisma.service'
@Injectable() @Injectable()
export class QuizSchema extends PothosSchema { export class QuizSchema extends PothosSchema {
constructor( constructor(
@@ -155,6 +155,10 @@ export class QuizSchema extends PothosSchema {
type: 'String', type: 'String',
required: false, required: false,
}), }),
amount: t.arg({
type: 'Int',
required: false,
}),
}, },
resolve: async (query, _root, args, ctx, _info) => { resolve: async (query, _root, args, ctx, _info) => {
if (ctx.isSubscription) { if (ctx.isSubscription) {
@@ -168,16 +172,23 @@ export class QuizSchema extends PothosSchema {
const centerMentor = await this.prisma.centerMentor.findUnique({ const centerMentor = await this.prisma.centerMentor.findUnique({
where: { mentorId: ctx.http.me.id }, where: { mentorId: ctx.http.me.id },
}) })
// using pseudo random to get amount of quizzes based on userid as seed
const random = getRandomWithSeed(
parseInt(crypto.createHash('sha256').update(ctx.http.me.id).digest('hex'), 16),
)
if (!centerMentor) { if (!centerMentor) {
throw new Error('Center mentor not found') throw new Error('Center mentor not found')
} }
return await this.prisma.quiz.findMany({ const quizzes = await this.prisma.quiz.findMany({
...query, ...query,
where: { where: {
serviceId: args.serviceId, serviceId: args.serviceId,
centerMentorId: centerMentor.mentorId, centerMentorId: centerMentor.mentorId,
}, },
}) })
// get amount of quizzes using args.amount and random index based on random
const randomIndex = Math.floor(random * quizzes.length)
return quizzes.slice(randomIndex, randomIndex + (args.amount ?? 1))
} }
// use case 2: Customer // use case 2: Customer
@@ -311,3 +322,12 @@ export class QuizSchema extends PothosSchema {
})) }))
} }
} }
function seededRandom(seed: number) {
const x = Math.sin(seed) * 10000
return x - Math.floor(x)
}
function getRandomWithSeed(seed: number) {
return seededRandom(seed)
}