/** * 客观题试卷服务模块 * 负责试卷数据获取和处理 */ import { questionApi } from '../../../config/question_api.js'; /** * 获取试卷详情 * @param {String} paperId - 试卷ID * @param {String} taskId - 任务ID * @returns {Promise} 处理后的试卷数据 */ export function fetchQuestionPaper(paperId, taskId) { return new Promise((resolve, reject) => { if (!paperId) { reject(new Error('试卷ID不能为空')); return; } questionApi.getPaperDetail(paperId) .then(res => { let paperInfo = null; if (res && res.code === 200 && res.data) { paperInfo = res.data; } else if (res && res.success === true && (res.paper || res.data)) { paperInfo = res.paper || res.data; } if (paperInfo) { if (!paperInfo.questions || !Array.isArray(paperInfo.questions)) { reject(new Error('试卷数据格式错误')); return; } const mapped = paperInfo.questions.map(q => { // Fiber 后端返回的格式:QuestionInfo // { id, type (QuestionType: 1=主观题, 2=选择题, 3=判断题, 4=填空题), title, content, answer, explanation, options ([]string), tags } // 兼容旧格式(PHP后端) if (q && (q.question_id || q.question_content || q.question_type)) { return { ...q, id: q.question_id, title: q.question_content, type: q.question_type, materials: q.materials || [], options: (q.options || []).map(opt => ({ ...opt, id: opt.option_id, content: opt.option_content, label: opt.option_label })), user_answer: q.user_answer || null, explanation: q.explanation || '' }; } else { // Fiber 后端格式 // type: 1=主观题, 2=选择题(单选), 3=判断题, 4=填空题 // 对于客观题,type 应该是 2 (选择题) const opts = Array.isArray(q.options) ? q.options.map((text, idx) => ({ id: idx + 1, content: text, label: String.fromCharCode(65 + idx) // A, B, C... })) : []; // 映射题目类型 // Fiber: 2=选择题 -> 前端: 'single_choice' 或 'multiple_choice' // 这里默认是单选,如果需要判断多选,可能需要根据其他字段或答案格式 let mappedType = 'single_choice'; if (q.type === 2) { // 选择题,根据答案是否包含逗号判断单选或多选 const answer = q.answer || ''; mappedType = answer.includes(',') ? 'multiple_choice' : 'single_choice'; } else if (q.type === 3) { mappedType = 'true_false'; } else if (q.type === 4) { mappedType = 'fill_blank'; } return { ...q, id: q.id, title: q.title || q.content || '', type: mappedType, material_id: q.material_id || null, // 保留题目关联的材料ID materials: q.materials || [], // Fiber 后端可能没有 materials 字段 options: opts, user_answer: q.user_answer || null, explanation: q.explanation || '' }; } }); const questions = mapped.filter(q => Array.isArray(q.options) && q.options.length > 0); const answers = questions.map(question => { const optionsLength = question.options.length; const arr = new Array(optionsLength).fill(false); if (question.user_answer) { const userAnsArr = question.user_answer.split(',').map(s => s.trim()).filter(Boolean); userAnsArr.forEach(ans => { const idx = question.options.findIndex(opt => opt.label === ans); if (idx !== -1) arr[idx] = true; }); } return arr; }); // 确保 paperInfo 包含必要的字段 const finalPaperInfo = { ...paperInfo, title: paperInfo.title || '', description: paperInfo.description || '', duration_minutes: paperInfo.duration_minutes || 0 // Fiber 后端可能没有此字段,默认为 0 }; // 材料列表:后端 /paper/detail 返回 paper.materials,用于背景层左右滑动展示 const materials = Array.isArray(paperInfo.materials) ? paperInfo.materials : []; resolve({ paperInfo: finalPaperInfo, questions, answers, questionAnsweredStatus: answers.map(arr => arr.some(v => v)), materials }); } else { reject(new Error((res && res.message) || (res && res.msg) || '获取试卷失败')); } }) .catch(err => { console.error('API调用失败:', err); reject(err); }); }); }