mirror of
https://github.com/rgrgogu/new_starr.git
synced 2026-09-27 00:12:54 +08:00
@@ -17,7 +17,6 @@ const { TaskCompletion, TaskCompletionFile } = require('../../models/task/task_c
|
||||
const { TaskLinkVisit, TaskProgress } = require('../../models/task/task_progress.mdl');
|
||||
const { mdl_UserGroups, mdl_UserGroupMembers } = require('../../models/users/user_groups.mdl');
|
||||
const mdl_Users = require('../../models/users/users.mdl');
|
||||
const { QuizAttempt } = require('../../models/courses/courses.associations');
|
||||
|
||||
const { userExclude } = require('../../models/task/task.attributes');
|
||||
const { clientExclude } = require('../../models/task/task_completion.attributes');
|
||||
@@ -135,15 +134,9 @@ const isMember = async (userId, groupId) => {
|
||||
|
||||
// ─── Helper: per-user completion signals for a batch of tasks ─────────────────
|
||||
// Shared by getGroupTaskList/getGroupTaskLists. upload_file/submit_text share
|
||||
// one TaskCompletion per task (resubmit-anytime — latest by submitted_at wins);
|
||||
// pass_quiz is computed live from QuizAttempt, same as unit-quiz has_passed
|
||||
// (courses.controller.js) rather than a separately-synced TaskProgress row.
|
||||
const getTaskCompletionSignals = async (userId, taskIds, requirements) => {
|
||||
const quizIds = [...new Set(
|
||||
requirements.filter((r) => r.type === 'pass_quiz' && r.reference_id).map((r) => r.reference_id)
|
||||
)];
|
||||
|
||||
const [completions, linkVisits, progressRows, passedAttempts] = await Promise.all([
|
||||
// one TaskCompletion per task (resubmit-anytime — latest by submitted_at wins).
|
||||
const getTaskCompletionSignals = async (userId, taskIds) => {
|
||||
const [completions, linkVisits, progressRows] = await Promise.all([
|
||||
taskIds.length
|
||||
? TaskCompletion.findAll({
|
||||
where: { task_id: { [Op.in]: taskIds }, user_id: userId },
|
||||
@@ -163,12 +156,6 @@ const getTaskCompletionSignals = async (userId, taskIds, requirements) => {
|
||||
attributes: ['task_id', 'requirement_id', 'reference_id'],
|
||||
})
|
||||
: [],
|
||||
quizIds.length
|
||||
? QuizAttempt.findAll({
|
||||
where: { quiz_id: { [Op.in]: quizIds }, user_id: userId, passed: true },
|
||||
attributes: ['quiz_id'],
|
||||
})
|
||||
: [],
|
||||
]);
|
||||
|
||||
// First row per task_id wins — completions are ordered submitted_at DESC.
|
||||
@@ -181,7 +168,6 @@ const getTaskCompletionSignals = async (userId, taskIds, requirements) => {
|
||||
latestCompletionByTask,
|
||||
visitedRequirementIds: new Set(linkVisits.map((v) => v.requirement_id)),
|
||||
completedProgressKeys: new Set(progressRows.map((p) => `${p.requirement_id}:${p.reference_id}`)),
|
||||
passedQuizIds: new Set(passedAttempts.map((a) => String(a.quiz_id))),
|
||||
};
|
||||
};
|
||||
|
||||
@@ -200,8 +186,6 @@ const isRequirementDone = (r, signals) => {
|
||||
case 'read_unit':
|
||||
case 'read_lesson':
|
||||
return signals.completedProgressKeys.has(`${r.requirement_id}:${r.reference_id}`);
|
||||
case 'pass_quiz':
|
||||
return signals.passedQuizIds.has(String(r.reference_id));
|
||||
default:
|
||||
return true; // unknown requirement types don't block completion
|
||||
}
|
||||
@@ -241,7 +225,7 @@ const checkTaskCompletion = async (userId, taskId) => {
|
||||
const reqs = await TaskRequirement.findAll({ where: { task_id: taskId } });
|
||||
if (!reqs.length) return false;
|
||||
const plainReqs = reqs.map((r) => r.toJSON());
|
||||
const signals = await getTaskCompletionSignals(userId, [taskId], plainReqs);
|
||||
const signals = await getTaskCompletionSignals(userId, [taskId]);
|
||||
return plainReqs.every((r) => isRequirementDone(r, signals));
|
||||
};
|
||||
|
||||
@@ -359,8 +343,7 @@ exports.getGroupTaskList = async (req, res) => {
|
||||
await hydrateReadTaskProgress(userId, readRequirements);
|
||||
|
||||
// ── Fetch user's completion signals for these tasks ────────────────────
|
||||
const allRequirements = tasks.flatMap((task) => task.requirements ?? []);
|
||||
const signals = await getTaskCompletionSignals(userId, taskIds, allRequirements);
|
||||
const signals = await getTaskCompletionSignals(userId, taskIds);
|
||||
|
||||
const now = Date.now();
|
||||
|
||||
@@ -490,8 +473,7 @@ exports.getGroupTaskLists = async (req, res) => {
|
||||
await hydrateReadTaskProgress(userId, readRequirements);
|
||||
|
||||
// ── Fetch user's completion signals for these tasks ────────────────────
|
||||
const allRequirements = allTasks.flatMap((task) => task.requirements ?? []);
|
||||
const signals = await getTaskCompletionSignals(userId, taskIds, allRequirements);
|
||||
const signals = await getTaskCompletionSignals(userId, taskIds);
|
||||
|
||||
const now = Date.now();
|
||||
|
||||
|
||||
Reference in New Issue
Block a user