feat(arbiter): event-id dedupe for supervisor and fabricator - #103
Merged
Conversation
…nsumers CIT-125 slice B: at-least-once EventBridge delivery + SQS DLQ redrive safety. Supervisor (EventBridge-fed): single conditional-put claim on event['id'] in the shared citadel-idempotency-<env> table (PK eventId, TTL). Duplicate task.request/task.completion deliveries are a no-op; non-conditional-check DDB errors rethrow so the message redelivers/DLQs. Fabricator (SQS-fed, no EventBridge envelope): two-phase PENDING/DONE claim keyed on the SQS messageId instead of event.id (deviation, documented in module + test docstrings and reply) — the fabricator queue has no EB rule target; both producers (fabricator-request-resolver.ts, agent-import- resolver.ts) SendMessage directly with no id/detail field. messageId gives the same at-least-once/redrive-stability guarantee the design relies on. A redelivery seen while PENDING routes to reconcile instead of re-fabricating; a redelivery of a DONE message is a no-op. Both reuse the existing table by name (Table.fromTableName in arbiter-stack.ts) with RW grants + IDEMPOTENCY_TABLE env — no new table, no new CFN edge, no split-gates-gated resource touched (arbiter isn't synthesized by split-gates). Red-first tests: 18 new pytest cases (9 supervisor, 9 fabricator) + 4 CDK wiring tests (table-count-unchanged, both envs, both RW grants).
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
The DLQ audit classified the supervisor and fabricator consumers as redrive-unsafe: EventBridge delivers at-least-once, and a duplicate (or a DLQ redrive) re-ran orchestration and re-fabricated agents - the fabricator's duplicate-fabrication history is documented. This PR makes both consumers idempotent so the new shared DLQs can actually be redriven.
event.idin the existing 'citadel-idempotency-‹env› table (referenced by name, no new table); duplicatetask.request/task.completionevents become no-ops; claim rows carry a 7-day TTLmessageId- its queue has no EventBridge envelope (both producers call SendMessage directly), somessageldis the stable identity across redeliveries and redrivesIDEMPOTENCY_TABLEenv + read/write grants on the shared table; zero new DynamoDB tables synthesizedTesting
Notes