Skip to content

ADR-002: Integer Arithmetic with Millitokens

Status: Accepted Date: 2026-01-09 Commit: 3902c8c Milestone: v0.1.0

Context

Token bucket algorithms require tracking fractional tokens during refill calculations. In distributed systems, floating-point arithmetic can cause precision issues:

  • IEEE 754 floating-point has representation errors (0.1 + 0.2 ≠ 0.3)
  • Different clients/languages may have slightly different FP implementations
  • Accumulated rounding errors cause bucket drift over time
  • DynamoDB stores numbers as strings, adding serialization concerns

Decision

Store all token values as millitokens (×1000) using integer arithmetic.

Implementation: - Internal storage: tokens_milli (integer) - User-facing API: tokens (float, converted at boundary) - Refill stored as fraction: refill_amount / refill_period_seconds - All bucket math uses integer operations

Consequences

Positive: - Exact arithmetic: no precision loss across any number of operations - Deterministic: same calculation yields identical results everywhere - Simple debugging: values are exact integers - DynamoDB-friendly: integers serialize cleanly

Negative: - API boundary conversion required (minor complexity) - Sub-millitoken precision not supported (acceptable for rate limiting) - Developers must remember internal representation when debugging

Alternatives Considered

  • Decimal type: Rejected; Python's Decimal doesn't map cleanly to DynamoDB Number type
  • Floating-point with rounding: Rejected; accumulated errors in long-running buckets
  • Fixed-point with higher precision (microtokens): Rejected; millitokens sufficient for rate limiting use cases