3.6 KiB
3.6 KiB
OpenSpec Change: idempotency-spec-conformance
- Change ID: idempotency-spec-conformance
- Package:
@suaveplan/idempotency - Status: PROPOSED
- Date: 2026-04-26
Summary
Bring @suaveplan/idempotency into spec conformance with openspec/specs/idempotency/spec.md. The implementation already satisfies every MUST clause; this change closes the documentation and parsing gaps so bun scripts/openspec-conformance.ts @suaveplan/idempotency exits 0. No public-API changes.
Current state
@suaveplan/idempotency ships a complete enterprise-grade implementation: structured error hierarchy, eight IDEMPOTENCY.* codes with metadata, eight Zod boundary schemas, injectable Clock, AbortSignal propagation, full OTel meter wiring, MemoryIdempotencyStore / RedisIdempotencyStore / DatabaseIdempotencyStore, MemoryLockProvider / RedisLockProvider, fast-check property tests, and a mitata benchmark suite. The conformance gaps are mechanical:
src/error-codes.tsdeclared the codes inline ({ ... } as const) instead of viadefineCodes("IDEMPOTENCY", [...]), so the conformance script could not parse the registry.- The folded spec used
### REQ-IDMP-NNN — nameheadings, which the parser (^[A-Z][A-Z0-9]*-\d+) silently skips, yielding 0 parsed requirements. - Schemas were exported but never invoked outside
src/schemas/(every consumer composes the underlying Zod object directly), triggering boundary warnings. - 10/10 requirements lacked
**Verified by:**lines. - Five implicit scenarios were exercised only indirectly: clock injection, AbortSignal mid-flight, OTel no-op + per-instrument labels, structural-adapter acceptance, and benchmark presence.
tasks.mdof2026-04-19-enterprise-idempotency/carries theretroactively tickedmarker.
What changes
- Refactor
src/error-codes.tsto declareIDEMPOTENCY_CODESviadefineCodes("IDEMPOTENCY", [...])from@suaveplan/error. Re-export fromsrc/errors/idempotency-error.tsfor backwards compat. No public-API change. - Add
// schema: boundary-onlymarker tosrc/schemas/idempotency.schemas.tsto suppress the (correct) boundary warning — schemas are consumer-facing only. - Rewrite the requirement headings in
openspec/specs/idempotency/spec.mdfromREQ-IDMP-NNN — nametoIDMP-NN — nameso the conformance parser picks them up. Add**Verified by:**lines under every requirement. - Add five
*.spec-conformance.test.tsfiles pinning the implicit scenarios:src/errors/idempotency-error.spec-conformance.test.ts— IDMP-01 (hierarchy + namespace + frozen registry).src/schemas/idempotency.schemas.spec-conformance.test.ts— IDMP-02 (every required schema present and round-trippable).src/guard/idempotency-guard.spec-conformance.test.ts— IDMP-03 (clock-driven timestamps & cleanup) + IDMP-04 (pre-aborted and mid-flight signal).src/metrics/idempotency-metrics.spec-conformance.test.ts— IDMP-05 (no-op without meter, all five instruments, correct outcome / operation / result labels, histogram values).tests/structural-adapters.spec-conformance.test.ts— IDMP-08 (plain-object adapter and lock provider).tests/benchmarks-present.spec-conformance.test.ts— IDMP-07 (suite at canonical path covers all four hot paths).
- Re-run
bun scripts/openspec-conformance.ts @suaveplan/idempotencyand confirm exit 0.
Impact
- Public API unchanged.
- Error-code registry now uses the canonical
defineCodeshelper. - Six new test files (~350 lines combined).
openspec/specs/idempotency/spec.mdgains 10**Verified by:**lines and parseable headings.