FM_001 · Duplicate execution caused by retry after timeout
FM_001 — Duplicate execution caused by retry after timeout
Context
Systems with at-least-once delivery can legitimately retry work after a timeout. If commit semantics are not idempotent at the logical job boundary, retries can amplify side effects.
Hidden assumption
"If a worker times out, its attempt did not commit any irreversible effect."
Violated invariant
INV_001— Job execution is logically idempotent.
Description
When the first worker exceeds lease timeout, the queue re-leases the same job to another worker. Without an idempotent commit boundary, both workers can apply the logical effect.
Trigger
- Worker A leases job
J. - Worker A starts work and lease expires.
- Worker B leases the same job
Jas retry. - Both workers finish and apply effects.
Failure mechanism
- Worker A leases
job Jand starts processing. - Lease expires before A reaches terminal completion.
- Queue re-leases
job Jto Worker B (at-least-once behavior). - Both attempts cross effect application without a durable single-commit boundary.
- Logical effect is applied twice.
Symptoms
- duplicate side effects for the same
job_id - two successful executions for one logical job
Violated invariants
INV_001(logical idempotency)INV_002(partial execution crash consistency risk)INV_004(recovery must restore correctness after crash)
Detection
- count of side effects by
job_id> 1 - more than one execution reaching terminal success semantics for the same job
Recovery / prevention strategy
- enforce a durable
COMMITTEDboundary perjob_id - only first commit is accepted
- duplicate attempts must no-op safely
Expected impact
- correctness loss due to duplicated irreversible effects
- downstream reconciliation burden
- hidden financial/state integrity risk in retry-heavy paths
Acceptance criteria
test_repro_fm001.pyproves duplicate effects in baseline modetest_prevent_fm001.pyproves exactly one effect after commit boundarytest_recover_fm001.pyproves crash-after-commit reconciles to correct terminal state without duplicate effectstest_fm001_happy_path.pyproves invariant-preserving baseline flow