Repository navigation
DiLoCo #218: requeue worker on transient backend-derivation timeout + modal Reset-to-defaults - #236
Merged
Merged
Conversation
…ntly unreachable (#218) The scheduler derives a worker's sync backend by GETting the param server's /info at launch. That ran as a single attempt with a 15s timeout and no retry, so a worker dispatched in the brief window where the server is still finishing startup (or momentarily busy as 4 workers make first contact at once) was permanently FAILED by one timed-out probe — even though the server was healthy seconds later. Observed live: all 4 workers of a smoke run failed with 'backend could not be derived ... unreachable (timed out)'; re-submitting against the warm server worked. The probe runs inside the serial dispatch tick, so a blocking sleep-retry would stall every other dispatch. Instead: - shorten the per-attempt timeout to 5s (_DILOCO_DERIVE_TIMEOUT_S) so one probe can't hold up the tick, and - raise a typed _DilocoServerUnreachable; _launch catches it and REQUEUES the worker (drop the record — freeing the reserved GPU — and re-add the item with its original submitted_at, so FIFO position is kept) for the next tick. It fails for real only after _DILOCO_DERIVE_RETRY_BUDGET_S (180s) of retries, covering a slow server startup without hanging forever on a server that never comes up. A permanent config error (backend/topology mismatch) is a plain RuntimeError and still fails immediately — only the network-unreachable case is retried. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
The other service modals (e.g. DatasetServerModal) have it; the DiLoCo one didn't, making it hard to definitively clear persisted ad-hoc overrides when starting something different. Create-mode only (edit mode reflects a saved service); clears the persisted blob and restores every field to its default. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…ailure Review follow-up: _diloco_derive_first_seen leaked an entry when a worker in the #218 retry window was cancelled (cancel_queued) or later failed via a non- unreachable error. Prune it in both paths. (+ regression test) Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Fixes issue #218 (the launch-time backend-derivation race that failed all 4 workers of a smoke run), plus a small DiLoCo-server-modal usability add.
#218 — requeue instead of fail on transient unreachability (
scheduler.py)The scheduler derives a worker's sync backend by GETting the param server's
/infoat launch — a single attempt, 15 s timeout, no retry. A worker dispatched in the brief window where the server is still finishing startup (or momentarily busy as 4 workers make first contact at once) was permanently failed by that one timed-out probe, even though the server was healthy seconds later. (Observed live; re-submitting against the warm server worked.)The probe runs inside the serial dispatch tick, so a blocking sleep-retry would stall every other dispatch. Instead:
_DILOCO_DERIVE_TIMEOUT_S) so one probe can't hold up the tick;_diloco_query_inforaises a typed_DilocoServerUnreachable;_launchcatches it and requeues the worker — drops the record (freeing the reserved GPU) and re-adds the item with its originalsubmitted_at(FIFO position kept) — for the next tick. It fails for real only after_DILOCO_DERIVE_RETRY_BUDGET_S(180 s), covering a slow server startup without hanging forever on a server that never comes up.A permanent config error (backend/topology mismatch) stays a plain
RuntimeErrorand still fails immediately — only the network-unreachable case is retried.webui — "Reset to defaults" on the DiLoCo server modal
The other service modals have it; the DiLoCo one didn't, making it hard to definitively clear persisted ad-hoc overrides. Create-mode only.
Tests
test_scheduler_diloco_retry.py: typed-exception raise, requeue-within-budget, fail-after-budget, success-clears-bookkeeping. Scheduler + diloco-env suites green;black/isortclean; webuitsc --noEmitclean.Docs
docs/trainers/diloco-backends.md— the "fails loud if unreachable" line now describes the requeue/retry.🤖 Generated with Claude Code