import { z } from "zod" const isValidDateString = (v: string | null | undefined): boolean => { if (v === null || v === undefined || v === "") return true const d = new Date(v) return !Number.isNaN(d.getTime()) } export const CreateCoursePlanSchema = z .object({ classId: z.string().trim().min(1), subjectId: z.string().trim().min(1), teacherId: z.string().trim().min(1), academicYearId: z.string().trim().optional().nullable(), semester: z.enum(["1", "2"]).optional(), totalHours: z.coerce.number().int().min(0).optional(), weeklyHours: z.coerce.number().int().min(0).optional(), startDate: z .string() .trim() .optional() .nullable() .refine(isValidDateString, "开始日期格式无效"), endDate: z .string() .trim() .optional() .nullable() .refine(isValidDateString, "结束日期格式无效"), syllabus: z.string().trim().optional().nullable(), objectives: z.string().trim().optional().nullable(), status: z.enum(["planning", "active", "completed", "paused"]).optional(), }) .transform((v) => ({ classId: v.classId, subjectId: v.subjectId, teacherId: v.teacherId, academicYearId: v.academicYearId && v.academicYearId.length > 0 ? v.academicYearId : null, semester: v.semester ?? "1", totalHours: v.totalHours ?? 0, weeklyHours: v.weeklyHours ?? 0, startDate: v.startDate && v.startDate.length > 0 ? v.startDate : null, endDate: v.endDate && v.endDate.length > 0 ? v.endDate : null, syllabus: v.syllabus && v.syllabus.length > 0 ? v.syllabus : null, objectives: v.objectives && v.objectives.length > 0 ? v.objectives : null, status: v.status ?? "planning", })) export type CreateCoursePlanInput = z.infer export const UpdateCoursePlanSchema = z .object({ classId: z.string().trim().min(1).optional(), subjectId: z.string().trim().min(1).optional(), teacherId: z.string().trim().min(1).optional(), academicYearId: z.string().trim().optional().nullable(), semester: z.enum(["1", "2"]).optional(), totalHours: z.coerce.number().int().min(0).optional(), completedHours: z.coerce.number().int().min(0).optional(), weeklyHours: z.coerce.number().int().min(0).optional(), startDate: z .string() .trim() .optional() .nullable() .refine(isValidDateString, "开始日期格式无效"), endDate: z .string() .trim() .optional() .nullable() .refine(isValidDateString, "结束日期格式无效"), syllabus: z.string().trim().optional().nullable(), objectives: z.string().trim().optional().nullable(), status: z.enum(["planning", "active", "completed", "paused"]).optional(), }) .transform((v) => ({ ...v, academicYearId: v.academicYearId !== undefined ? v.academicYearId && v.academicYearId.length > 0 ? v.academicYearId : null : undefined, startDate: v.startDate !== undefined ? v.startDate && v.startDate.length > 0 ? v.startDate : null : undefined, endDate: v.endDate !== undefined ? v.endDate && v.endDate.length > 0 ? v.endDate : null : undefined, syllabus: v.syllabus !== undefined ? v.syllabus && v.syllabus.length > 0 ? v.syllabus : null : undefined, objectives: v.objectives !== undefined ? v.objectives && v.objectives.length > 0 ? v.objectives : null : undefined, })) export type UpdateCoursePlanInput = z.infer export const CreateCoursePlanItemSchema = z .object({ planId: z.string().trim().min(1), week: z.coerce.number().int().min(1), topic: z.string().trim().min(1).max(255), content: z.string().trim().optional().nullable(), hours: z.coerce.number().int().min(1).optional(), textbookChapter: z.string().trim().optional().nullable(), notes: z.string().trim().optional().nullable(), }) .transform((v) => ({ planId: v.planId, week: v.week, topic: v.topic, content: v.content && v.content.length > 0 ? v.content : null, hours: v.hours ?? 2, textbookChapter: v.textbookChapter && v.textbookChapter.length > 0 ? v.textbookChapter : null, notes: v.notes && v.notes.length > 0 ? v.notes : null, })) export type CreateCoursePlanItemInput = z.infer export const UpdateCoursePlanItemSchema = z .object({ week: z.coerce.number().int().min(1).optional(), topic: z.string().trim().min(1).max(255).optional(), content: z.string().trim().optional().nullable(), hours: z.coerce.number().int().min(1).optional(), textbookChapter: z.string().trim().optional().nullable(), notes: z.string().trim().optional().nullable(), isCompleted: z.boolean().optional(), completedAt: z .string() .trim() .optional() .nullable() .refine(isValidDateString, "完成日期格式无效"), }) .transform((v) => ({ ...v, content: v.content !== undefined ? v.content && v.content.length > 0 ? v.content : null : undefined, textbookChapter: v.textbookChapter !== undefined ? v.textbookChapter && v.textbookChapter.length > 0 ? v.textbookChapter : null : undefined, notes: v.notes !== undefined ? v.notes && v.notes.length > 0 ? v.notes : null : undefined, completedAt: v.completedAt !== undefined ? v.completedAt && v.completedAt.length > 0 ? v.completedAt : null : undefined, })) export type UpdateCoursePlanItemInput = z.infer