Basic Architecture of Sport Web

This commit is contained in:
Nông Đức Huy
2026-08-11 13:37:25 +07:00
commit 8032fff6ac
262 changed files with 20348 additions and 0 deletions
@@ -0,0 +1,29 @@
# ADR-0011: Money as integer minor units
- **Status:** Accepted
- **Date:** 2026-08-11
## Context
`0.1 + 0.2 !== 0.3`. Floating-point money produces discrepancies that are invisible in
testing and unfixable once they are in an order history.
## Decision
All monetary values are integers in the currency's minor unit, in the database
(`priceAmount Int`), across the API (`{ amount, currency }`), and in TypeScript (`Money`).
VND has a minor-unit scale of 0, so `250000` means ₫250.000. Conversion to a display string
happens in exactly one function, `formatMoney`, using `Intl.NumberFormat`.
## Consequences
Arithmetic is exact. No conversion happens between layers because every layer holds
the same integer. Multi-currency is already representable without a schema change.
Developers must remember that `price.amount` is not a display value; the single formatter and
the absence of any other division by 100 are what keep that from going wrong.
## Alternatives considered
`Decimal`/`numeric` columns — correct in the database but arrive in JavaScript as
strings or a Decimal object that must be handled at every boundary. Floats — never.