Files
platform/order/order.go
T
2026-06-28 17:52:49 +02:00

54 lines
2.3 KiB
Go

// Package order is the platform's shared order seam: the exported wire shape of
// the `order.created` domain event (B4.1). It is the contract between the order
// service (producer) and every reactor — inventory commit, fulfillment
// allocation, loyalty, ERP sync — none of which the order service knows about.
//
// Like platform/catalog and platform/inventory, it holds only the wire value
// types + encode/decode, and imports only the stdlib.
//
// `order.created` is a FACT, not a request: by the time it is emitted the order
// is placed and paid. Reactors must be idempotent (the transport is
// at-least-once) and must not assume they can refuse it — the sale already
// happened. Oversell on commit is reconciled downstream (backorder), not
// prevented here.
package order
import "encoding/json"
// Line is one ordered line item, reduced to what reactors need: the SKU, how
// many units sold, and the inventory location to commit against. Pricing/tax
// live in the order grain, not on this seam.
type Line struct {
SKU string `json:"sku"`
Quantity int `json:"quantity"`
// Location is the inventory location / store id to decrement. Empty means
// "use the order's Country" (central stock) — see Created.Country.
Location string `json:"location,omitempty"`
}
// Created is the payload of an event.OrderCreated envelope.
//
// Country is the default inventory location for the commit (central stock). A
// Line may override it with its own Location (store id); when a line's Location
// is empty the commit falls back to Country. See docs/inventory-shape.md.
type Created struct {
OrderID string `json:"order_id"`
OrderReference string `json:"order_reference,omitempty"`
CartID string `json:"cart_id,omitempty"`
Country string `json:"country"`
Currency string `json:"currency,omitempty"`
CustomerEmail string `json:"customer_email,omitempty"`
Lines []Line `json:"lines"`
PlacedAtMs int64 `json:"placed_at_ms,omitempty"`
}
// Encode serialises the payload for event.Event.Payload.
func (c Created) Encode() ([]byte, error) { return json.Marshal(c) }
// Decode parses an order.created payload — the consumer side of Encode.
func Decode(raw []byte) (Created, error) {
var c Created
err := json.Unmarshal(raw, &c)
return c, err
}