Pending course, rest ready for launch
This commit is contained in:
107
app/(public)/courses/[slug]/learn/actions.ts
Normal file
107
app/(public)/courses/[slug]/learn/actions.ts
Normal file
@@ -0,0 +1,107 @@
|
||||
"use server";
|
||||
|
||||
import { revalidatePath } from "next/cache";
|
||||
import { requireUser } from "@/lib/auth/requireUser";
|
||||
import { db } from "@/lib/prisma";
|
||||
import { issueCertificateIfEligible } from "@/lib/certificates";
|
||||
import { refreshStudyRecommendations } from "@/lib/recommendations";
|
||||
|
||||
type ToggleLessonCompleteInput = {
|
||||
courseSlug: string;
|
||||
lessonId: string;
|
||||
};
|
||||
|
||||
export async function toggleLessonComplete({ courseSlug, lessonId }: ToggleLessonCompleteInput) {
|
||||
const user = await requireUser();
|
||||
|
||||
if (!user?.id) {
|
||||
return { success: false, error: "Unauthorized" };
|
||||
}
|
||||
|
||||
const lesson = await db.lesson.findUnique({
|
||||
where: { id: lessonId },
|
||||
select: {
|
||||
id: true,
|
||||
module: {
|
||||
select: {
|
||||
courseId: true,
|
||||
course: {
|
||||
select: {
|
||||
slug: true,
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
});
|
||||
|
||||
if (!lesson || lesson.module.course.slug !== courseSlug) {
|
||||
return { success: false, error: "Lesson not found" };
|
||||
}
|
||||
|
||||
const enrollment = await db.enrollment.findUnique({
|
||||
where: {
|
||||
userId_courseId: {
|
||||
userId: user.id,
|
||||
courseId: lesson.module.courseId,
|
||||
},
|
||||
},
|
||||
select: { id: true },
|
||||
});
|
||||
|
||||
if (!enrollment) {
|
||||
return { success: false, error: "Not enrolled in this course" };
|
||||
}
|
||||
|
||||
const existingProgress = await db.userProgress.findUnique({
|
||||
where: {
|
||||
userId_lessonId: {
|
||||
userId: user.id,
|
||||
lessonId,
|
||||
},
|
||||
},
|
||||
select: {
|
||||
id: true,
|
||||
isCompleted: true,
|
||||
},
|
||||
});
|
||||
|
||||
const nextCompleted = !existingProgress?.isCompleted;
|
||||
|
||||
if (existingProgress) {
|
||||
await db.userProgress.update({
|
||||
where: { id: existingProgress.id },
|
||||
data: {
|
||||
isCompleted: nextCompleted,
|
||||
finishedAt: nextCompleted ? new Date() : null,
|
||||
lastPlayedAt: new Date(),
|
||||
},
|
||||
});
|
||||
} else {
|
||||
await db.userProgress.create({
|
||||
data: {
|
||||
userId: user.id,
|
||||
lessonId,
|
||||
isCompleted: true,
|
||||
finishedAt: new Date(),
|
||||
},
|
||||
});
|
||||
}
|
||||
|
||||
const certificateResult = nextCompleted
|
||||
? await issueCertificateIfEligible(user.id, lesson.module.courseId)
|
||||
: { certificateId: null, certificateNumber: null, newlyIssued: false };
|
||||
|
||||
revalidatePath(`/courses/${courseSlug}/learn`);
|
||||
revalidatePath("/my-courses");
|
||||
revalidatePath("/profile");
|
||||
await refreshStudyRecommendations(user.id);
|
||||
|
||||
return {
|
||||
success: true,
|
||||
isCompleted: nextCompleted,
|
||||
certificateId: certificateResult.certificateId,
|
||||
certificateNumber: certificateResult.certificateNumber,
|
||||
newlyIssuedCertificate: certificateResult.newlyIssued,
|
||||
};
|
||||
}
|
||||
Reference in New Issue
Block a user