Transactional REST API for carts, orders, payments, and ACP checkout sessions.
The CRUD service is a non-agent FastAPI microservice that owns transactional state and exposes seller-side APIs for checkout and order fulfillment. It routes agent calls through Azure API Management (APIM) with circuit breaker and retry for resilient integration.
- Cart management and item pricing snapshots
- Order creation and state tracking
- Payment processing integration (Stripe placeholder)
- ACP checkout session lifecycle endpoints
- Delegated payment token validation (ACP demo PSP)
- APIM-routed agent invocation (12 agent methods with circuit breaker + retry)
- JWKS-based JWT authentication with Entra ID
- Brand-shopping contract surface for UI personalization orchestration
- Bounded route composition groups (
platform,commerce,staff,truth) with unchanged endpoint contracts
POST /acp/checkout/sessions- Create checkout sessionGET /acp/checkout/sessions/{id}- Retrieve sessionPATCH /acp/checkout/sessions/{id}- Update items, address, or fulfillmentPOST /acp/checkout/sessions/{id}/complete- Complete with delegated tokenDELETE /acp/checkout/sessions/{id}- Cancel session
POST /acp/payments/delegate- Create delegated payment token with allowance
GET /api/catalog/products/{sku}- Canonical product contract for personalization contextGET /api/customers/{customer_id}/profile- Customer + CRM/personalization profile contract (owner orstaff|admin)POST /api/pricing/offers- Deterministic offer computation contractPOST /api/recommendations/rank- Ranked recommendation scoring contractPOST /api/recommendations/compose- Final recommendation composition contract
GET /api/inventory/{sku}- Retrieve inventory snapshotPATCH /api/inventory/{sku}- Update quantity fields (quantity_on_hand,reserved_quantity) (staff|admin)PATCH /api/inventory/{sku}/thresholds- Update reorder/safety thresholds (staff|admin)GET /api/inventory/health- Inventory health summary (healthy/low_stock/out_of_stock)POST /api/inventory/reservations- Create reservation hold (created)GET /api/inventory/reservations/{reservation_id}- Retrieve reservation (owner orstaff|admin)POST /api/inventory/reservations/{reservation_id}/confirm- Confirm hold (owner orstaff|admin, idempotent when already confirmed)POST /api/inventory/reservations/{reservation_id}/release- Release hold and decrement reserved quantity (owner orstaff|admin, idempotent when already released)
- Allowed transitions:
created -> confirmed,created -> released - Terminal states:
confirmed,released - Invalid transitions return
409 Conflict
- UI creates holds before order/payment setup.
- UI confirms holds only after successful
POST /api/payments/confirm-intent. - UI issues compensating release when setup fails or checkout is abandoned before payment confirmation.
- CRUD: contract ownership, validation, schema stability.
- UI: flow orchestration (product/profile → offers → rank → compose).
- Current brand-shopping contracts are treated as
v1under/api. - Additive response fields are allowed without path changes.
- Breaking request/response or route changes require a new parallel versioned path (for example
/api/v2/...) before deprecatingv1.
- States:
requested,approved,rejected,received,restocked,refunded - Allowed transitions:
requested->approved|rejected,approved->received,received->restocked,restocked->refunded - Terminal states:
rejected,refunded - Invalid transitions return
409 Conflict - Repeating the current target state returns
200withidempotent=true
POST /api/returnscreates a return inrequested(201)GET /api/returnslists customer-owned returnsGET /api/returns/{return_id}returns canonical lifecycle timelineGET /api/returns/{return_id}/refundreturns refund progression (issued) or404when refund record does not exist
GET /api/staff/returns/,GET /api/staff/returns/{return_id}POST /api/staff/returns/{return_id}/approvePATCH /api/staff/returns/{return_id}/approve(legacy compatibility)POST /api/staff/returns/{return_id}/rejectPOST /api/staff/returns/{return_id}/receivePOST /api/staff/returns/{return_id}/restockPOST /api/staff/returns/{return_id}/refundGET /api/staff/returns/{return_id}/refund
Staff returns routes accept staff|admin roles.
- Lifecycle topic:
return-eventsReturnRequested,ReturnApproved,ReturnRejected,ReturnReceived,ReturnRestocked,ReturnRefunded
- Refund topic:
payment-eventsRefundIssued
Event payload data includes: return_id, order_id, user_id, status, occurred_at, actor_id, actor_roles, sla, timestamp.
The sla object carries lifecycle timestamps (requested_at, approved_at, rejected_at, received_at, restocked_at, refunded_at, last_transition_at).
- PostgreSQL (asyncpg): JSONB tables —
cart,orders,checkout_sessions,payment_tokens,users,products,reviews,tickets,shipments,audit_logs - Connection pooling via shared
asyncpg.Pool(class-level singleton) - GIN + B-tree indexes on all JSONB tables
- Provisioned via Azure PostgreSQL Flexible Server
- 12 agent methods routed through APIM gateway (
APIM_BASE_URL) circuitbreaker(failure_threshold=5, recovery_timeout=60s)tenacityretry with exponential backoff (3 attempts)- Graceful degradation: returns
Noneif agent unavailable
- Connector registry bootstrap is activated only when connector domains are configured.
- Connector package capabilities are treated as optional install extras for dependency boundary control.
- Publishes
OrderCreatedandPaymentProcessedvia Event Hubs
- Checkout sessions follow ACP lifecycle semantics (create, update, complete, cancel).
- Delegate payment is modeled as a demo PSP for local ACP flows.