mirror of
https://github.com/rgrgogu/new_starr.git
synced 2026-09-27 00:12:54 +08:00
forgot useMemo usage for AssetPickerSheet
Signed-off-by: Kenneth Obsequio <k80308392@gmail.com>
This commit is contained in:
@@ -313,7 +313,46 @@ exports.getCourse = async (req, res) => {
|
|||||||
|
|
||||||
// Access check — plan association → subscription field → individual purchase
|
// Access check — plan association → subscription field → individual purchase
|
||||||
if (!await canAccessCourse(req.user.user_id, courseId)) {
|
if (!await canAccessCourse(req.user.user_id, courseId)) {
|
||||||
return R.error(res, "You do not have access to this course.", 403);
|
// Still send the course's own basic info — including its unit/lesson
|
||||||
|
// structure (titles + durations, no lesson content/blocks/quiz answers)
|
||||||
|
// so the client can render the "Course content" outline as a preview,
|
||||||
|
// with an upsell prompt on every actionable button.
|
||||||
|
const blockedCourse = await Course.findOne({
|
||||||
|
where: { course_id: courseId, ...notDeleted },
|
||||||
|
attributes: COURSE_LIST_ATTRS,
|
||||||
|
include: [
|
||||||
|
{
|
||||||
|
model: Unit, as: "units",
|
||||||
|
where: notDeleted, required: false,
|
||||||
|
attributes: ["unit_id", "uuid", "title", "description", "duration_seconds"],
|
||||||
|
through: { attributes: ["order_index"] },
|
||||||
|
include: [
|
||||||
|
{
|
||||||
|
model: Lesson, as: "lessons",
|
||||||
|
where: notDeleted, required: false,
|
||||||
|
attributes: ["lesson_id", "uuid", "title", "description", "duration_seconds"],
|
||||||
|
through: { attributes: ["order_index"] },
|
||||||
|
},
|
||||||
|
{
|
||||||
|
model: UnitQuiz, as: "quiz",
|
||||||
|
required: false,
|
||||||
|
attributes: ["quiz_id", "uuid", "title"],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
});
|
||||||
|
const product = blockedCourse && await mdl_Product.findOne({
|
||||||
|
where: { purchasable_type: 'course', purchasable_id: courseId, is_active: true },
|
||||||
|
attributes: ['id', 'name', 'price', 'currency', 'access_days'],
|
||||||
|
});
|
||||||
|
const blockedPlain = blockedCourse ? blockedCourse.toJSON() : null;
|
||||||
|
if (blockedPlain) blockedPlain.units = flattenUnits(blockedPlain.units);
|
||||||
|
return res.status(403).json({
|
||||||
|
status: "error",
|
||||||
|
message: "You do not have access to this course.",
|
||||||
|
item: blockedPlain ? { ...blockedPlain, product: product ?? null } : null,
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
const course = await Course.findOne({
|
const course = await Course.findOne({
|
||||||
@@ -1311,7 +1350,19 @@ exports.getLessonsByUnitUuid = async (req, res) => {
|
|||||||
status: "error",
|
status: "error",
|
||||||
message: "You do not have access to this unit.",
|
message: "You do not have access to this unit.",
|
||||||
course: first ? { title: first.title, subscription: first.subscription } : null,
|
course: first ? { title: first.title, subscription: first.subscription } : null,
|
||||||
item: { uuid: unit.uuid, subscription: unit.subscription },
|
item: {
|
||||||
|
uuid: unit.uuid, subscription: unit.subscription,
|
||||||
|
title: unit.title, description: unit.description,
|
||||||
|
duration_seconds: unit.duration_seconds,
|
||||||
|
// Structure only (titles/durations) — no page.blocks/objectives content,
|
||||||
|
// no quiz questions — so the client can render the lessons/quiz outline
|
||||||
|
// as a preview without leaking any actual gated content.
|
||||||
|
lessons: (unit.lessons ?? []).map((l) => ({
|
||||||
|
lesson_id: l.lesson_id, uuid: l.uuid,
|
||||||
|
title: l.title, duration_seconds: l.duration_seconds,
|
||||||
|
})),
|
||||||
|
quiz: unit.quiz ? { quiz_id: unit.quiz.quiz_id, uuid: unit.quiz.uuid, title: unit.quiz.title } : null,
|
||||||
|
},
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -195,6 +195,15 @@ const DEFAULT_HANDLERS = {
|
|||||||
*/
|
*/
|
||||||
async function evaluateEntity({ entityType, entityId, userId, courseId = null, transaction = null }) {
|
async function evaluateEntity({ entityType, entityId, userId, courseId = null, transaction = null }) {
|
||||||
const t = transaction;
|
const t = transaction;
|
||||||
|
|
||||||
|
// Units always complete by passing their own quiz — overrides whatever
|
||||||
|
// completion_requirement type (if any) is configured on the unit. A unit
|
||||||
|
// with no quiz attached never completes (isUnitQuizPassed returns false).
|
||||||
|
if (entityType === 'unit') {
|
||||||
|
const completed = await isUnitQuizPassed({ unitId: entityId, userId, t });
|
||||||
|
return { status: completed ? 'completed' : 'in_progress', evaluated_via: 'quiz_required', satisfied: [] };
|
||||||
|
}
|
||||||
|
|
||||||
const rows = await CompletionRequirement.findAll({
|
const rows = await CompletionRequirement.findAll({
|
||||||
where: { entity_type: entityType, entity_id: entityId },
|
where: { entity_type: entityType, entity_id: entityId },
|
||||||
order: [['order', 'ASC']],
|
order: [['order', 'ASC']],
|
||||||
|
|||||||
Reference in New Issue
Block a user