Repository navigation
Return 404 when a DagRun disappears during task API writes - #72907
pierrejeambrun merged 10 commits into
Conversation
jason810496
left a comment
There was a problem hiding this comment.
Thanks for the improvement, LGTM overall.
3a0ede1 to
c3aba24
Compare
jason810496
left a comment
There was a problem hiding this comment.
LGTM after the update, thanks.
Wait for the change of #72926 (review) get in this PR.
Signed-off-by: 1fanwang <[email protected]>
The conflict merge kept the dedicated DagRunNotFound exception but retained an upstream test that raised ValueError, so current-head CI failed before exercising the route contract. Signed-off-by: Stefan Wang <[email protected]>
Signed-off-by: 1fanwang <[email protected]>
Signed-off-by: 1fanwang <[email protected]>
|
Thanks again for the review @jason810496, is this good to go? Thnx |
henry3260
left a comment
There was a problem hiding this comment.
Thanks for the PR, looks good!
|
Need to resolve conflits cc @jason810496 |
Main reworked the public task state store routes around task coordinates and added more 2026-10-30 Execution API version changes. Keep both sides: the new DynamicRegion import next to DagRunNotFound, and ReturnNotFoundForMissingDagRun alongside the other 2026-10-30 changes. Signed-off-by: 1fanwang <[email protected]>
pierrejeambrun
left a comment
There was a problem hiding this comment.
Thanks for this, and for addressing the earlier feedback! I tested it against a running API server by deleting the Dag run in the middle of a write: the Execution API now returns 404 for 2026-10-30 clients and keeps 500 for older ones. One note on the description: on current main the public API PUT/PATCH already return 404 for this race (they caught ValueError), so the user-visible fix is in the Execution API, and the public API change narrows which errors map to 404. Could you update the "Before" section? A couple of small things inline.
… API On main the Execution API route never caught ValueError, so the test there passed without this change. The public API used to turn any ValueError into a 404.
pierrejeambrun
left a comment
There was a problem hiding this comment.
I just pushed a small adjustment commit to address those.
Backport successfully created: v3-4-testNote: As of Merging PRs targeted for Airflow 3.X In matter of doubt please ask in #release-management Slack channel.
|
apache#72907) * Return 404 instead of 500 when DagRun is missing in Execution API In task_instances.py validate_inlets_and_outlets and task_state_store.py set_task_state_store, missing DagRun instances triggered unhandled AttributeError and ValueError exceptions that surfaced as HTTP 500 Internal Server Errors. Catch the missing DagRun condition and return a clean 404 Not Found response matching the pattern established in PR 72890. Signed-off-by: 1fanwang <[email protected]> * Distinguish missing runs from other state backend errors Unrelated backend ValueErrors must not be reported as missing runs. Exercise writes racing actual run deletion instead of manufacturing impossible ORM results. Signed-off-by: 1fanwang <[email protected]> * Return 404 on task-state writes after a DagRun is deleted mid-request Signed-off-by: Stefan Wang <[email protected]> * Fix task state store 404 regression coverage The conflict merge kept the dedicated DagRunNotFound exception but retained an upstream test that raised ValueError, so current-head CI failed before exercising the route contract. Signed-off-by: Stefan Wang <[email protected]> * Test the narrowed ValueError handling where it changed, in the public API On main the Execution API route never caught ValueError, so the test there passed without this change. The public API used to turn any ValueError into a 404. --------- (cherry picked from commit f90d260) Co-authored-by: Stefan Wang <[email protected]> Signed-off-by: 1fanwang <[email protected]> Signed-off-by: Stefan Wang <[email protected]> Co-authored-by: pierrejeambrun <[email protected]>
apache#72907) * Return 404 instead of 500 when DagRun is missing in Execution API In task_instances.py validate_inlets_and_outlets and task_state_store.py set_task_state_store, missing DagRun instances triggered unhandled AttributeError and ValueError exceptions that surfaced as HTTP 500 Internal Server Errors. Catch the missing DagRun condition and return a clean 404 Not Found response matching the pattern established in PR 72890. Signed-off-by: 1fanwang <[email protected]> * Distinguish missing runs from other state backend errors Unrelated backend ValueErrors must not be reported as missing runs. Exercise writes racing actual run deletion instead of manufacturing impossible ORM results. Signed-off-by: 1fanwang <[email protected]> * Return 404 on task-state writes after a DagRun is deleted mid-request Signed-off-by: Stefan Wang <[email protected]> * Fix task state store 404 regression coverage The conflict merge kept the dedicated DagRunNotFound exception but retained an upstream test that raised ValueError, so current-head CI failed before exercising the route contract. Signed-off-by: Stefan Wang <[email protected]> * Test the narrowed ValueError handling where it changed, in the public API On main the Execution API route never caught ValueError, so the test there passed without this change. The public API used to turn any ValueError into a 404. --------- (cherry picked from commit f90d260) Co-authored-by: Stefan Wang <[email protected]> Signed-off-by: 1fanwang <[email protected]> Signed-off-by: Stefan Wang <[email protected]> Co-authored-by: pierrejeambrun <[email protected]>
#72907) (#76599) * Return 404 instead of 500 when DagRun is missing in Execution API In task_instances.py validate_inlets_and_outlets and task_state_store.py set_task_state_store, missing DagRun instances triggered unhandled AttributeError and ValueError exceptions that surfaced as HTTP 500 Internal Server Errors. Catch the missing DagRun condition and return a clean 404 Not Found response matching the pattern established in PR 72890. * Distinguish missing runs from other state backend errors Unrelated backend ValueErrors must not be reported as missing runs. Exercise writes racing actual run deletion instead of manufacturing impossible ORM results. * Return 404 on task-state writes after a DagRun is deleted mid-request * Fix task state store 404 regression coverage The conflict merge kept the dedicated DagRunNotFound exception but retained an upstream test that raised ValueError, so current-head CI failed before exercising the route contract. * Test the narrowed ValueError handling where it changed, in the public API On main the Execution API route never caught ValueError, so the test there passed without this change. The public API used to turn any ValueError into a 404. --------- (cherry picked from commit f90d260) Signed-off-by: 1fanwang <[email protected]> Signed-off-by: Stefan Wang <[email protected]> Co-authored-by: Stefan Wang <[email protected]> Co-authored-by: pierrejeambrun <[email protected]>
#72907) (#76599) * Return 404 instead of 500 when DagRun is missing in Execution API In task_instances.py validate_inlets_and_outlets and task_state_store.py set_task_state_store, missing DagRun instances triggered unhandled AttributeError and ValueError exceptions that surfaced as HTTP 500 Internal Server Errors. Catch the missing DagRun condition and return a clean 404 Not Found response matching the pattern established in PR 72890. * Distinguish missing runs from other state backend errors Unrelated backend ValueErrors must not be reported as missing runs. Exercise writes racing actual run deletion instead of manufacturing impossible ORM results. * Return 404 on task-state writes after a DagRun is deleted mid-request * Fix task state store 404 regression coverage The conflict merge kept the dedicated DagRunNotFound exception but retained an upstream test that raised ValueError, so current-head CI failed before exercising the route contract. * Test the narrowed ValueError handling where it changed, in the public API On main the Execution API route never caught ValueError, so the test there passed without this change. The public API used to turn any ValueError into a 404. --------- (cherry picked from commit f90d260) Signed-off-by: 1fanwang <[email protected]> Signed-off-by: Stefan Wang <[email protected]> Co-authored-by: Stefan Wang <[email protected]> Co-authored-by: pierrejeambrun <[email protected]>
A task-state write can race with DagRun deletion. The backend then finds no DagRun, and the affected API request returned HTTP 500 even though the target no longer existed. The public and execution APIs now return their versioned 404 responses for that race. Unrelated backend failures still return HTTP 500.
The backend now marks a missing run explicitly. Each API turns that signal into its existing 404 response format.
related: #72890
Testing Done
The reproducer sends real HTTP requests through each FastAPI surface, writes rows to SQLite, deletes the DagRun immediately before the backend lookup, confirms the foreign-key cascade, and repeats the write.
Before:
After:
Reproducer source: dev/repro_airflow_72907.py and test_state_store_http_probe_72907.py
Was generative AI tooling used to co-author this PR?
Generated-by: GitHub Copilot CLI (GPT-6 Astra) following the guidelines