eyaltoledano/claude-task-master · error · MoveTaskError
SUBTASK_NOT_FOUND
SUBTASK_NOT_FOUND
Error message
Source subtask ${sourceId} not found What it means
After finding the source parent, moveSubtaskToSubtask searches parent.subtasks for the subtask ID given in 'X.Y'. If the subtask is absent from the parent's subtasks array, it throws MoveTaskError with code SUBTASK_NOT_FOUND (message interpolates the full sourceId like '5.2').
Source
Thrown at scripts/modules/task-manager/move-task.js:250
MOVE_ERROR_CODES.PARENT_TASK_NOT_FOUND,
`Destination parent task with ID ${destParentId} not found`
);
}
// Initialize subtasks arrays if they don't exist (based on commit fixes)
if (!sourceParentTask.subtasks) {
sourceParentTask.subtasks = [];
}
if (!destParentTask.subtasks) {
destParentTask.subtasks = [];
}
// Find source subtask
const sourceSubtaskIndex = sourceParentTask.subtasks.findIndex(
(st) => st.id === sourceSubtaskId
);
if (sourceSubtaskIndex === -1) {
throw new MoveTaskError(
MOVE_ERROR_CODES.SUBTASK_NOT_FOUND,
`Source subtask ${sourceId} not found`
);
}
const sourceSubtask = sourceParentTask.subtasks[sourceSubtaskIndex];
if (sourceParentId === destParentId) {
// Moving within the same parent
if (destParentTask.subtasks.length > 0) {
const destSubtaskIndex = destParentTask.subtasks.findIndex(
(st) => st.id === destSubtaskId
);
if (destSubtaskIndex !== -1) {
// Remove from old position
sourceParentTask.subtasks.splice(sourceSubtaskIndex, 1);
// Insert at new position (adjust index if moving within same array)
const adjustedIndex =View on GitHub (pinned to c0c98d367c)
Solutions
- Run `task-master show <parentId>` to list the parent's actual subtask IDs and correct the ordinal
- Re-pull/sync tasks.json if another process modified it
- Remove empty parts of the source string (e.g. '5.' or '5,5.2' malformed entries) — parsing can yield NaN that matches nothing
- If the subtask was already moved, the operation is a no-op; skip it
Example fix
// before (task 5 has subtasks 1 and 2 only) task-master move --from=5.3 --to=7.1 // after task-master show 5 # subtasks: 5.1, 5.2 task-master move --from=5.2 --to=7.1
Defensive patterns
Strategy: validation
Validate before calling
function assertSourceSubtask(tasks, sourceId) {
const [p, s] = String(sourceId).split('.').map((n) => parseInt(n, 10));
const parent = tasks.find((t) => t.id === p);
if (!parent?.subtasks?.some((st) => st.id === s)) {
throw new Error(`Subtask ${sourceId} not found on parent ${p}`);
}
} Type guard
const subtaskExists = (tasks, sourceId) => {
const [p, s] = sourceId.split('.').map(Number);
return tasks.find((t) => t.id === p)?.subtasks?.some((st) => st.id === s) ?? false;
}; Try / catch
try {
await moveTask(tasksPath, '5.2', '7.1', false, { projectRoot, tag });
} catch (err) {
if (err.name === 'MoveTaskError' && err.code === 'SUBTASK_NOT_FOUND') {
console.error('Check `task-master show 5` for the actual subtask IDs');
} else throw err;
} Prevention
- Inspect the parent's subtasks with `task-master show <parentId>` before moving
- Don't reuse stale ID lists after any prior move — subtask IDs change location, not the operations' idempotency
- Sync tasks.json before scripted multi-step moves
- Guard with parent.subtasks.some(s => s.id === n) in automation
When it happens
Trigger: Calling moveTask('5.3', '7.1') where task 5 exists but has no subtask with id 3; subtask was already moved/deleted; using a 1-based vs 0-based ID confusion (subtask IDs are stored as given, typically 1-based).
Common situations: Stale local tasks.json after a teammate moved the subtask; typo in the subtask ordinal; assuming subtasks auto-exist; hand-edited tasks.json where the subtasks array lost the entry.
Related errors
- PARENT_TASK_NOT_FOUND
- Parent task ${parentId} not found
- Subtask ${subtaskId} not found in parent task ${parentId}
- PARENT_TASK_NO_SUBTASKS
- Invalid iterations: ${iterations}. Must be a positive intege
AI-assisted analysis of eyaltoledano/claude-task-master@c0c98d367c (2026-08-29).
Data as JSON: /api/errors/6fc7989771c4ae2b.
Report an issue: GitHub.