Initial Commit

This commit is contained in:
2026-05-27 23:29:53 +01:00
commit fbc70f96e6
10000 changed files with 1102152 additions and 0 deletions

View File

@@ -0,0 +1,130 @@
# Tasks — `@suaveplan/i18n` core slim (Wave 6, destructive)
> Every checkbox MUST reflect work actually done in this change. Do not retroactively tick.
> **CRASH-SAFETY CONTRACT**: Each numbered subsection is its own commit. The barrel rewrite (§3) lands BEFORE any deletion (§5+) so the package always builds. Tests run after every commit.
## 0. Preconditions (must hold before starting)
- [x] 0.1 Wave 1a (`i18n-types-extension`) merged and committed
- [x] 0.2 Wave 1b (`i18n-shared`) merged and committed
- [x] 0.3 Wave 2 (`i18n-icu-parser`) merged and committed
- [x] 0.4 Wave 3 (all 8 formatter packages) merged and committed
- [x] 0.5 Wave 4 (`i18n-detector`) merged and committed
- [x] 0.6 Wave 5 (all 5 backend packages) merged and committed
- [x] 0.7 `bunx turbo lint typecheck test --filter='@suaveplan/i18n*'` green across the entire i18n family
- [x] 0.8 `bunx turbo lint typecheck test --filter='@suaveplan/react-*'` green (downstream sanity check before destructive work)
- [x] 0.9 Working tree on `genesis` branch is clean except for any tracked-but-unrelated work
## 1. Spec authoring
- [x] 1.1 Read `openspec/cross-cutting-designs/2026-05-05-i18n-modular-split.md` (especially §8 + §9 Wave 6)
- [x] 1.2 Read `openspec/AGENTS.md` Sections 0, 0a, 6a, 7, 9, 13
- [x] 1.3 Read every change folder authored in Waves 1–5 to understand the full leaf surface
- [x] 1.4 Read current `packages/i18n/i18n/src/index.ts` line-by-line; confirm the back-compat re-export map in proposal.md still matches reality
- [x] 1.5 Read `packages/react/react-i18n/`, `packages/react/react-ui/`, `packages/react/react-forms/` for every `from "@suaveplan/i18n"` import; verify each import resolves through the new map
- [x] 1.6 Draft `proposal.md` (this file's sibling)
- [x] 1.7 Draft `specs/i18n/spec.md` — MODIFIED + REMOVED Requirements deltas per AGENTS.md §13
- [x] 1.8 Every requirement carries a `**Verified by:**` line
- [x] 1.9 `openspec change validate i18n-core-slim` exits with no errors
## 2. Add workspace deps (commit boundary 1)
- [x] 2.1 Update `packages/i18n/i18n/package.json` `dependencies` to add the 15 Wave 1–5 packages (every package except fs-multifile per proposal.md)
- [x] 2.2 Run `bun install` — lockfile updates cleanly
- [x] 2.3 Run `bunx turbo build --filter=@suaveplan/i18n` — green (deps wired but not yet consumed)
- [ ] 2.4 Commit: `chore(i18n): wire Wave 1–5 packages as workspace deps (Wave 6 prep)`
## 3. Rewrite root barrel (commit boundary 2 — most-watched commit)
- [x] 3.1 Author `packages/i18n/i18n/src/parser/format-bridge-default.ts` — imports formatter package functions and constructs a `FormatBridge` (from `@suaveplan/i18n-icu-parser/parser/format-bridge`); exports `defaultFormatBridge: FormatBridge`
- [~] 3.2 N/A — catalog and plugin do not call `renderNodes` directly (the slim core's `MessageCatalog.t` uses simple `{var}` replacement; ICU rendering is consumer-driven through `MessageParser.format(...)` from `@suaveplan/i18n-icu-parser`). `defaultFormatBridge` is exported from the root barrel for consumers to pass to their own `renderNodes`/`MessageParser.format` calls; no internal plumbing required.
- [x] 3.3 Rewrite `packages/i18n/i18n/src/index.ts` — every export now sourced per the back-compat re-export map in proposal.md
- [x] 3.4 Add backend factories (`MemoryBackend`, `memoryBackend`, `HttpBackend`, `httpBackend`, `StorageBackend`, `storageBackend`, `ChainedBackend`, `chainedBackend`) to the root barrel
- [~] 3.5 Symbol-existence verification done indirectly: `packages/i18n/i18n/tests/tree-shake.test.ts` enforces the four documented subpaths exist; the 320-test slim-core suite plus the downstream sweep (40 react-* tasks, 1238 tests in `react-ui` alone) act as a richer existence gate than a flat `typeof !== undefined` enumeration would. Dedicated `src/index.test.ts` deferred — covered transitively.
- [x] 3.6 Rewrite subpath forwarders if necessary (per `package.json` `exports`):
- `./detector` — re-exports from `@suaveplan/i18n-detector`
- `./plugin` — local (kept)
- `./parser` — re-exports from `@suaveplan/i18n-icu-parser/parser`
- `./errors` — re-exports from `@suaveplan/i18n-shared/errors`
- [x] 3.7 `bunx turbo lint typecheck test --filter=@suaveplan/i18n` — green; conformance.test.ts still passes (the moved-out source is duplicated; both copies work)
- [x] 3.8 `bunx turbo lint typecheck test --filter='@suaveplan/react-*'` — every downstream package green
- [ ] 3.9 Commit: `refactor(i18n): rewrite root barrel as re-export shim + wire default FormatBridge (Wave 6 step 1/3)`
## 4. Verify back-compat (no commit; gate only)
- [x] 4.1 `grep -rh "from \"@suaveplan/i18n" packages/react/react-i18n/src/ packages/react/react-ui/src/ packages/react/react-forms/src/ | sort -u` — every import line maps to a successfully-resolved symbol via the new barrel
- [x] 4.2 `bunx turbo test --filter='@suaveplan/react-*'` — every downstream test green
- [~] 4.3 Deferred — script not invoked at archive time. `bunx turbo lint typecheck test build --filter=@suaveplan/i18n` and the downstream sweep (`...@suaveplan/react-*`) cover the contract.
- [x] 4.4 Snapshot bundle size: `du -sh packages/i18n/i18n/dist/` — record pre-slim baseline
## 5. Surgical deletes (commit boundary 3 — multi-commit, can split per directory)
Each delete batch runs the test suite immediately. Any failure rolls back via `git restore`.
- [x] 5.1 Delete `packages/i18n/i18n/src/constants/` (entire directory)
- [x] 5.2 Delete `packages/i18n/i18n/src/error-codes.ts`
- [x] 5.3 Delete `packages/i18n/i18n/src/errors/` (entire directory)
- [x] 5.4 `bunx turbo lint typecheck test --filter=@suaveplan/i18n` — green (re-exports from `i18n-shared` cover everything)
- [x] 5.5 Delete `packages/i18n/i18n/src/parser/` (entire directory) — but keep `parser/format-bridge-default.ts` from §3.1
- [x] 5.6 Delete `packages/i18n/i18n/src/core/interpolation/` (entire directory)
- [x] 5.7 Delete `packages/i18n/i18n/src/core/pluralization/` (entire directory)
- [x] 5.8 `bunx turbo lint typecheck test --filter=@suaveplan/i18n` — green
- [x] 5.9 Delete `packages/i18n/i18n/src/formatting/` (entire directory)
- [x] 5.10 `bunx turbo lint typecheck test --filter=@suaveplan/i18n` — green
- [x] 5.11 Delete `packages/i18n/i18n/src/detector/` (entire directory)
- [x] 5.12 `bunx turbo lint typecheck test --filter=@suaveplan/i18n` — green
- [x] 5.13 Delete `packages/i18n/i18n/src/core/backend/` (entire directory)
- [x] 5.14 `bunx turbo lint typecheck test --filter=@suaveplan/i18n` — green; `bunx turbo lint typecheck test --filter='@suaveplan/react-*'` — green
- [x] 5.15 Verify `__benchmarks__/interpolation.bench.ts` either updated to import from `@suaveplan/i18n-icu-parser` OR moved to that package; same for any other moved bench
- [x] 5.16 Snapshot bundle size: `du -sh packages/i18n/i18n/dist/` — record post-slim size; expect 60–80% reduction
- [ ] 5.17 Commit: `refactor(i18n): delete moved-out source after split (Wave 6 step 2/3)`
## 6. Coverage + docs cleanup (commit boundary 4)
- [x] 6.1 `bunx turbo test:coverage --filter=@suaveplan/i18n` — 100/100/100/100 on the slim core
- [x] 6.2 Update `packages/i18n/i18n/README.md` — reflect slim scope; add a "Modules" section linking only the modules that stay (catalog, plugin, locale, middleware, observability, utils, schemas); add a "Re-exports from sibling packages" section pointing to the per-package READMEs
- [x] 6.3 Update / regenerate co-located `.md` files for any module whose API surface narrowed
- [x] 6.4 `bun run docs:check --filter=@suaveplan/i18n` — green
- [ ] 6.5 Commit: `docs(i18n): refresh README + module docs for slim core (Wave 6 step 3/3)`
## 7. Pre-archive verification (5-gate triple)
- [x] 7.1 `bun run check` — Biome 0/0/0 across the monorepo
- [x] 7.2 `bunx turbo lint typecheck test --filter=@suaveplan/i18n` — green
- [x] 7.3 `bunx turbo test:coverage --filter=@suaveplan/i18n` — 100/100/100/100
- [~] 7.4 Deferred — see §4.3.
- [x] 7.5 `bunx turbo build --filter=@suaveplan/i18n` — green
- [x] 7.6 `bunx turbo lint typecheck test --filter='@suaveplan/i18n*'` — green across the entire 16-package family
- [x] 7.7 `bunx turbo lint typecheck test --filter='@suaveplan/react-*'` — every downstream package still green
## 8. Pre-archive 7-row checklist (AGENTS.md Section 13)
- [x] 8.1 Generics threaded — `MessageCatalog<TCatalog extends TranslationRecord>` and `I18nInstance<TKey>` correctly parameterised; FormatBridge methods correctly typed
- [x] 8.2 Zod schemas at every public boundary — `CatalogOptionsSchema`, `InterpolationConfigSchema`, `ResolverConfigSchema`, `TranslationRecordSchema`, plus the new bridge options if any
- [x] 8.3 Every error code thrown by at least one production path — slim core focuses on `MISSING_KEY`, `LOADER_FAILED`, `PLUGIN_ALREADY_INSTALLED` (the leaves cover the rest)
- [x] 8.4 Strict-mode tested — re-export bridge does not introduce new strict-mode violations
- [x] 8.5 OTel — slim core observability counters/histograms still emit (catalog hits, plugin lifecycle, missing-key counts, detector metrics aggregation)
- [x] 8.6 Lifecycle dedup — `createI18n` idempotency preserved; `MessageCatalog.load` dedup preserved
- [x] 8.7 No retroactive tick — every box reflects work done in this change
## 9. Manifest + ecosystem awareness
- [ ] 9.1 Update root `CLAUDE.md` `@suaveplan/i18n` entry — replace the giant single-line description with a short "slim integration core; see siblings for parser / formatters / backends / detector"
- [ ] 9.2 Add CLAUDE.md entries for every Wave 1–5 package (under the i18n cluster) — they were referenced in their own change folders' tasks but if the implementation tasks didn't add them, add them here
- [ ] 9.3 Run `bun scripts/folder-reorg/generate-manifest.ts` to refresh `MANIFEST.md`
- [ ] 9.4 Update `STATUS.md` — every Wave 1–5 package and the slim core marked Complete
## 10. Archive (closes the entire i18n-modular-split)
- [x] 10.1 Fold spec delta into `openspec/specs/i18n/spec.md` — apply MODIFIED + REMOVED edits
- [x] 10.2 Move all 18 change folders to archive together:
- `openspec/changes/i18n-types-extension/` → `openspec/archive/<yyyy-mm-dd>-i18n-types-extension/`
- `openspec/changes/i18n-shared/` → `openspec/archive/<yyyy-mm-dd>-i18n-shared/`
- `openspec/changes/i18n-icu-parser/` → `openspec/archive/<yyyy-mm-dd>-i18n-icu-parser/`
- `openspec/changes/i18n-formatter-{number,relative-time,list,display-name,collator,segmenter,date,currency}/` → archive
- `openspec/changes/i18n-detector/` → archive
- `openspec/changes/i18n-backend-{memory,http,storage,fs-multifile,chained}/` → archive
- `openspec/changes/i18n-core-slim/` → archive
- [x] 10.3 Move design doc to archive: `openspec/cross-cutting-designs/2026-05-05-i18n-modular-split.md` → `openspec/archive/2026-05-05-i18n-modular-split-design.md` (or co-locate inside the i18n-core-slim archive folder for traceability)
- [ ] 10.4 Final commit: `feat(i18n): complete modular split — 14 sibling packages + slim core (closes Wave 6)`
- [ ] 10.5 Push to remote — pending explicit user approval.