# Epic 003 scope and invariants

## Product model

Each product has `name`, gross customer-facing `grossPrice` including VAT, and `vatPercent`. An
optional operator-controlled `kitchenLabel` supplies glanceable kitchen shorthand; the product name
is the fallback. Automatic abbreviation is not required.

Finalized item snapshots preserve product identity, name, kitchen label, gross unit price, and VAT
percentage. Later product edits or deletion never rewrite them.

## Global order invariants

1. Every order has an immutable internal system identity; queue number is never that identity.
2. Queue number is optional, may be duplicated, and preserves formatting such as `01`.
3. Notes are optional and most orders are expected to have none.
4. Queue number and note remain editable after finalization; changes are timestamped.
5. Finalized order items are immutable.
6. Commercial and non-commercial orders share order and fulfillment behavior where practical.
7. Their primary semantic difference is checkout invocation and commercial-sales contribution.
8. A finalized order is a durable historical record.
9. Fulfillment changes never alter payment/settlement state.
10. Catalog changes never rewrite finalized item snapshots.
11. Significant state changes are append-only historical facts; backward transitions do not erase
    earlier facts. Diagnostic logs are not authoritative history.

## Order construction and finalization

The KDS always presents a current cart, initially empty; there is no explicit start-draft action.
Each product-card tap adds one unit, so repeated taps are the primary fast-add interaction. The cart
shows total item count and gross total. Review before finalization permits correction/removal.

`Pay` opens review/checkout with cart contents, optional queue number and note, eat-here/take-away
metadata, payment method when the provider contract supports it, and final Pay. `Non-commercial`
bypasses external checkout but reuses relevant review/metadata behavior. Successful finalization
queues the order and immediately replaces the current cart with a new empty one.

Commercial checkout uses a provider-neutral boundary capable of success, definitive
failure/cancellation, and unknown/indeterminate outcome plus a stable provider reference when
available. Provider authentication, protocol, credentials, formats, and reconciliation remain in an
adapter. Automated acceptance and local development use the deterministic fake, never a Surfboard
account. Staging uses Surfboard Demo through the provider adapter. Production uses the same adapter
with a separately supplied Live base URL and credentials only after Surfboard certification and
release approval; environment selection is configuration, not application branching.

Repeated operator interaction must not intentionally initiate independent charges for one checkout.
Unknown outcomes remain unresolved and cannot be blindly retried. Failed or unknown checkout does
not create false sales or a successfully paid queued order.

## KDS presentation and fulfillment

The tablet target contains three persistent functional regions: an approximately 10% sales ticker,
45% order entry, and 45% kitchen queue. Percentages express intent, not pixel requirements. Domain
logic must not require all panels to remain on one physical screen forever.

Active orders are oldest-queued first. Approximately the next three show complete slip-equivalent
information without drill-down: optional queue number, all item quantities/labels, optional note,
and visible fulfillment state. Quantity one may be omitted; larger quantities are explicit.

Every later order remains individually represented. Prefer its queue number; otherwise show a short,
possibly truncated item fingerprint. The total active count is always visible. Around 15 orders must
remain useful, but 15 is not a maximum.

States are `Queued`, `Preparing`, `Ready`, and `Delivered`. Direct large-target operations support
fast forward and backward transitions with immediate feedback; an explicit detailed state operation
also exists. Requirements are gesture-independent. Delivery removes the order from the active queue,
not from durable history; no delivered-order browser is included.

## Sales and historical facts

The persistent top ticker uses the configured local calendar day. It prefers per-product counts
using kitchen labels and shows gross commercial total in SEK. A constrained responsive fallback may
show total quantity, but the primary tablet layout shows the product breakdown for the expected
roughly five-product menu.

Successful commercial orders contribute. Non-commercial orders and failed/unknown checkout do not.
Fulfillment changes do not alter sales; reload/process restart does not reset them. Product rename
does not split one product identity into unrelated counters. This is operational in-system data, not
authoritative accounting after future out-of-band refunds or corrections.

Finalized history preserves internal ID, classification, eat-here/take-away, item snapshots,
quantity, optional queue number/note, checkout attempts/result/reference, finalization/queue times,
every fulfillment transition, and every metadata edit with relevant timestamps. Normal current state
plus sufficient append-only facts is expected; full event sourcing is not.

## Included assumptions

- One foodtruck/store and one active KDS.
- SEK and one configured local timezone.
- Tablet-sized KDS minimum; it is not mobile-first.
- Existing Application Zero cookie-session authentication protects product administration and KDS.
- Any authenticated MVP user may perform admin/operator actions because roles do not yet exist.
- No offline-first behavior.

## Explicit exclusions

Authentication implementation; customer/tablet/QR/online ordering; customer Kanban; refunds,
returns, discounts, coupons, invoice/cash/Swish settlement; alternate event pricing or event model;
event product lists; sold-out/inventory; categories, modifiers, variants, images, or line-item
notes; split/partial payments, tips; receipt history, reports, inspector, historical search or
cancellation UI; queue estimates; analytics beyond live counters; ML/NN; multiple stores/stations;
separately configurable Order/Queue/Statistics screens; offline sync; automatic queue-number
assignment or uniqueness enforcement.

Preserving explicitly required facts for those future capabilities does not bring their UI or
workflow into scope.

## Surfboard integration boundary

Surfboard is the selected payment provider and Swedish fiscal cash-register system. Its Carbon,
Electronic Cash Register (ECR), order, receipt, terminal, and webhook contracts remain isolated in
infrastructure adapters; application and domain code depend only on provider-neutral payment and
fiscal capabilities.

Discovery must fetch `https://surfpay.ai/llms.txt` and the linked authoritative developer sources,
then record dated evidence for Demo access, partner/merchant/store/terminal/register prerequisites,
line items and tax-inclusive VAT, order and payment outcomes, cancellation, idempotency,
reconciliation, webhooks, stable references, ECR enablement, shift lifecycle, control-unit and
Skatteverket declaration data, receipts, X/Z reports, and the Demo-to-Live certification path.
Unknowns stay explicit rather than leaking guessed fields into the neutral contracts.

Local development deliberately keeps the existing deterministic fake: it is fast, offline,
credential-free, and can reproduce success, refusal, cancellation, and uncertainty. Staging must
exercise Surfboard Demo with test payment methods and non-production fiscal resources. Production
must use separately managed Live credentials and identifiers. No API key, secret, merchant ID,
terminal ID, register ID, or other environment-specific identifier is committed to source control,
logged, or sent to the browser. Card numbers, CVV, and track data never pass through this system.
