{"record":{"id":"02fe988a01accc42","repo":"eyaltoledano/claude-task-master","slug":"task-existingtaskidnum-is-already-a-subtask-of","errorCode":null,"errorMessage":"Task ${existingTaskIdNum} is already a subtask of task ${existingTask.parentTaskId}","messagePattern":"Task (.+?) is already a subtask of task (.+?)","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"scripts/modules/task-manager/add-subtask.js","lineNumber":66,"sourceCode":"\t\tlet newSubtask;\n\n\t\t// Case 1: Convert an existing task to a subtask\n\t\tif (existingTaskId !== null) {\n\t\t\tconst existingTaskIdNum = parseInt(existingTaskId, 10);\n\n\t\t\t// Find the existing task\n\t\t\tconst existingTaskIndex = data.tasks.findIndex(\n\t\t\t\t(t) => t.id === existingTaskIdNum\n\t\t\t);\n\t\t\tif (existingTaskIndex === -1) {\n\t\t\t\tthrow new Error(`Task with ID ${existingTaskIdNum} not found`);\n\t\t\t}\n\n\t\t\tconst existingTask = data.tasks[existingTaskIndex];\n\n\t\t\t// Check if task is already a subtask\n\t\t\tif (existingTask.parentTaskId) {\n\t\t\t\tthrow new Error(\n\t\t\t\t\t`Task ${existingTaskIdNum} is already a subtask of task ${existingTask.parentTaskId}`\n\t\t\t\t);\n\t\t\t}\n\n\t\t\t// Check for circular dependency\n\t\t\tif (existingTaskIdNum === parentIdNum) {\n\t\t\t\tthrow new Error(`Cannot make a task a subtask of itself`);\n\t\t\t}\n\n\t\t\t// Check if parent task is a subtask of the task we're converting\n\t\t\t// This would create a circular dependency\n\t\t\tif (isTaskDependentOn(data.tasks, parentTask, existingTaskIdNum)) {\n\t\t\t\tthrow new Error(\n\t\t\t\t\t`Cannot create circular dependency: task ${parentIdNum} is already a subtask or dependent of task ${existingTaskIdNum}`\n\t\t\t\t);\n\t\t\t}\n\n\t\t\t// Find the highest subtask ID to determine the next ID","sourceCodeStart":48,"sourceCodeEnd":84,"githubUrl":"https://github.com/eyaltoledano/claude-task-master/blob/c0c98d367c55296bfe69e65680625b6db437af02/scripts/modules/task-manager/add-subtask.js#L48-L84","documentation":"addSubtask refuses to convert a task that already has a parentTaskId, since moving it silently would corrupt subtask bookkeeping. The error names both the task and its current parent so you can decide the correct operation.","triggerScenarios":"Calling addSubtask(parentId, existingTaskId) where the existing task's parentTaskId is already set (it is already a subtask of some task).","commonSituations":"Re-running a conversion that already succeeded, scripting bulk moves without checking parentTaskId, or attempting to nest a subtask under another task.","solutions":["Remove the task from its current parent (e.g. remove-subtask) before re-adding it.","If the current placement is correct, no action is needed — skip the call.","Adjust scripts to check existingTask.parentTaskId before attempting conversion.","If moving is intended, use the remove-then-add sequence explicitly."],"exampleFix":"// before\nawait addSubtask('2', '5'); // task 5 already subtask of 1\n// after\nawait removeSubtask('5');\nawait addSubtask('2', '5');","handlingStrategy":"validation","validationCode":"const data = readJSON(tasksPath, projectRoot, tag);\nconst t = data.tasks.find(t => t.id === parseInt(existingTaskId, 10));\nif (t?.parentTaskId) {\n  console.log(`Task ${t.id} already a subtask of ${t.parentTaskId}; skipping`);\n}","typeGuard":"function isConvertibleToSubtask(t) {\n  return t != null && t.parentTaskId == null;\n}","tryCatchPattern":"try {\n  await addSubtask(tasksPath, parentId, existingTaskId);\n} catch (err) {\n  if (err.message.includes('is already a subtask')) {\n    // already converted — treat as success (idempotent) or remove-subtask first\n  } else throw err;\n}","preventionTips":["Make conversion scripts idempotent by checking parentTaskId first","Track which tasks were already converted in batch jobs","Use remove-subtask explicitly when a move is intended","Log the parent task ID when converting so reruns can detect duplicates"],"tags":["tasks","subtasks","state-conflict","idempotency"],"backgroundTag":"task-already-subtask","analyzedSha":"c0c98d367c55296bfe69e65680625b6db437af02","analyzedAt":"2026-08-29T02:56:26.071Z","schemaVersion":2},"datasetVersion":"2026-08-29T07:17:48.351Z"}