There was no CLAUDE.md. This adds one, holding what has actually cost time in this repo rather than a style guide — CONTRIBUTING.md is that.
The plural key is the other form.plural() looks the entry up by forms.other, so a call site written as plural(n, { one: "Deleted {n} contact", other: "Deleted {n} contacts" }) is keyed on the plural. Keying the catalogue on the one form type-checks, builds, passes every test, and silently renders English in all nine languages. It cost a round trip on #278.
The part worth writing down is the signal, not the rule. There is exactly one: the "falling back to English" count from i18n-catalog-check. The percentage is actively misleading here — adding keys moves the denominator, so it sat at 98% whether or not the new strings were translated. The note says to compare the fallback count against main, and why not to read the percentage instead.
Two other things, both from this week:
A change touching user-visible strings is work in nine catalogues, and should be reported explicitly — including when the answer is "none added", so it is never left to be inferred.
Store tests do not exercise the component. The shift-click range bug in #278 is the standing example: the range was measured inside a setState updater, which React runs after the anchor ref has already moved, so it passed every store assertion and failed the moment the built app was driven.
Docs only — no code, no strings, no catalogue changes.
There was no `CLAUDE.md`. This adds one, holding what has actually cost time in this repo rather than a style guide — `CONTRIBUTING.md` is that.
**The plural key is the `other` form.** `plural()` looks the entry up by `forms.other`, so a call site written as `plural(n, { one: "Deleted {n} contact", other: "Deleted {n} contacts" })` is keyed on the plural. Keying the catalogue on the `one` form type-checks, builds, passes every test, and silently renders English in all nine languages. It cost a round trip on #278.
**The part worth writing down is the signal, not the rule.** There is exactly one: the "falling back to English" count from `i18n-catalog-check`. The percentage is actively misleading here — adding keys moves the denominator, so it sat at 98% whether or not the new strings were translated. The note says to compare the fallback count against `main`, and why not to read the percentage instead.
Two other things, both from this week:
- A change touching user-visible strings is work in nine catalogues, and should be reported explicitly — including when the answer is "none added", so it is never left to be inferred.
- Store tests do not exercise the component. The shift-click range bug in #278 is the standing example: the range was measured inside a `setState` updater, which React runs after the anchor ref has already moved, so it passed every store assertion and failed the moment the built app was driven.
Docs only — no code, no strings, no catalogue changes.
**Merged** 2026-09-04 as coffey-labs/ihasmail@fcbd8f64491b
<sub>Rebuilt from: GH Archive, git history, session transcript.</sub>
This repo is archived. You cannot comment on issues.
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
There was no
CLAUDE.md. This adds one, holding what has actually cost time in this repo rather than a style guide —CONTRIBUTING.mdis that.The plural key is the
otherform.plural()looks the entry up byforms.other, so a call site written asplural(n, { one: "Deleted {n} contact", other: "Deleted {n} contacts" })is keyed on the plural. Keying the catalogue on theoneform type-checks, builds, passes every test, and silently renders English in all nine languages. It cost a round trip on #278.The part worth writing down is the signal, not the rule. There is exactly one: the "falling back to English" count from
i18n-catalog-check. The percentage is actively misleading here — adding keys moves the denominator, so it sat at 98% whether or not the new strings were translated. The note says to compare the fallback count againstmain, and why not to read the percentage instead.Two other things, both from this week:
setStateupdater, which React runs after the anchor ref has already moved, so it passed every store assertion and failed the moment the built app was driven.Docs only — no code, no strings, no catalogue changes.
Merged 2026-09-04 as coffey-labs/ihasmail@fcbd8f6449
Rebuilt from: GH Archive, git history, session transcript.