How to validate a Japanese invoice registration number
Check a Japanese qualified invoice issuer registration number properly: format, check digit, whether it is registered, and whether it was valid on the invoice date.
Confirming that a registration number on an invoice is genuinely valid happens in stages. Most implementations stop at the first one, and that is where the problem starts.
There are four stages, not one
| Stage | What it establishes | Where it can be answered |
|---|---|---|
| Format | Is it T + 13 digits? | Local |
| Check digit | Do the digits cohere? | Local |
| Most implementations stop here | ||
| Registered | Does it actually exist? | Needs the register |
| Valid on a date | Was it valid on the invoice date? | Needs change history |
Plenty of implementations do 1 and 2 and call it validation. But well-formed unregistered numbers are trivial to generate. Passing stage 2 means the string is a plausible number and nothing more.
Stages 1 and 2: what you can do locally
A registration number is T followed by 13 digits. For a corporation those 13
digits are the corporate number (法人番号), whose leading digit is a checksum
over the other twelve. Transposed digits and similar slips are caught here.
We publish this as open source. No network call, no API key.
npm install @daichodo/validate
import { isValid } from '@daichodo/validate';
isValid('T8000000000001'); // true
Python works the same way.
pip install daichodo-validate
Sole traders break the check digit assumption
Every registration number satisfies the check digit, sole traders included. We measured this over the whole register on 2026-09-05 — the monthly full file plus the newest daily diffs, 5,421,496 numbers — and found zero exceptions. Corporations, sole traders and unincorporated associations all pass.
A sole trader's 13 digits are not a corporate number. None of 50,000 sampled appear in the 5.8-million-row corporate register. But they come from the same numbering scheme, so the check digit still holds.
The practical consequence is the one that catches people out: the number alone cannot tell you whether it belongs to a corporation or a sole trader. Only a register lookup can. If your code branches on "did the check digit produce a corporate number", it is answering a different question than it thinks.
The mirror-image mistake is worse, and we shipped it ourselves until we measured. Treating a check-digit failure as "probably a sole trader, therefore valid" accepts every typo and every fabricated number, because no genuine number fails. A single mistyped digit sails through.
Stage 3: is it actually registered?
This needs the register. The NTA's public site will tell you, but it stops being practical the moment you have more than a handful to check.
curl https://api.daichodo.com/v1/invoice-issuers/T8000000000001 \
-H "Authorization: Bearer dc_ test_ ..."
An unregistered number returns 404; a malformed one returns 400. Keep them
distinct — "that is not a number" and "that is a number and it is not
registered" mean different things to your accounting process.
A null name is not "not found"
The NTA strips identity fields for individuals at source. A sole trader's record comes back with every date intact and no name.
Treating name === null as "not found" is the most common way to get this
wrong.
Stage 4: was it valid on the invoice date?
This is the stage that actually matters.
Whether input tax credit applies turns on the registration's status on the date of the invoice. A business that has lapsed today may well have been registered when it issued the invoice you are processing. Looking only at current state gets this wrong in both directions.
curl "https://api.daichodo.com/v1/invoice-issuers/T8000000000001/validity?on=2024-06-30" \
-H "Authorization: Bearer dc_ test_ ..."
{
"registration_ number": "T8000000000001",
"on": "2024-06-30",
"valid": true,
"reason": "valid",
"registered_ on": "2023-10-01",
"ended_ on": null
}
We answer this from the diffs we have kept since our first ingestion, so it does not depend on the NTA's site being reachable or on your holding an application ID of your own.
Point-in-time validity is on the paid plans. Stages 1 and 2 — format and check digit — stay free at every tier, and the npm package above needs no key at all.
Because individuals retain their date fields, this works for sole traders as well as corporations.
Practical guidance
- Do stages 1 and 2 locally. A free library is enough.
- Stages 3 and 4 need the register: ingest it yourself, or use an API.
- If you ingest it yourself, mind the diff retention window. Files drop out of it, and a day you missed cannot be fetched from anywhere afterwards.
Common questions
What format is a Japanese invoice registration number?
"T" followed by 13 digits. For a corporation those 13 digits are the corporate number (法人番号). A sole trader's 13 digits are not a corporate number, but they come from the same numbering scheme, so the check digit applies to them too. The number alone cannot tell you which kind of entity it belongs to — only a register lookup can.
Is a valid check digit enough?
No. The check digit only confirms the number is well-formed. Whether it is actually registered requires a lookup, and well-formed unregistered numbers are trivial to generate.
How do I check whether it was valid on the invoice date?
Current state cannot answer that. Input tax credit turns on the registration status on the invoice date, so you need point-in-time validity against the change history.