formatjs date format range error invalid locale data
Covers the formatjs RangeError on invalid locale data - confirm with Intl directly, normalize underscores to hyphens, add a fallback. Use it when date or number formatting throws on the locale tag. Not for wrong-language output.
Fix the formatjs date format range error on invalid locale data
TL;DR
The locale tag you passed is not valid BCP47, so Intl rejects it before formatjs even starts. Validate the tag and fall back to a known-good one. This usually happens when a locale string comes from user input or a CMS with underscores instead of hyphens.
The error
RangeError: Incorrect locale information provided
at DateTimeFormat (formatDate with locale "en_US")Fix it
Step 1: Confirm the tag is the problem
node -e "try{new Intl.DateTimeFormat('en_US')}catch(e){console.log('bad:',e.message)}; console.log('good:',new Intl.DateTimeFormat('en-US').resolvedOptions().locale)"Expected: en_US throws, en-US resolves. Underscore is the giveaway.
Step 2: Normalize the locale where it enters your code
node -e "const fix=s=>s.replace(/_/g,'-'); console.log(fix('en_US'), fix('pt_BR'))"Expected: Every locale string becomes hyphenated BCP47 before it reaches formatjs.
Step 3: Add a fallback for tags that still fail
node -e "function safe(l){try{new Intl.DateTimeFormat(l);return l}catch(e){return 'en-US'}}; console.log(safe('xx-YY'))"Expected: Unknown tags fall back to en-US instead of throwing.
Step 4: Check the CMS or API that supplies the locale
grep -rn "locale" src/config.js | head -5Expected: The source now emits hyphenated tags.
When to use this
- formatjs or Intl throws RangeError about incorrect locale information
- Locale strings come from a CMS, URL param, or user profile
When NOT to use this
- The date formats but in the wrong language, that is a missing locale-data issue
- You need a locale Intl does not know, load a polyfill with its data
Tool and version compatibility
- formatjs v5/v6, all browsers with Intl, Node 13+
- BCP47 language tags, hyphens not underscores
Variant phrasings
same error from NumberFormat
Identical fix. All Intl constructors validate the tag the same way.
locale with script subtag fails
Check the subtag order: language, script, region. zh-Hans-CN is right, zh-CN-Hans is not.
Why it happens
Intl constructors validate the locale string against BCP47 before doing any formatting. Underscores, wrong subtag order, or unknown subtags fail validation, and formatjs just surfaces the RangeError from the constructor.
Edge cases
- Lowercase region codes usually still work but canonical form is uppercase, normalize both
- Private-use subtags starting with x- are valid, do not strip them in normalization
- Some environments lack full ICU, a valid tag can still throw, check resolvedOptions
Provenance
Resolved from the public thread: https://vectle.com/posts/pst1btkDuusrPdG5_ap5gCFg
Maintainer review
No maintainer verification is recorded for this version.
This records the version a maintainer checked. It does not assert that the version is the latest upstream release.