Localize version 0.26.0
[0.26.0] — May 6th, 2026
This release fixes user-reported bug #22 in time interval formatting and a number of RBNF conformance bugs arising from a more complete conformance testing process. The RBNF bugs have been around unreported and undiagnosed for many years.
Breaking Change
- The default
Localize.Interval.to_string/3format output (which is:medium) for time-only inputs now includes seconds.Localize.Interval.to_string!(~T[12:00:00], ~T[14:00:00], locale: :ja)shifts from午後0時00分~2時00分to12:00:00~14:00:00.:en's:mediumshifts from12:00 – 2:00 PMto12:00:00 PM – 2:00:00 PM. Users who relied on no-seconds output should explicitly pass time_format::short.
Bug Fixes
-
Fix
Localize.Interval.to_string/3collapsing the:short,:medium,:long, and:fulltime styles to the same:hmskeleton on Time inputs.:shortkeeps CLDR's interval-format dispatch (collapsed AM/PM);:mediumand above route through the locale's per-style time-format pattern, restoring per-style differentiation and including seconds in the default:mediumoutput. Thanks to @woylie for the report. Fixes #22. -
Fix
:time_formatbeing silently ignored onLocalize.Interval.to_string/3for Time inputs. The option now takes precedence over:format, matching the precedence used on datetime intervals. Thanks to @woylie for the report. Fixes #22. -
Fix
Localize.Interval.to_string/3crashing withFunctionClauseErrorwhen called with a binary:format(or:time_format) on Time inputs. Binary patterns are now applied to both endpoints and joined via the locale's interval-format fallback template, matching the behaviour of datetime intervals. Thanks to @woylie for the report. Fixes #22. -
RBNF parser now distinguishes
>>from>>>so CJK locales emit fractional digits without an inter-digit separator —Localize.Number.Rbnf.to_string(3.14, "spellout-numbering", locale: :zh)is三点一四instead of三点一 四. -
RBNF leading and embedded zeros in fractional digits, and very small magnitudes, are now preserved —
0.05 enis"zero point zero five",3.04 zhis三点〇四, and0.000001 enis"zero point zero zero zero zero zero one". -
RBNF
0.xspecial-base rule now matches when the integer part is zero and the value is non-zero, routing ko0.5 spellout-numberingthrough its locale-correct sino-Korean영점오instead of the previousx.x-fallback공점공오. -
RBNF negative floats no longer double their output or silently drop the sign — ko
-0.5 spellout-numberingis-영점오instead of공점공점오, and locales that lack a-xrule now get an ASCII-prefix. -
RBNF integer
<#,##0<quotient and float>%name>/>#,##0>/<%name<modulo and quotient no longer crash, completing case-clause coverage for every TR35 substitution-argument shape. -
RBNF
$(cardinal,…)and$(ordinal,…)plural-keyed substitutions now use the requested locale's plural rules instead of hard-coding English — frLocalize.Number.Rbnf.to_string(21, "digits-ordinal-masculine", locale: :fr)is"21e"instead of"21er". -
RBNF fraction-with-rule numerator/denominator algorithm is now spec-correct — ky
1.5 spellout-cardinalisбир бүтүн ондон бешinstead ofбир бүтүн беш.
Enhancements
-
Add
:minimum_significant_digitsand:maximum_significant_digitsoptions toLocalize.Number.to_string/2. -
Localize.Number.Rbnf.to_string/3now acceptsDecimalinputs in addition to native integers and floats, with whole-valued Decimals routed through the integer path with no precision loss. -
RBNF
>>>integer modulo now applies the source-preceding rule per TR35 §RBNF_Syntax, closing a latent gap; no current CLDR locale exercises this path.