@@ -40,8 +40,6 @@ export interface MessageNumberPart extends MessageExpressionPart {
4040export type MessageNumberOptions = Intl . NumberFormatOptions &
4141 Intl . PluralRulesOptions & { select ?: 'exact' | 'cardinal' | 'ordinal' } ;
4242
43- const INT = Symbol ( 'INT' ) ;
44-
4543export function readNumericOperand (
4644 value : unknown ,
4745 source : string
@@ -73,6 +71,9 @@ export function getMessageNumber(
7371 value : number | bigint ,
7472 options : MessageNumberOptions
7573) : MessageNumber {
74+ // @ts -expect-error We may have been a bit naughty earlier.
75+ if ( options . useGrouping === 'never' ) options . useGrouping = false ;
76+
7677 let locale : string | undefined ;
7778 let nf : Intl . NumberFormat | undefined ;
7879 let cat : Intl . LDMLPluralRule | undefined ;
@@ -121,7 +122,7 @@ export function getMessageNumber(
121122
122123/**
123124 * `number` accepts a number, BigInt or string representing a JSON number as input
124- * and formats it with the same options as
125+ * and formats it with a subset of the options of
125126 * {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/NumberFormat | Intl.NumberFormat}.
126127 * It also supports plural category selection via
127128 * {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/PluralRules | Intl.PluralRules}.
@@ -130,15 +131,15 @@ export function getMessageNumber(
130131 */
131132export function number (
132133 ctx : MessageFunctionContext ,
133- exprOpt : Record < string | symbol , unknown > ,
134+ exprOpt : Record < string , unknown > ,
134135 operand ?: unknown
135136) : MessageNumber {
136137 const input = readNumericOperand ( operand , ctx . source ) ;
137138 const value = input . value ;
138- const options : MessageNumberOptions = Object . assign (
139- { localeMatcher : ctx . localeMatcher } ,
140- input . options
141- ) ;
139+ const options : MessageNumberOptions = Object . assign ( { } , input . options , {
140+ localeMatcher : ctx . localeMatcher ,
141+ style : 'decimal'
142+ } as const ) ;
142143
143144 for ( const [ name , optval ] of Object . entries ( exprOpt ) ) {
144145 if ( optval === undefined ) continue ;
@@ -153,17 +154,12 @@ export function number(
153154 // @ts -expect-error TS types don't know about roundingIncrement
154155 options [ name ] = asPositiveInteger ( optval ) ;
155156 break ;
156- case 'useGrouping' : {
157- const strval = asString ( optval ) ;
158- // @ts -expect-error TS type is wrong
159- options [ name ] = strval === 'never' ? false : strval ;
160- break ;
161- }
162157 case 'roundingMode' :
163158 case 'roundingPriority' :
164159 case 'select' : // Called 'type' in Intl.PluralRules
165160 case 'signDisplay' :
166161 case 'trailingZeroDisplay' :
162+ case 'useGrouping' :
167163 // @ts -expect-error Let Intl.NumberFormat construction fail
168164 options [ name ] = asString ( optval ) ;
169165 }
@@ -173,32 +169,54 @@ export function number(
173169 }
174170 }
175171
176- const num =
177- Number . isFinite ( value ) && exprOpt [ INT ]
178- ? Math . round ( value as number )
179- : value ;
180-
181- return getMessageNumber ( ctx , num , options ) ;
172+ return getMessageNumber ( ctx , value , options ) ;
182173}
183174
184175/**
185176 * `integer` accepts a number, BigInt or string representing a JSON number as input
186- * and formats it with the same options as
177+ * and formats it with a subset of the options of
187178 * {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/NumberFormat | Intl.NumberFormat}.
188179 * It also supports plural category selection via
189180 * {@link https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Intl/PluralRules | Intl.PluralRules}.
190181 *
191- * The `maximumFractionDigits=0` and `style='decimal'` options are fixed for `:integer`.
192- *
193182 * @beta
194183 */
195- export const integer = (
184+ export function integer (
196185 ctx : MessageFunctionContext ,
197- options : Record < string , unknown > ,
198- input ?: unknown
199- ) =>
200- number (
201- ctx ,
202- { ...options , maximumFractionDigits : 0 , style : 'decimal' , [ INT ] : true } ,
203- input
204- ) ;
186+ exprOpt : Record < string , unknown > ,
187+ operand ?: unknown
188+ ) {
189+ const input = readNumericOperand ( operand , ctx . source ) ;
190+ const value = Number . isFinite ( input . value )
191+ ? Math . round ( input . value as number )
192+ : input . value ;
193+ const options : MessageNumberOptions = Object . assign ( { } , input . options , {
194+ //localeMatcher: ctx.localeMatcher,
195+ maximumFractionDigits : 0 ,
196+ minimumFractionDigits : undefined ,
197+ minimumSignificantDigits : undefined ,
198+ style : 'decimal'
199+ } as const ) ;
200+
201+ for ( const [ name , optval ] of Object . entries ( exprOpt ) ) {
202+ if ( optval === undefined ) continue ;
203+ try {
204+ switch ( name ) {
205+ case 'minimumIntegerDigits' :
206+ case 'maximumSignificantDigits' :
207+ options [ name ] = asPositiveInteger ( optval ) ;
208+ break ;
209+ case 'select' : // Called 'type' in Intl.PluralRules
210+ case 'signDisplay' :
211+ case 'useGrouping' :
212+ // @ts -expect-error Let Intl.NumberFormat construction fail
213+ options [ name ] = asString ( optval ) ;
214+ }
215+ } catch {
216+ const msg = `Value ${ optval } is not valid for :integer option ${ name } ` ;
217+ ctx . onError ( new MessageResolutionError ( 'bad-option' , msg , ctx . source ) ) ;
218+ }
219+ }
220+
221+ return getMessageNumber ( ctx , value , options ) ;
222+ }
0 commit comments