EventBridge fanout
AI-generated content
This document was generated by an AI assistant. Verify accuracy before relying on the details.
Async events between ADB services flow through MongoDB Atlas → AWS EventBridge → SQS. Atlas Triggers watch each domain MongoDB collection's change stream; on every INSERT / UPDATE / REPLACE / DELETE they publish a TargetObjectMessage to a per-collection partner EventBridge bus in AWS account 182790345476 region eu-west-3. Per-environment EventBridge rules (<env>-<consumer>-<event>) then route each event to a per-consumer SQS queue (<env>-<consumer>-<event> with a matching -dlq). There is no SNS fanout — the duplication-per-consumer happens at the EventBridge rule level. Per-service <env>-<service>-dlq SNS topics exist, but only as DLQ-depth alert sinks.
At a glance
| Fact | Value | Source |
|---|---|---|
| Producer | MongoDB Atlas Triggers in app triggers-kkeqz | realm-cli pull |
| Trigger count | 18 (16 → AWS, 2 internal Realm functions) | audit |
| Partner buses | 31 in AWS (some likely orphaned stage-*) | audit |
| Rules | ~80, <env>-<consumer>-<event> | audit |
| SQS queues | 96 = (24 logical × 2 envs) + 48 DLQs | catalog |
| DLQ alert topics | 8 (4 services × 2 envs) | catalog |
| Consumer services | accounting, contracts, files, views | catalog |
| AWS region | eu-west-3 | trigger configs |
Details
The flow
flowchart LR
subgraph "MongoDB Atlas (Azure FRANCE_CENTRAL)"
col[adb-contracts.contracts]
trig[Atlas Trigger<br>contract-modified]
col -->|change stream| trig
end
subgraph "AWS eu-west-3 (account 182790345476)"
bus[Partner Bus<br>aws.partner/mongodb.com/...]
rA[Rule: prod-accounting-contract-modified]
rC[Rule: prod-contracts-contract-modified]
rV[Rule: prod-views-contract-modified]
qA[SQS: prod-accounting-contract-modified]
qC[SQS: prod-contracts-contract-modified]
qV[SQS: prod-views-contract-modified]
bus --> rA --> qA
bus --> rC --> qC
bus --> rV --> qV
end
trig -->|TargetObjectMessage| bus
qA --> accounting[adb-accounting]
qC --> contracts[adb-contracts]
qV --> adb-views[adb-views]
Naming convention
- Trigger —
<event>(e.g.contract-modified). Some have aparts-prefix retained from history (parts-charge-budget-modified→ AWS eventcharge-budget-modified). - Partner bus — auto-named by Atlas (
aws.partner/mongodb.com/stitch.trigger/<id>). One bus per trigger. - Rule —
<env>-<consumer>-<event>(prod-accounting-contract-modified). - Queue — same as rule (
prod-accounting-contract-modified). - DLQ —
<env>-<consumer>-<event>-dlqwithredrivePolicy.maxReceiveCount=5. - DLQ alert SNS topic —
<env>-<consumer>-dlq(one per consumer service per env).
What's in TargetObjectMessage
Every trigger applies a project transformation that wraps the change-stream document into:
{
"domainObject": {
"self": "http://adb-contracts/contracts/<id>",
"targetId": "<documentKey._id>",
"type": "TargetObject"
},
"event": "CREATED",
"operationType": <int>,
"requestContextData": {
"agencyTimeZone": "Europe/Paris",
"locale": "fr_FR",
"organizationId": "<fullDocument.organisationId>",
...
}
}
The static event: "CREATED" and operationType: 1 look like a bug or simplification in the trigger config — the actual operation type comes from the change stream but isn't propagated. Worth investigating; tracked in Open questions below.
Adding a new event
Single source of truth is infra/src/catalog/services.js. To add a new consumer subscription:
- Append the event name to the consumer's
consumes:list. - If it's a new event type, also add it to the top-level
EVENTSarray withdb,collection,ops. - Run
npm run syntaxininfra/to confirm the catalog still parses. - Run
pulumi previewon the env stack to see the new SQS queue + IAM grants. - Add a new Atlas Trigger via
realm-cliif the producer side doesn't exist yet.
Open questions
- The
stage-*AWS rules + queues exist but the Atlas org has only one project producing one set of events to one AWS account. Hypothesis: stage Atlas project was deleted, AWS partner buses + rules + queues are orphaned. To confirm: checkApproximateAgeOfOldestMessageon anystage-*queue — flat zero for >30 days = dead. - Why is
event: "CREATED"andoperationType: 1static in every trigger config? Looks unintentional. - Should
aggregates,parts,persons,utilities,reports,uiservices also subscribe (they currently don't)? They consume domain data from siblings but apparently via HTTP, not events.