SA Pro Lab 01 — Fan out events with SNS and filter with SQS
Scaffold: 4/5 (almost complete). The topic, the two queues, the dead-letter queue, and the subscriptions are all built. You write the one thing that decides where events go: the filter policy.
The scenario
An order service publishes an event for every order. Two teams want those events. The fulfilment team wants every order. The fraud team only wants the big ones, the orders worth 1000 or more, and they do not want to pay to receive and discard the rest.
The tempting answer is one queue and a filter in the consumer. That makes both teams pay for every message and couples them to each other’s throughput. The decoupled answer is one topic, two queues, and a filter policy on the subscription that matters, so SNS drops the events the fraud team does not want before they ever reach the queue.
The requirement
Publish four orders worth 300, 1500, 750, and 2000. All four should land in the catch-all queue. Only the two worth 1000 or more should land in the high-value queue.
What’s provided
template.yaml— an SNS topic, a catch-all SQS queue, a high-value SQS queue, a shared dead-letter queue, the queue policy that lets SNS deliver, and both subscriptions. The high-value subscription’sFilterPolicyis a parameter, fed from yourfilter-policy.json.src/filter-policy.json— the gap. It starts as{}, which matches everything, so out of the box the high-value queue behaves exactly like the catch-all one.scripts/— deploy, test, and teardown.solution/filter-policy.json— the reference answer.
Your task
Open src/filter-policy.json and write a policy that matches only orders whose
order_value message attribute is 1000 or more. SNS filter policies match on
message attributes and support numeric comparisons. The shape you want is a map
from attribute name to a list of match rules.
It is one small JSON object. If you want the mechanics first, read the walk-through post linked at the bottom.
Run it
# Defaults: stack sa-pro-lab-01, region ap-southeast-2.
./scripts/deploy.sh # deploys with your filter-policy.json
./scripts/test.sh # publishes four orders and counts each queue
./scripts/teardown.sh # deletes everything
With the starter {} policy, test.sh reports the high-value queue holding all
four orders: the fan-out works, but nothing is filtered. Fix the policy, redeploy,
and run the test again.
What success looks like
./scripts/test.sh prints:
Standard (catch-all) queue: 4 (expected 4)
High-value queue: 2 (expected 2)
PASS: fan-out delivered every order, and the filter kept only the high-value ones.
Reveal the solution
Deploy the reference filter policy without editing anything:
SRC=solution ./scripts/deploy.sh && ./scripts/test.sh
What you just learned
- Fan-out is one publisher, many independent subscribers. Each queue is decoupled from the others and from the publisher’s rate; a slow consumer on one queue cannot back up the other.
- A subscription filter policy moves the routing decision to SNS, before delivery. The fraud team never receives, pays for, or has to discard the small orders.
- Filter policies match on message attributes (or, with a scope change, the body), and support numeric, prefix, and anything-but rules.
- A dead-letter queue on the subscription catches messages a consumer repeatedly fails to process, so a poison message does not block the queue forever.
Next
The rest of the SA Pro lab track is listed in labs/README-sa-pro.md.