2.2 KiB
2.2 KiB
Architect — F-022 Checkout orchestrator with idempotency
Feature
F-022 orchestrates the money path: cart -> validation -> pricing -> stock -> discounts -> shipping -> order -> reservation -> payment intent. It owns no business data and exposes a single endpoint with idempotency.
Design
Module boundaries
Create project/src/modules/checkout/ with domain/application/api/tests. Checkout does not own persistence; it composes cart, pricing, promotions, inventory, shipping, orders and a payment provider interface stub.
Endpoint
POST /checkoutrequires authenticated user, payload{ items, address, promoCode?, idempotencyKey }(recalculated internally). Server fetches cart viaCartService, recalculates through Pricing/Promotions/Inventory/Shipping, validates everything, createsAWAITING_PAYMENTorder, reserves stock, creates payment intent.
Idempotency
idempotency_keyis required on the request body.- The orders table already has
idempotency_key UNIQUE. When an order already exists for(userId, idempotencyKey)the orchestrator returns the existing order without re-reserving stock or re-creating payment intent. - Double-submit returns the same order id with no duplicate stock reservation.
Flow and failure handling
- Load cart. Reject 409 if cart empty or any item unavailable after recalculation.
- Apply promo discount server-side; reject 422 on invalid promo.
- Calculate shipping with default address if missing; reject 422 outside zones.
- Create
AWAITING_PAYMENTorder with snapshots. - Reserve inventory atomically. If any reservation fails: cancel the order (state machine), release any partial reservations, return HTTP 409 with reason.
- Create payment intent (interface stub for v1) and link to order.
- Return 200 with order summary, stock reserved, payment intent reference.
Metrics
checkout_success_totalcountercheckout_failure_totalcounter
Acceptance trace
- Unavailable item -> 409, no order, no payment, no reservation.
- Idempotent key reuse -> same order, no duplicate reservation, no duplicate payment.
- Successful checkout -> order AWAITING_PAYMENT + stock reserved.
- Failure after reservation -> reservation released, order cancelled.