2026-08-17 12:25:42 +08:00
|
|
|
|
import request from './request'
|
|
|
|
|
|
|
|
|
|
|
|
// ==================== 管理员后台 API ====================
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取管理后台统计数据
|
|
|
|
|
|
* @returns {Promise} { totalAccounts, activatedAccounts, submissionsCount, ... }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getStats(params = {}) {
|
|
|
|
|
|
return request.get('/admin/stats', { params })
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取账号列表(含筛选)
|
|
|
|
|
|
* @param {object} params - { page, pageSize, keyword, group, status }
|
|
|
|
|
|
* @returns {Promise} { list, total, page, pageSize }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getAccounts(params) {
|
|
|
|
|
|
return request.get('/admin/accounts', { params })
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 导入 Excel 批量创建账号
|
|
|
|
|
|
* @param {FormData} formData - 包含 Excel 文件的 FormData
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function importExcel(formData) {
|
|
|
|
|
|
// 注意:不要手动设置 Content-Type。axios/浏览器在发送 FormData 时会自动补上
|
|
|
|
|
|
// `multipart/form-data; boundary=...`;手动写死 'multipart/form-data'(无 boundary)
|
|
|
|
|
|
// 会导致后端 getFileStream 解析失败(Missing boundary)-> 500,且永不落库。
|
|
|
|
|
|
return request.post('/admin/import-excel', formData, {
|
|
|
|
|
|
timeout: 60000,
|
|
|
|
|
|
})
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取参赛作品列表(按组别)
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @returns {Promise} 作品列表
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getSubmissions(group) {
|
|
|
|
|
|
return request.get(`/admin/submissions/${group}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取比赛时间配置
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getTimes() {
|
|
|
|
|
|
return request.get('/admin/times')
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 设置比赛时间
|
|
|
|
|
|
* @param {Object} data - { zhongzhi: {start, end}, gaozhi: ... }
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function setTimes(data) {
|
|
|
|
|
|
// 后端要求 times 数组,格式:[{ group, startTime, endTime, deadline, choiceCount, judgeCount }]
|
|
|
|
|
|
// 注意:必须携带 choiceCount / judgeCount,否则后端按缺省 50/20 处理,后台「抽取数量」配置无法落库
|
|
|
|
|
|
const times = Object.entries(data).map(([group, item]) => ({
|
|
|
|
|
|
group,
|
|
|
|
|
|
startTime: item.start,
|
|
|
|
|
|
endTime: item.end,
|
|
|
|
|
|
deadline: item.deadline,
|
|
|
|
|
|
choiceCount: item.choiceCount != null ? parseInt(item.choiceCount, 10) : 50,
|
|
|
|
|
|
judgeCount: item.judgeCount != null ? parseInt(item.judgeCount, 10) : 20,
|
|
|
|
|
|
}))
|
|
|
|
|
|
return request.put('/admin/times', { times })
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 设置评分
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {object} data - 评分数据
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function setScores(group, data) {
|
|
|
|
|
|
return request.put(`/admin/scores/${group}`, data)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取考题列表(管理员,含答案,按题型分表返回)
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @returns {Promise} { choice: [...], judge: [...], word: [...] }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getQuestions(group) {
|
|
|
|
|
|
return request.get(`/admin/exam/${group}/questions`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取作品管理统一列表(覆盖全部 4 个组别)
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @returns {Promise} { list: [{ contestantId, name, idNumber, phone, group, files: [...] }] }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getWorks(group) {
|
|
|
|
|
|
return request.get(`/admin/works/${group}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 批量删除题目(按题型)
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {string} questionType - choice / judge / word
|
|
|
|
|
|
* @param {number[]} ids - 题目 ID 数组
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function bulkDeleteQuestions(group, questionType, ids) {
|
|
|
|
|
|
return request.put(`/admin/exam/${group}/questions`, {
|
|
|
|
|
|
question_type: questionType,
|
|
|
|
|
|
action: 'bulkDelete',
|
|
|
|
|
|
question_uids: ids,
|
|
|
|
|
|
})
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 设置考题(按题型分表管理)
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {string} questionType - 题型:choice / judge / word
|
|
|
|
|
|
* @param {object} data - 考题数据 { questions: [...], action: 'add'|'update'|'delete' }
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function setQuestions(group, questionType, data) {
|
|
|
|
|
|
return request.put(`/admin/exam/${group}/questions`, {
|
|
|
|
|
|
question_type: questionType,
|
|
|
|
|
|
...data,
|
|
|
|
|
|
})
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 客观题 Excel 批量导入(单工作表:题型/题目/选项A~D/正确答案/分值)
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {FormData} formData - 包含 Excel 文件的 FormData(字段名 file)
|
|
|
|
|
|
* @returns {Promise} { imported, skipped, errors }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function importQuestionsExcel(group, formData) {
|
|
|
|
|
|
// 同上:不要手动设置 Content-Type,避免缺失 boundary 导致后端解析 500。
|
|
|
|
|
|
return request.post(`/admin/exam/${group}/questions/import-excel`, formData, {
|
|
|
|
|
|
timeout: 120000,
|
|
|
|
|
|
})
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 上传 Word 答题模板
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {FormData} formData - 包含 Word 文件的 FormData
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function uploadWordTemplate(group, formData) {
|
|
|
|
|
|
return request.put(`/admin/exam/${group}/word-template`, formData, {
|
|
|
|
|
|
timeout: 30000,
|
|
|
|
|
|
})
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取 Word 模板信息
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getWordTemplate(group) {
|
|
|
|
|
|
return request.get(`/admin/exam/${group}/word-template`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 删除 Word 模板
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function deleteWordTemplate(group) {
|
|
|
|
|
|
return request.delete(`/admin/exam/${group}/word-template`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// ==================== 备赛资料管理 ====================
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取备赛资料列表
|
|
|
|
|
|
* @param {string} group - 组别
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getMaterials(group) {
|
|
|
|
|
|
return request.get(`/admin/materials/${group}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 上传备赛资料
|
|
|
|
|
|
* @param {string} group - 组别
|
|
|
|
|
|
* @param {FormData} formData - 文件
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function uploadMaterial(group, formData) {
|
|
|
|
|
|
return request.post(`/admin/materials/${group}`, formData, { timeout: 60000 })
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 删除备赛资料
|
|
|
|
|
|
* @param {string} group - 组别
|
|
|
|
|
|
* @param {string} fileName - 文件名
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function deleteMaterial(group, fileName) {
|
|
|
|
|
|
return request.delete(`/admin/materials/${group}/${encodeURIComponent(fileName)}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// ==================== 成绩管理 ====================
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取某组成绩列表(管理员)
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @returns {Promise} 成绩列表
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getScores(group) {
|
|
|
|
|
|
return request.get(`/admin/scores/${group}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 发布/撤回指定组别的成绩
|
|
|
|
|
|
*
|
|
|
|
|
|
* 发布状态按组独立存储:发布本科组不会让中职组考生看到成绩。
|
|
|
|
|
|
* 不传 group 时对全部组生效(批量操作)。
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {boolean} publish - true: 发布, false: 撤回
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function publishScores(group, publish) {
|
|
|
|
|
|
return request.put('/admin/publish-scores', group ? { publish, group } : { publish })
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取成绩发布状态
|
|
|
|
|
|
* @param {string} group - 组别标识;不传时 published 表示「全部组均已发布」
|
|
|
|
|
|
* @returns {Promise} { published, group, groups: { zhongzhi, gaozhi, benke, jiaoshi } }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getPublishStatus(group) {
|
|
|
|
|
|
return request.get('/admin/publish-scores', group ? { params: { group } } : undefined)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// ==================== 新闻管理 ====================
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取新闻列表(管理员)
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function listNews() {
|
|
|
|
|
|
return request.get('/admin/news')
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 创建新闻
|
|
|
|
|
|
* @param {object} data - { title, content, category, coverImage }
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function createNews(data) {
|
|
|
|
|
|
return request.post('/admin/news', data)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 更新新闻
|
|
|
|
|
|
* @param {number|string} id - 新闻 ID
|
|
|
|
|
|
* @param {object} data - 更新的字段
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function updateNews(id, data) {
|
|
|
|
|
|
return request.put(`/admin/news/${id}`, data)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 删除新闻
|
|
|
|
|
|
* @param {number|string} id - 新闻 ID
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function deleteNews(id) {
|
|
|
|
|
|
return request.delete(`/admin/news/${id}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 更新新闻排序
|
|
|
|
|
|
* @param {Array<{id: number, sort_order: number}>} orders
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function updateNewsOrder(orders) {
|
|
|
|
|
|
return request.put('/admin/news/order', { orders })
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// ==================== 轮播图管理 ====================
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取轮播图列表(管理员)
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function listCarousel() {
|
|
|
|
|
|
return request.get('/admin/carousel')
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 添加轮播图
|
|
|
|
|
|
* @param {object} data - { imageUrl, linkUrl, sortOrder, title }
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function addCarousel(data) {
|
|
|
|
|
|
return request.post('/admin/carousel', data)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 更新轮播图
|
|
|
|
|
|
* @param {number|string} id - 轮播图 ID
|
|
|
|
|
|
* @param {object} data - 更新的字段
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function updateCarousel(id, data) {
|
|
|
|
|
|
return request.put(`/admin/carousel/${id}`, data)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 删除轮播图
|
|
|
|
|
|
* @param {number|string} id - 轮播图 ID
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function deleteCarousel(id) {
|
|
|
|
|
|
return request.delete(`/admin/carousel/${id}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 批量更新轮播图排序
|
|
|
|
|
|
* @param {Array} orders - [{ id, sort_order }]
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function updateCarouselOrder(orders) {
|
|
|
|
|
|
return request.put('/admin/carousel/order', { orders })
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// ==================== 测试数据标记与重置 ====================
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 切换选手的测试数据标记
|
|
|
|
|
|
* @param {number} id - 选手ID
|
|
|
|
|
|
* @param {number} testFlag - 0=生产数据, 1=测试数据
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function toggleTestFlag(id, testFlag) {
|
|
|
|
|
|
return request.post('/admin/toggle-test-flag', { id, test_flag: testFlag })
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 重置测试数据(仅重置 test_flag=1 的选手及其提交记录)
|
|
|
|
|
|
* @returns {Promise}
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function resetTestData() {
|
|
|
|
|
|
return request.post('/admin/reset-test-data')
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2026-09-21 11:17:59 +08:00
|
|
|
|
// ==================== 综合大题管理(中职/高职) ====================
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取综合大题题库(按组别)
|
|
|
|
|
|
*
|
|
|
|
|
|
* 仅中职/高职启用;本科/教师组调用返回 400(未启用综合大题)。
|
|
|
|
|
|
* @param {string} group - 组别标识(zhongzhi / gaozhi)
|
|
|
|
|
|
* @returns {Promise} {
|
|
|
|
|
|
* list: [{ id, questionUid, group, title, description,
|
|
|
|
|
|
* subPrompt1, subPrompt2, subPrompt3,
|
|
|
|
|
|
* scorePerSub, totalScore, sortOrder, status, createdAt, updatedAt }],
|
|
|
|
|
|
* total, scorePerSub, subCount, maxChars
|
|
|
|
|
|
* }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getBigQuestions(group) {
|
|
|
|
|
|
return request.get(`/admin/big-questions/${group}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 新增大题
|
|
|
|
|
|
*
|
|
|
|
|
|
* 题干 description 为富文本 HTML(支持表格);三小问提示 subPrompt1~3 与题干同存一行。
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {object} data - { title, description, subPrompt1, subPrompt2, subPrompt3, scorePerSub, sortOrder, status }
|
|
|
|
|
|
* @returns {Promise} { id, questionUid }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function createBigQuestion(group, data) {
|
|
|
|
|
|
return request.post(`/admin/big-questions/${group}`, data)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 更新大题
|
|
|
|
|
|
*
|
|
|
|
|
|
* 注意:已被考生抽取的题目仍可修改,但考生端展示的是抽题时刻的题干快照,
|
|
|
|
|
|
* 不会受此修改影响(防纠纷设计)。
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {number|string} id - 大题 ID
|
|
|
|
|
|
* @param {object} data - 同 createBigQuestion
|
|
|
|
|
|
* @returns {Promise} { id }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function updateBigQuestion(group, id, data) {
|
|
|
|
|
|
return request.put(`/admin/big-questions/${group}/${id}`, data)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 删除大题
|
|
|
|
|
|
*
|
|
|
|
|
|
* 已被考生抽取的题目服务端拒绝删除(返回 409),避免作答记录悬空。
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {number|string} id - 大题 ID
|
|
|
|
|
|
* @returns {Promise} { deleted }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function deleteBigQuestion(group, id) {
|
|
|
|
|
|
return request.delete(`/admin/big-questions/${group}/${id}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 获取大题作答与查证列表(覆盖该组全部考生,含未抽题者)
|
|
|
|
|
|
*
|
|
|
|
|
|
* 每行含考生信息、抽题快照、三小问答案、已答数量、三小问得分、大题总分与提交时间,
|
|
|
|
|
|
* 供管理员核对考生实际抽到的题目与作答内容,避免考生纠纷。
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @returns {Promise} {
|
|
|
|
|
|
* list: [{ contestantId, aggregationUid, name, idNumber, phone, teamId,
|
|
|
|
|
|
* drawn, bigQuestionUid, questionSnapshot,
|
|
|
|
|
|
* answer1, answer2, answer3, answeredCount,
|
|
|
|
|
|
* score1, score2, score3, bigScore, wordScore, submitTime }],
|
|
|
|
|
|
* total, drawnCount
|
|
|
|
|
|
* }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function getBigAnswers(group) {
|
|
|
|
|
|
return request.get(`/admin/big-answers/${group}`)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
|
* 录入三小问得分(小题分)
|
|
|
|
|
|
*
|
|
|
|
|
|
* 服务端逐问校验 0 ~ scorePerSub 区间,累加后经唯一评分写路径
|
|
|
|
|
|
* service.admin.updateScores 落 contestants.word_score(中职/高职总分 = exam_score + word_score)。
|
|
|
|
|
|
* @param {string} group - 组别标识
|
|
|
|
|
|
* @param {number|string} uid - 考生聚合 ID(aggregation_uid)
|
|
|
|
|
|
* @param {{score_1: number, score_2: number, score_3: number}} scores
|
|
|
|
|
|
* @returns {Promise} { total, perSubScore }
|
|
|
|
|
|
*/
|
|
|
|
|
|
export function setBigAnswerScores(group, uid, scores) {
|
|
|
|
|
|
return request.put(`/admin/big-answers/${group}/${uid}/scores`, scores)
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2026-08-17 12:25:42 +08:00
|
|
|
|
|