Initial Commit
This commit is contained in:
@@ -0,0 +1,53 @@
|
||||
# Capability Spec: Datetime
|
||||
|
||||
**Package**: `@suaveplan/datetime`
|
||||
**Version**: 0.0.0 (genesis)
|
||||
**Status**: ADDED
|
||||
|
||||
---
|
||||
|
||||
## ADDED Requirements
|
||||
|
||||
### DT-01 — DateInput acceptance
|
||||
|
||||
Every function that accepts a date parameter MUST accept `DateInput = Date | string | number`. Strings must be ISO-8601; numbers are Unix milliseconds. Invalid inputs throw `DatetimeError` with code `DATETIME.PARSE.INVALID_INPUT`.
|
||||
|
||||
### DT-02 — Injectable clock
|
||||
|
||||
Every function that reads current time (e.g. `timeAgo`, `isBusinessDay` for "today") MUST accept an optional `{ clock?: Clock }` option. The `Clock` interface is sourced from `@suaveplan/types`. Zero-config default uses `Date.now()`. No `Date.now()` or `new Date()` calls at module scope.
|
||||
|
||||
### DT-03 — Business day arithmetic
|
||||
|
||||
`addBusinessDays`, `subtractBusinessDays`, `nextBusinessDay`, `previousBusinessDay`, `isBusinessDay`, `businessDaysBetween` MUST all accept `BusinessDayOptions` including a custom `holidays?: Date[]` list and `weekendDays?: Weekday[]` array (defaults: Saturday and Sunday). `businessDaysBetween` MUST check `AbortSignal` every 256 days to support large ranges.
|
||||
|
||||
### DT-04 — Calendar math correctness
|
||||
|
||||
`addDuration` and `subtractDuration` MUST correctly handle month rollover (e.g. Jan 31 + 1 month = Feb 28/29) and DST transitions without double-counting hours. `daysInMonth` MUST return correct values for all months including February in leap years.
|
||||
|
||||
### DT-05 — Recurrence rules
|
||||
|
||||
`parseRRule` MUST parse a simplified RRULE string supporting `FREQ`, `INTERVAL`, `COUNT`, `UNTIL`, `BYDAY`, `BYMONTHDAY`. `expandRecurrence` MUST require either `count` or `until` in the rule; rules missing both MUST throw `DatetimeError` with code `DATETIME.RECURRENCE.INFINITE_EXPANSION`. `AbortSignal` is checked every 64 occurrences.
|
||||
|
||||
### DT-06 — Structured errors
|
||||
|
||||
All thrown errors MUST extend `DatetimeError` which extends `SuaveplanError`. Error codes are namespaced under `DATETIME.*`. The error includes `{ code, message, cause?, context? }`.
|
||||
|
||||
### DT-07 — Zod schemas
|
||||
|
||||
Every exported public type that carries runtime data MUST have a corresponding Zod schema in a sibling `*.schemas.ts` file. Schemas are exported directly (not via a schema-registry package).
|
||||
|
||||
### DT-08 — i18n-ready output
|
||||
|
||||
`formatRelative`, `timeAgo`, and `timeUntil` MUST produce output via i18n-keyed strings. The default locale is English pass-through. The key system is compatible with a future `@suaveplan/i18n` adapter.
|
||||
|
||||
### DT-09 — OTel instrumentation
|
||||
|
||||
`expandRecurrence` and `businessDaysBetween` MUST emit OpenTelemetry histograms tracking call duration and output size. All instruments are registered via `@opentelemetry/api` and are no-ops when no exporter is registered.
|
||||
|
||||
### DT-10 — sideEffects: false
|
||||
|
||||
The package MUST set `"sideEffects": false` in `package.json`. A tree-shake test MUST verify no side effects leak at import time.
|
||||
|
||||
### DT-11 — Coverage gate
|
||||
|
||||
Vitest thresholds MUST be set to 100/100/100/100 (statement/branch/function/line). No `istanbul ignore` pragmas. No `.skip` or `.only` in `src/`.
|
||||
Reference in New Issue
Block a user