{"record":{"id":"666ce06299ef4af7","repo":"invoke-ai/InvokeAI","slug":"unexpected-error-while-canceling-by-destination","errorCode":null,"errorMessage":"Unexpected error while canceling by destination: {e}","messagePattern":"Unexpected error while canceling by destination: (.+?)","errorType":"http","errorClass":"HTTPException","httpStatus":500,"severity":"error","filePath":"invokeai/app/api/routers/session_queue.py","lineNumber":373,"sourceCode":"@session_queue_router.put(\n    \"/{queue_id}/cancel_by_destination\",\n    operation_id=\"cancel_by_destination\",\n    responses={200: {\"model\": CancelByDestinationResult}},\n)\ndef cancel_by_destination(\n    current_user: CurrentUserOrDefault,\n    queue_id: str = Path(description=\"The queue id to perform this operation on\"),\n    destination: str = Query(description=\"The destination to cancel all queue items for\"),\n) -> CancelByDestinationResult:\n    \"\"\"Immediately cancels all queue items with the given destination. Non-admin users can only cancel their own items.\"\"\"\n    try:\n        # Admin users can cancel all items, non-admin users can only cancel their own\n        user_id = None if current_user.is_admin else current_user.user_id\n        return ApiDependencies.invoker.services.session_queue.cancel_by_destination(\n            queue_id=queue_id, destination=destination, user_id=user_id\n        )\n    except Exception as e:\n        raise HTTPException(status_code=500, detail=f\"Unexpected error while canceling by destination: {e}\")\n\n\n@session_queue_router.put(\n    \"/{queue_id}/retry_items_by_id\",\n    operation_id=\"retry_items_by_id\",\n    responses={200: {\"model\": RetryItemsResult}},\n)\ndef retry_items_by_id(\n    current_user: CurrentUserOrDefault,\n    queue_id: str = Path(description=\"The queue id to perform this operation on\"),\n    item_ids: list[int] = Body(description=\"The queue item ids to retry\"),\n) -> RetryItemsResult:\n    \"\"\"Retries the given queue items. Users can only retry their own items unless they are an admin.\"\"\"\n    try:\n        # Check queue membership for all items and ownership for non-admins.\n        valid_item_ids: list[int] = []\n        for item_id in item_ids:\n            try:","sourceCodeStart":355,"sourceCodeEnd":391,"githubUrl":"https://github.com/invoke-ai/InvokeAI/blob/0b6a024f2ff6a86bfb953dcdb9cc504ef7397a06/invokeai/app/api/routers/session_queue.py#L355-L391","documentation":"Same catch-all 500 pattern as the batch-cancel route, but for cancel_by_destination: any exception from the session queue service while canceling items by destination id is converted into HTTP 500 with the original message appended. The destination parameter identifies the node destination whose items should be canceled.","triggerScenarios":"PUT /api/v1/queue/{queue_id}/cancel_by_destination with a destination string, when the underlying service call raises (DB failure, unknown destination, service-layer bug).","commonSituations":"Passing a destination id that no session/graph references; DB locked or down; server upgraded with schema mismatch; typo'd destination name from a workflow.","solutions":["Read the {e} text in the response detail plus server traceback for the root cause.","Validate the destination exists in the currently queued items (query queue items and inspect destination fields) before canceling.","Check database health and migrations as for other queue 500s.","Retry once after transient DB lock errors; otherwise fix the underlying DB/service condition."],"exampleFix":"// before: blind cancel by destination\nrequests.put(f\"{base}/api/v1/queue/{queue_id}/cancel_by_destination\", json={\"destination\": dest})\n// after: verify destination is present in queue first\nitems = requests.get(f\"{base}/api/v1/queue/{queue_id}/items\").json()[\"items\"]\nif any(i[\"destination\"] == dest for i in items):\n    requests.put(f\"{base}/api/v1/queue/{queue_id}/cancel_by_destination\", json={\"destination\": dest})","handlingStrategy":"validation","validationCode":"const items = (await fetch(`${base}/api/v1/queue/${queueId}/items`).then(r => r.json())).items;\nif (!items.some(i => i.destination === destination)) {\n  throw new Error(`destination ${destination} has no queued items`);\n}","typeGuard":"function hasItemsAtDestination(items, destination) {\n  return Array.isArray(items) && items.some(i => i?.destination === destination);\n}","tryCatchPattern":"try {\n  const r = await fetch(url, { method: 'PUT', body: JSON.stringify({ destination }) });\n  if (!r.ok) throw new Error((await r.json()).detail);\n} catch (e) {\n  logger.error(`cancel_by_destination failed: ${e.message}`);\n}","preventionTips":["Validate the destination exists among queued items first","Avoid typo'd destination names — derive them from graph definitions","Monitor DB lock errors during heavy queue churn","Re-check destinations after server upgrades/schema changes"],"tags":["http-500","fastapi","queue","database"],"backgroundTag":"unhandled-exception-wrapped-as-500","analyzedSha":"0b6a024f2ff6a86bfb953dcdb9cc504ef7397a06","analyzedAt":"2026-08-29T04:46:49.967Z","schemaVersion":2},"datasetVersion":"2026-08-29T07:17:48.351Z"}