Canadian area code map — source: CNAC
If you try registering with eBay1, Shopify2, Twilio3, Intuit4, or Anthropic5 using a Canadian phone number with area code 2576 or 9427, most of them will tell you it doesn't exist.
The form field is very confident, and the form field is who you have to convince.
Area codes 257 (BC, May 24, 2025) and 942 (Ontario, April 26, 2025) are fully assigned, CRTC-approved, carrier-deployed Canadian area codes. Bell, Telus, and Rogers are issuing them. They route correctly. They receive SMS. They are, by every meaningful definition, real phone numbers.
They are also, according to a surprising number of major platforms, completely invalid. Not at the carrier level. Not in routing. On a web form.
$ curl -sX POST https://example.tld/signup \
-d 'phone=+12575550123'
{"error":"invalid_phone","field":"phone","reason":"unknown_area_code"}The crime scene
Here is the current Canadian numbering plan, expressed the way a validator actually sees it — one regex per province, matching the area codes carriers are actively issuing as of April 2026:
╔══════════════════════════════════════════════════════════════════════════╗
║ CA AREA CODES :: by province :: 2026.04.28 ║
╚══════════════════════════════════════════════════════════════════════════╝
BC ^(?:236|250|257|604|672|778)$ ← 257 added 2025
AB ^(?:368|403|587|780|825)$
SK ^(?:306|474|639)$ ← 474 added 2025
MB ^(?:204|431|584)$
ON ^(?:226|249|289|343|365|382|416|437|519
|548|613|647|683|705|742|807|905|942)$ ← 382, 742, 942 added 2025
QC ^(?:263|354|367|418|438|450|468|514|579
|581|819|873)$ ← 263, 354, 468 added 2025
NB ^(?:428|506)$ ← 428 added 2025
NS/PE ^(?:782|902)$
NL ^(?:709|879)$
YT ^867$
NT ^867$
NU ^867$
── legend ──────────────────────────────────────────────────────────────────
each pattern matches the three-digit area code segment of an E.164 number
codes added 2025 are absent from libphonenumber bundles older than 9.0.7
────────────────────────────────────────────────────────────────────────────
The libraries don't actually express it this cleanly — the real patterns are minified into compressed alternation groups across all of NANP, optimized for parser speed rather than human readability. But this is the logical content. Each province has an allowlist. Each allowlist has to grow when the CRTC says it grows. If your bundle doesn't reflect the rows above, you are rejecting valid Canadian phone numbers right now.
Phone number validation, in every library worth using, is fundamentally an allowlist lookup against compiled metadata. The library does not ask the carrier whether +12575550123 is a real number. It cannot. It opens a bundled data file, finds the entry for country code 1 and country CA, walks a regex pattern compiled from the current set of approved Canadian area codes, and asks whether your number matches.
If the regex matches, valid. If it doesn't, invalid. There is no third branch. There is no "I don't know, let me ask someone." The metadata file is the source of truth, and the metadata file is whatever shipped in the version of the library you have on disk.
This is true across the ecosystem: Google's libphonenumber8, the JS port libphonenumber-js, the wrapper intl-tel-input9, the various PHP and Python ports, vendor-built validators that consume the same upstream metadata. They differ in API surface and bundle size. They do not differ on the fundamental: the validity of an area code is a property of the data file, not of the carrier network.
To make the failure concrete: in libphonenumber, the Canadian area code allowlist is an explicit alternation group in the country's regex pattern. For codes starting with 2, the pre-fix pattern reads roughly:
2(?:04|[23]6|[48]9|50|63)
Covering 204, 226, 236, 249, 289, 250, and 263. Notably absent: 257. Same story for 942 in the 9xx group. When your number hits validation, the regex fails to match, the library returns invalid, and the platform rejects you. No useful error. No explanation. Just a red outline on a phone field and a vague message about entering a valid number.
The fix is, at the data layer, adding two characters to a regex. Three if you count the alternation pipe. The patch landed upstream and shipped in libphonenumber ≥ 9.0.710. The fix flowed downstream into the wrapper most frontends use, intl-tel-input ≥ 25.3.29, which pulls in libphonenumber v9.0.11 with the corrected metadata. Both patches have been publicly available since mid-2025. Updating is a one-line dependency bump.
$ npm i libphonenumber-js@latest
$ npm i intl-tel-input@latest
That is the entire engineering effort required to allow your customers in British Columbia to give you their phone number.
This is the part developers reach for the "well, technically it's not the library's fault, the metadata was correct at release time" defense. Sure. The library is doing what it was designed to do: lookup against a compiled allowlist. The library will keep being right — for as long as the allowlist is current. The moment the world adds an area code, the library is wrong about that area code until the bundle is refreshed and re-deployed. That window is the entire bug class. Phone number metadata is not a one-time install. It is an ongoing subscription to changes in the numbering plan, and you are responsible for staying current on it for as long as you accept phone numbers from users.
And yet.
The receipt
We tested directly against the following platforms and confirmed each rejects one or both area codes as invalid: eBay, Shopify, Twilio, Intuit.
We reported the issue to all of them, along with Anthropic. As of publication, Anthropic is the only one that has acknowledged and shipped a fix. The others have, charitably, been quiet and incapable of demonstrating a will to understand the issue.
In some cases the rejection happens via a stale validation bundle served directly from a CDN, cached at a version that predates the fix. In others the same outdated metadata appears to be baked server-side as well, which means bypassing the frontend doesn't help.
Twilio's own public documentation11 still lists Canada as having 42 area codes. It has 43. That page is part of their developer-facing glossary for phone number infrastructure. Twilio sells phone number infrastructure. The irony is doing a lot of heavy lifting there.
It gets better. A major Canadian telecommunications provider — actively issuing numbers in these area codes to its own customers — fails to validate those same numbers on its own account signup form. You cannot register on their website using a phone number they sold you. The form rejects it. The same stale validation, the same undeployed fix, the same red outline. A carrier gatekeeping itself.
A Canadian federal government website responsible for import and export registration also fails. If you are a business operating in Canada with a 257 or 942 number and you need to register with that system, your own government's form will tell you your phone number is not a phone number. The CRTC approved the area code. A different arm of the federal government's web infrastructure has not received the memo, the second memo, or the email asking why nobody has read either memo.
Five platforms is what we got around to testing. The pattern, the dependency, and the failure mode are all generic. There is no reason to think this stops at the five we named. If you ship a phone-input field anywhere on the public internet and you have not refreshed your validation metadata since spring 2025, you are very likely on this list and just do not know it yet. Go check. We'll wait.
The dependency story underneath
The uncomfortable implication is not really about phone numbers.
A dependency as prominent as Google's phone validation library, with a public changelog that is not hard to follow, not making it into production for six-plus months at companies with nine-figure infrastructure budgets says something. It says the dependency update process at those companies is either not running, not watching this class of library, or not converting findings into deploys. That is the same process responsible for pulling in security patches, deprecation notices, and breaking change advisories across every other third-party dependency in the stack.
Phone number validation is a low-stakes canary. It breaks in an obvious, user-visible way. Nobody gets breached because 257 gets rejected. But if the team responsible for validating Canadian phone numbers at a major carrier doesn't know their own libphonenumber metadata is eight-plus months stale, it is reasonable to wonder what they also don't know about the rest of their dependency graph. A company that can't validate its own product is not a company running a tight ship on CVE triage12. Stale phone metadata and stale security patches come from the same place: a dependency update pipeline that nobody is watching.
// what the rejection actually looks like in libphonenumber-js
import { isValidPhoneNumber } from 'libphonenumber-js'
isValidPhoneNumber('+12575550123', 'CA') // false ← stale bundle
isValidPhoneNumber('+12575550123', 'CA') // true ← post-2025 metadata
Same call, same number, same library. The only difference is whether the metadata bundle in node_modules was last refreshed before or after May 2025. That is the entire bug. It is the kind of bug that should not survive a single dependency-update sprint, let alone an entire fiscal year.
What to do about it
For developers hitting this:
- Bump
libphonenumber-jsto ≥ 9.0.7 andintl-tel-inputto ≥ 25.3.2. That is the fix. - If your validation runs client-side, check the bundle that is actually being served. CDN caches lie. Hash the metadata file and read the date.
- If you use Twilio Lookup13 to gate SMS flows, test explicitly with a 257 or 942 number against your current configuration. Do not assume.
- If you ship a phone-input field anywhere, write a regression test that hits every Canadian area code added in the last 24 months. There will be more.
The fix exists. It shipped months ago. Deploying it is not the hard part. Realizing you need to is.
Dealing with support has turned into a sanity test. Poorly implemented AI support agents will confidently misroute the issue, ask you to clear your cache, and close the ticket. Human support teams, when you reach them, will not know what "regex" or "client-side versus server-side" means, let alone what libphonenumber is. The escalation path is real but it is not visible from the form they handed you.
For Canadians locked out of platforms: cite CRTC Decision 2023-13514, name the specific library (libphonenumber) and the version requirement (≥ 9.0.7), and ask for engineering escalation. Support tier one will not know what libphonenumber is. That is expected. Get past them.
Area code 27315 goes live in Eastern Quebec in February 2027. See you then. Bring a regex.
-
eBay Canada — https://www.ebay.ca ↩
-
Shopify — https://www.shopify.com ↩
-
Twilio — https://www.twilio.com ↩
-
Intuit — https://www.intuit.com ↩
-
Anthropic — https://www.anthropic.com ↩
-
"New area code 257 to be introduced in British Columbia in 2025." Newswire, 2024. https://www.newswire.ca/news-releases/new-area-code-257-to-be-introduced-in-british-columbia-in-2025-801174266.html ↩
-
CRTC Decision 2023-135 (introduces 942 in Ontario). https://crtc.gc.ca/eng/archive/2023/2023-135.htm ↩
-
Google libphonenumber — https://github.com/google/libphonenumber ↩
-
intl-tel-input — https://github.com/jackocnr/intl-tel-input ↩ ↩2
-
libphonenumber releases — https://github.com/google/libphonenumber/releases ↩
-
Twilio docs — North American area codes (still lists Canada at 42). https://www.twilio.com/docs/glossary/north-american-area-codes ↩
-
National Vulnerability Database — https://nvd.nist.gov/ ↩
-
Twilio Lookup v2 API — https://www.twilio.com/docs/lookup/v2-api ↩
-
Telecom Decision CRTC 2023-135 — Approval of new area codes 257 and 942. https://crtc.gc.ca/eng/archive/2023/2023-135.htm ↩
-
North American Numbering Plan Administrator — https://www.nationalnanpa.com/ ↩
