shareAI-lab/learn-claude-code · error · ValueError
Task {tid} not found
Error message
Task {tid} not found What it means
Raised by TaskManager._load in s_full.py when no file task_{tid}.json exists in TASKS_DIR. Every task operation (get, update status, assign owner, etc.) loads through _load, so any reference to a deleted or never-created id fails here. Ids are assigned by scanning existing files (max id + 1), so gaps from deleted tasks are never reused and those ids fail permanently.
Source
Thrown at agents/s_full.py:272
)
summary = resp.content[0].text
return [
{"role": "user", "content": f"[Compressed. Transcript: {path}]\n{summary}"},
]
# === SECTION: file_tasks (s07) ===
class TaskManager:
def __init__(self):
TASKS_DIR.mkdir(exist_ok=True)
def _next_id(self) -> int:
ids = [int(f.stem.split("_")[1]) for f in TASKS_DIR.glob("task_*.json")]
return max(ids, default=0) + 1
def _load(self, tid: int) -> dict:
p = TASKS_DIR / f"task_{tid}.json"
if not p.exists(): raise ValueError(f"Task {tid} not found")
return json.loads(p.read_text())
def _save(self, task: dict):
(TASKS_DIR / f"task_{task['id']}.json").write_text(json.dumps(task, indent=2))
def create(self, subject: str, description: str = "") -> str:
task = {"id": self._next_id(), "subject": subject, "description": description,
"status": "pending", "owner": None, "blockedBy": []}
self._save(task)
return json.dumps(task, indent=2)
def get(self, tid: int) -> str:
return json.dumps(self._load(tid), indent=2)
def update(self, tid: int, status: str = None,
add_blocked_by: list = None, remove_blocked_by: list = None) -> str:
task = self._load(tid)
if status:View on GitHub (pinned to 985456f4ad)
Solutions
- Always use the id returned from tasks.create() and thread it through the flow verbatim
- Before acting, verify existence via the list tool or TASKS_DIR glob rather than assuming
- If the tasks directory was reset, recreate the task and update stored references to the new id
- Catch ValueError at the tool boundary and re-list tasks so the agent can self-correct
Example fix
// before tasks.get(42) # never created // after t = tasks.create(subject="Fix login", description="...") tasks.get(t["id"])
Defensive patterns
Strategy: validation
Validate before calling
def task_exists(tid: int) -> bool:
return (TASKS_DIR / f"task_{tid}.json").exists()
if not task_exists(tid):
t = TASKS.create(subject=fallback_subject)
tid = t['id']
result = TASKS.get(tid) Try / catch
try:
TASKS.get(tid)
except ValueError as e:
if 'not found' in str(e):
tasks = TASKS.list()
# pick or recreate the right task, then retry
else:
raise Prevention
- Thread ids returned by create() through the entire flow
- Never construct ids from model guesses
- After resetting the tasks dir, invalidate all cached task references
When it happens
Trigger: Calling tasks.get(5) when task_5.json was never created or was deleted; reusing an id captured in an earlier session after the tasks directory was reset; passing a task id hallucinated by an LLM instead of one returned by create().
Common situations: Agent flows that guess ids; persisted plans referencing tasks across a workspace reset that wiped TASKS_DIR; races where cleanup deletes a task between listing and acting on it.
Related errors
- Task {task_id} not found
- Task {task_id} not found
- expected a JSON list
- invalid job ID
- prompt cannot be empty
AI-assisted analysis of shareAI-lab/learn-claude-code@985456f4ad (2026-08-14).
Data as JSON: /api/errors/36bcd21c1dfc06c0.
Report an issue: GitHub.