Public Access
refactor: update result schemas and tests for improved state management and feedback modes
This commit is contained in:
1 parent
ae8a01bc54
commit
95603f93a0
4 files changed
+47
-46
No files matched your search
@@ -11,12 +11,12 @@ describe('submitResultSchema', () => {
|
|||||||
graded_count: 10,
|
graded_count: 10,
|
||||||
elapsed_ms: 120000,
|
elapsed_ms: 120000,
|
||||||
state: {
|
state: {
|
||||||
|
currentIdx: 0,
|
||||||
answers: { q1: 'a' },
|
answers: { q1: 'a' },
|
||||||
gradedAnswers: { q1: { correct: true, points: 1 } },
|
flags: { q1: false },
|
||||||
answeredCount: 10,
|
notes: '',
|
||||||
score: 80,
|
startedAt: Date.now(),
|
||||||
correctCount: 8,
|
feedbackMode: 'end',
|
||||||
gradedCount: 10,
|
|
||||||
},
|
},
|
||||||
exam: {
|
exam: {
|
||||||
title: 'My Exam',
|
title: 'My Exam',
|
||||||
@@ -34,12 +34,12 @@ describe('submitResultSchema', () => {
|
|||||||
graded_count: 10,
|
graded_count: 10,
|
||||||
elapsed_ms: 120000,
|
elapsed_ms: 120000,
|
||||||
state: {
|
state: {
|
||||||
|
currentIdx: 0,
|
||||||
answers: {},
|
answers: {},
|
||||||
gradedAnswers: {},
|
flags: {},
|
||||||
answeredCount: 0,
|
notes: '',
|
||||||
score: 0,
|
startedAt: Date.now(),
|
||||||
correctCount: 0,
|
feedbackMode: 'end',
|
||||||
gradedCount: 0,
|
|
||||||
},
|
},
|
||||||
exam: { title: 'My Exam', questions: [] },
|
exam: { title: 'My Exam', questions: [] },
|
||||||
})
|
})
|
||||||
@@ -56,12 +56,12 @@ describe('submitResultSchema', () => {
|
|||||||
graded_count: 10,
|
graded_count: 10,
|
||||||
elapsed_ms: 120000,
|
elapsed_ms: 120000,
|
||||||
state: {
|
state: {
|
||||||
|
currentIdx: 0,
|
||||||
answers: {},
|
answers: {},
|
||||||
gradedAnswers: {},
|
flags: {},
|
||||||
answeredCount: 0,
|
notes: '',
|
||||||
score: 0,
|
startedAt: Date.now(),
|
||||||
correctCount: 0,
|
feedbackMode: 'end',
|
||||||
gradedCount: 0,
|
|
||||||
},
|
},
|
||||||
exam: { title: 'My Exam', questions: [] },
|
exam: { title: 'My Exam', questions: [] },
|
||||||
})
|
})
|
||||||
@@ -77,12 +77,35 @@ describe('submitResultSchema', () => {
|
|||||||
graded_count: 10,
|
graded_count: 10,
|
||||||
elapsed_ms: 120000,
|
elapsed_ms: 120000,
|
||||||
state: {
|
state: {
|
||||||
|
currentIdx: 0,
|
||||||
answers: {},
|
answers: {},
|
||||||
gradedAnswers: {},
|
flags: {},
|
||||||
answeredCount: 0,
|
notes: '',
|
||||||
score: 0,
|
startedAt: Date.now(),
|
||||||
correctCount: 0,
|
feedbackMode: 'end',
|
||||||
gradedCount: 0,
|
},
|
||||||
|
exam: { title: 'My Exam', questions: [] },
|
||||||
|
})
|
||||||
|
expect(result.success).toBe(true)
|
||||||
|
})
|
||||||
|
|
||||||
|
it('accepts immediate feedback mode', () => {
|
||||||
|
const result = submitResultSchema.safeParse({
|
||||||
|
title: 'My Exam',
|
||||||
|
score_points: 8,
|
||||||
|
total_points: 10,
|
||||||
|
correct_count: 8,
|
||||||
|
graded_count: 10,
|
||||||
|
elapsed_ms: 120000,
|
||||||
|
state: {
|
||||||
|
currentIdx: 2,
|
||||||
|
answers: { q1: 'a', q2: 'b' },
|
||||||
|
flags: { q1: true },
|
||||||
|
notes: 'some notes',
|
||||||
|
revealed: { q1: true },
|
||||||
|
startedAt: Date.now(),
|
||||||
|
completedAt: Date.now(),
|
||||||
|
feedbackMode: 'immediate',
|
||||||
},
|
},
|
||||||
exam: { title: 'My Exam', questions: [] },
|
exam: { title: 'My Exam', questions: [] },
|
||||||
})
|
})
|
||||||
|
|||||||
@@ -1,7 +1,5 @@
|
|||||||
import { z } from 'zod'
|
import { z } from 'zod'
|
||||||
|
|
||||||
const answerValueSchema = z.union([z.string(), z.array(z.string()), z.record(z.string(), z.string())])
|
|
||||||
|
|
||||||
export const submitResultSchema = z.object({
|
export const submitResultSchema = z.object({
|
||||||
exam_id: z.number().nullable().optional(),
|
exam_id: z.number().nullable().optional(),
|
||||||
title: z.string().min(1),
|
title: z.string().min(1),
|
||||||
@@ -11,28 +9,8 @@ export const submitResultSchema = z.object({
|
|||||||
graded_count: z.number(),
|
graded_count: z.number(),
|
||||||
passing_score: z.number().optional(),
|
passing_score: z.number().optional(),
|
||||||
elapsed_ms: z.number(),
|
elapsed_ms: z.number(),
|
||||||
state: z.object({
|
state: z.record(z.unknown()),
|
||||||
answers: z.record(z.string(), answerValueSchema),
|
exam: z.record(z.unknown()),
|
||||||
gradedAnswers: z.record(z.string(), z.object({
|
|
||||||
correct: z.boolean(),
|
|
||||||
points: z.number(),
|
|
||||||
explanation: z.string().optional(),
|
|
||||||
})),
|
|
||||||
answeredCount: z.number(),
|
|
||||||
score: z.number(),
|
|
||||||
correctCount: z.number(),
|
|
||||||
gradedCount: z.number(),
|
|
||||||
timeExpired: z.boolean().optional(),
|
|
||||||
}),
|
|
||||||
exam: z.object({
|
|
||||||
id: z.string().optional(),
|
|
||||||
title: z.string(),
|
|
||||||
subtitle: z.string().optional(),
|
|
||||||
questions: z.array(z.any()),
|
|
||||||
timeLimitMinutes: z.number().nullable().optional(),
|
|
||||||
passingScore: z.number().optional(),
|
|
||||||
feedbackMode: z.enum(['end', 'immediate']).optional(),
|
|
||||||
}).passthrough(),
|
|
||||||
})
|
})
|
||||||
|
|
||||||
export const resultIdParamSchema = z.object({
|
export const resultIdParamSchema = z.object({
|
||||||
|
|||||||
@@ -61,7 +61,7 @@ function AppInner() {
|
|||||||
const apiHistory: HistoryEntry[] = data.results.map((r) => ({
|
const apiHistory: HistoryEntry[] = data.results.map((r) => ({
|
||||||
id: String(r.id),
|
id: String(r.id),
|
||||||
title: r.title,
|
title: r.title,
|
||||||
completedAt: r.completed_at * 1000,
|
completedAt: r.completed_at,
|
||||||
elapsedMs: r.elapsed_ms,
|
elapsedMs: r.elapsed_ms,
|
||||||
gradedCount: r.graded_count,
|
gradedCount: r.graded_count,
|
||||||
correctCount: r.correct_count,
|
correctCount: r.correct_count,
|
||||||
|
|||||||
+1
-1
@@ -1 +1 @@
|
|||||||
{"version":"4.1.5","results":[[":frontend/src/utils/grading.test.ts",{"duration":13.527699999999982,"failed":false}],[":frontend/src/utils/latex.test.ts",{"duration":19.335300000000075,"failed":false}],[":backend/src/validators/authSchemas.test.ts",{"duration":18.226099999999974,"failed":false}],[":frontend/src/utils/validation.test.ts",{"duration":8.861599999999953,"failed":false}],[":frontend/src/utils/storage.test.ts",{"duration":13.730599999999981,"failed":false}],[":backend/src/validators/examSchemas.test.ts",{"duration":14.561199999999985,"failed":false}],[":backend/src/validators/adminSchemas.test.ts",{"duration":10.744000000000028,"failed":false}],[":backend/src/middleware/error.test.ts",{"duration":3.961199999999991,"failed":false}],[":frontend/src/utils/slug.test.ts",{"duration":7.912199999999984,"failed":false}],[":frontend/src/utils/formatting.test.ts",{"duration":8.322499999999991,"failed":false}],[":backend/src/config.test.ts",{"duration":5.9365999999999985,"failed":false}],[":backend/src/validators/resultSchemas.test.ts",{"duration":10.511600000000044,"failed":false}],[":backend/src/utils/tokens.test.ts",{"duration":197.5005,"failed":false}],[":backend/src/validators/setupSchemas.test.ts",{"duration":12.653300000000058,"failed":false}],[":backend/src/utils/asyncHandler.test.ts",{"duration":8.633299999999963,"failed":false}],[":frontend/src/utils/api.test.ts",{"duration":5.6884000000000015,"failed":false}]]}
|
{"version":"4.1.5","results":[[":frontend/src/utils/grading.test.ts",{"duration":7.161699999999996,"failed":false}],[":frontend/src/utils/latex.test.ts",{"duration":9.518499999999989,"failed":false}],[":backend/src/validators/authSchemas.test.ts",{"duration":7.022400000000005,"failed":false}],[":frontend/src/utils/validation.test.ts",{"duration":4.217900000000014,"failed":false}],[":frontend/src/utils/storage.test.ts",{"duration":4.687600000000003,"failed":false}],[":backend/src/validators/examSchemas.test.ts",{"duration":6.788000000000011,"failed":false}],[":backend/src/validators/adminSchemas.test.ts",{"duration":7.534500000000008,"failed":false}],[":backend/src/middleware/error.test.ts",{"duration":2.5043000000000006,"failed":false}],[":frontend/src/utils/slug.test.ts",{"duration":4.5700999999999965,"failed":false}],[":frontend/src/utils/formatting.test.ts",{"duration":4.011300000000006,"failed":false}],[":backend/src/config.test.ts",{"duration":4.423100000000005,"failed":false}],[":backend/src/validators/resultSchemas.test.ts",{"duration":5.812899999999985,"failed":false}],[":backend/src/utils/tokens.test.ts",{"duration":73.72379999999998,"failed":false}],[":backend/src/validators/setupSchemas.test.ts",{"duration":5.070899999999995,"failed":false}],[":backend/src/utils/asyncHandler.test.ts",{"duration":4.5079000000000065,"failed":false}],[":frontend/src/utils/api.test.ts",{"duration":3.4222000000000037,"failed":false}]]}
|
||||||
Reference in new issue
Block a user