Skip to content

fix(ro-RO): insert "de" before the currency unit for 20+#404

Merged
TylerVigario merged 2 commits into
mainfrom
fix/ro-RO-currency-de
Jun 16, 2026
Merged

fix(ro-RO): insert "de" before the currency unit for 20+#404
TylerVigario merged 2 commits into
mainfrom
fix/ro-RO-currency-de

Conversation

@TylerVigario

Copy link
Copy Markdown
Collaborator

Romanian requires the particle "de" before a counted noun when the number's last two digits are 00 or 20–99. toCurrency got this right for the bani (cents) but never applied it to the lei, so it produced grammatically wrong output:

input before after
20 douăzeci lei douăzeci **de** lei
21 douăzeci și unu lei douăzeci și unu **de** lei
100 o sută lei o sută **de** lei
1000 o mie lei o mie **de** lei
101 o sută unu lei o sută unu lei (unchanged — last two digits 01, no "de")

The fix mirrors the rule the codebase already applies in the bani path and in buildScalePhrase for scale words: needsDe = n >= 20 && (n % 100 === 0 || n % 100 >= 20).

The fixtures had encoded the de-less output — which is why the suite was green on the bug. Seven lei cases (21, 42, 100, 1000, and the lei+bani combinations) are corrected to the proper forms; the <20 cases and the already-correct bani cases are untouched.

How it was found

Auditing each count-agreement language's number → form selection against Intl.PluralRules (using CLDR purely as a verification oracle, not a runtime dependency). Romanian's CLDR few → other category boundary at 20 is exactly the "de" boundary, which flagged the gap. cs-CZ turned up a second divergence from the same audit — handled separately, pending a CLDR-vs-colloquial call.

Lint clean, 453 tests green.

🤖 Generated with Claude Code

Romanian requires "de" before a counted noun when the number's last two digits
are 00 or 20-99 ("douăzeci de lei", "o sută de lei", but "o sută unu lei").
toCurrency applied this to the bani (cents) path but not to the lei: it spelled
"douăzeci lei" / "o sută lei". The lei path now mirrors the bani path and the
scale-word handling already present in buildScalePhrase.

The fixtures had encoded the de-less output, so the suite stayed green on the
bug; the seven affected lei cases (21, 42, 100, 1000, and the lei+bani
combinations) are corrected to the proper forms.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Copilot AI review requested due to automatic review settings June 16, 2026 22:01

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Fixes Romanian (ro-RO) currency grammar by inserting the particle “de” before “lei” when required by the “00 or 20–99” last-two-digits rule (consistent with the existing handling for “bani”).

Changes:

  • Update toCurrency in src/ro-RO.js to conditionally emit " de lei" based on the last two digits of the lei count.
  • Correct Romanian currency fixtures that previously expected the de-less (incorrect) lei forms.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.

File Description
src/ro-RO.js Adds a BigInt-based predicate to insert “de” before LEU_PLURAL in toCurrency.
test/fixtures/ro-RO.js Updates expected currency strings to include “de” for affected lei cases (including mixed lei+bani and negative).

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread test/fixtures/ro-RO.js
Comment on lines 214 to +216
[10, 'zece lei'],
[21, 'douăzeci și unu lei'],
[42, 'patruzeci și doi lei'],
[100, 'o sută lei'],
[1000, 'o mie lei'],
[21, 'douăzeci și unu de lei'],
[42, 'patruzeci și doi de lei'],

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done in 583854a — added [20, 'douăzeci de lei'] and also [19, 'nouăsprezece lei'] to pin the >= 20 boundary on both sides, so a > 20 vs >= 20 off-by-one fails either direction.

Comment thread src/ro-RO.js Outdated
Comment on lines +455 to +458
// Romanian inserts "de" before the noun when the count's last two digits
// are 00 or 20-99 (the CLDR `other` category): "douăzeci de lei", "o sută
// de lei", but "o sută unu lei". Mirrors the bani path below and the
// scale-word handling in buildScalePhrase.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in 583854a — reworded: the comment now states the >= 20 gate explicitly (so 0-19, including 0, take no "de") and no longer claims it mirrors buildScalePhrase, which uses a related but per-segment predicate rather than this whole-count n % 100 rule.

Add explicit 19 ("nouăsprezece lei", no "de") and 20 ("douăzeci de lei")
fixtures so the >= 20 boundary is pinned two-sided — a > 20 vs >= 20 off-by-one
would now fail. Reword the rule comment to make the >= 20 gate explicit (it
excludes 0-19, so 0 doesn't take "de") and to stop claiming it mirrors
buildScalePhrase, which uses a related but per-segment predicate.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
@TylerVigario TylerVigario merged commit c420c82 into main Jun 16, 2026
7 checks passed
@TylerVigario TylerVigario deleted the fix/ro-RO-currency-de branch June 16, 2026 22:19
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants