yikart/AiToEarn · error · AppHttpException
ErrHttpBack.task_no_material
ErrHttpBack.task_no_material
Error message
task_no_material
What it means
AppHttpException with ErrHttpBack.task_no_material (errCode 90000, message '该任务没有添加素材'). Thrown by AdminTaskService.updateStatus (adminTask.service.ts:108) when an admin activates (status=TaskStatus.ACTIVE) a task of type TaskType.ARTICLE but no TaskMaterial document exists for that taskId. ARTICLE tasks must carry at least one material before going live.
Source
Thrown at project/aitoearn-electron/server/src/modules/task/adminTask.service.ts:108
const updatedTask = await this.taskModel.findByIdAndUpdate(id, data).exec();
if (!updatedTask) throw new NotFoundException('Task not found');
return updatedTask;
}
/**
* 更新任务状态
* @param task
* @param status
* @returns
*/
async updateStatus(task: Task, status: TaskStatus): Promise<Task> {
if (status === TaskStatus.ACTIVE && task.type === TaskType.ARTICLE) {
// 查询是否存在任务的素材
const material = await this.taskMaterialModel.findOne({
taskId: task.id,
});
if (!material) throw new AppHttpException(ErrHttpBack.task_no_material);
}
const res = await this.taskModel.findByIdAndUpdate(
{ _id: task.id },
{
status,
},
);
return res;
}
/**
* 更新任务状态
* @param id
* @param status
* @returns
*/View on GitHub (pinned to d3aa8bea5b)
Solutions
- Add at least one task material for the task (admin material creation endpoint) before activating it
- Verify a material exists: query materials with filter { taskId } and create one if empty
- If the task should not require material, change its type away from ARTICLE
- Check the material's taskId field actually references this task (not another task's id)
Example fix
// before
await adminTaskApi.updateStatus(taskId, 'ACTIVE') // throws 90000
// after
await adminTaskApi.createTaskMaterial({ taskId, ...material })
await adminTaskApi.updateStatus(taskId, 'ACTIVE') Defensive patterns
Strategy: validation
Validate before calling
const material = await adminTaskApi.findTaskMaterial({ taskId })
if (!material && task.type === 'ARTICLE') {
throw new Error('Cannot activate ARTICLE task without material')
} Type guard
function canActivate(task: Task, materials: TaskMaterial[]): boolean {
return task.type !== 'ARTICLE' || materials.length > 0
} Try / catch
try {
await adminTaskApi.updateStatus(taskId, 'ACTIVE')
} catch (e) {
if (e?.errCode === '90000') {
// create a material for the task, then retry activation
} else throw e
} Prevention
- Enforce material upload in the admin UI when task type is ARTICLE
- Block material deletion while the task is active
- Run a pre-activation checklist: type, material presence, taskId linkage
When it happens
Trigger: Admin PATCH/POST to update a task's status to ACTIVE where task.type === ARTICLE and taskMaterialModel.findOne({ taskId }) returns null — the article task was created without uploading/attaching material.
Common situations: Admin forgets to add material in the admin panel; material was deleted after task creation; task type later switched to ARTICLE without adding material; wrong taskId linkage between task and material collections.
Related errors
- No subtitle entries in response
- No response from Gemini
- Invalid subtitle data: ${z.prettifyError(result.error)}
- Canvas not provided and no vid:// video source found in Trac
- Canvas not provided and failed to retrieve video dimensions
AI-assisted analysis of yikart/AiToEarn@d3aa8bea5b (2026-08-31).
Data as JSON: /api/errors/4fb4f2a300cedc74.
Report an issue: GitHub.