French SIREN Luhn check
The body 732 829 32 gets check digit 0, giving SIREN 732 829 320, while a mistyped 732 829 321 fails. Compute the Luhn digit from eight digits or validate all nine, with spaces and dots allowed as printed on French documents. Free in your browser.
- Free
- Runs in your browser
- No sign-up
- Your data stays on your device
Run — free
Worked example
- Siren
- 73282932
- Calculation mode
- Compute
- Input
- 73282932
- Check digit
- 0
- With check
- 732829320
The SIREN number is the nine-digit identifier assigned to every legal entity and sole trader registered in France. It appears on invoices, Kbis extracts, company directories, and many banking or procurement forms. The ninth digit is a Luhn mod-10 check digit computed from the first eight digits, so a single mistype or a swapped pair often breaks the checksum before any registry lookup.
What a French SIREN is and how the Luhn check digit works
A SIREN (Système d’identification du répertoire des entreprises) is a nine-digit code that uniquely identifies a French company or entrepreneur for administrative, tax, and commercial purposes. The first eight digits form the body assigned by the official directory; the ninth digit is a check digit calculated with the Luhn algorithm — the same family of mod-10 doubling used on many account numbers and payment cards.
From right to left, every second digit is doubled; if doubling produces a value greater than nine, nine is subtracted; the weighted digits are summed; the check digit is chosen so the total is divisible by ten. When someone types 732 829 320 as 732 829 321, the weighted sum no longer ends in zero and validation fails. That catches common keying errors during supplier onboarding, e-invoicing, and OCR of paper Kbis documents.
This tool implements standard Luhn on pure SIREN digits after optional space or dot stripping. It does not look up Sirene, prove that a company is active, distinguish establishments (that is SIRET, fourteen digits), or assign a legal form. Compared with multi-country tax-ID format checkers, the intent here is specifically the French SIREN Luhn check digit: length bounds, grouping display, and algorithm naming match French business-identifier workflows rather than a generic country switch.
Where French SIREN checks fit invoicing, KYC, and data-quality workflows
Electronic invoicing and billing systems store a customer or vendor SIREN on every legal document; a single mistyped digit during onboarding can send fiscal data to the wrong party or fail later compliance checks. Procurement and marketplace platforms that onboard French sellers can recompute the Luhn check without calling an external registry, filtering OCR noise and partial captures early. Banks and payment gateways that accept French company identifiers for KYC metadata can apply the same nine-digit rule as a first-pass filter before deeper screening.
Product teams that already expose general Luhn tools should still use this SIREN-specific capability for French company ID fields so length bounds, optional grouping, and algorithm labeling match the domain and do not accept fourteen-digit SIRET strings as SIREN. Do not treat a passing SIREN Luhn check as proof that the company exists, is active in Sirene, is authorized to invoice, or matches a given legal name — it only proves the digit string is consistent under the French SIREN Luhn check algorithm.
What you can do with it
Audit SIREN columns in partner and invoice files
Batch-validate every SIREN in a CSV import and quarantine rows whose check digit no longer matches the recomputed expected value.
FAQ
What is the French SIREN Luhn check digit?
It is the ninth digit of a SIREN, computed with the Luhn mod-10 algorithm from the first eight digits so the full weighted digit sum is divisible by ten, catching many single-digit and transposition typos.
What happens with letters, wrong length, or a SIRET?
Compute needs eight digits; validate needs nine. A fourteen-digit SIRET is not accepted — use a SIRET-specific tool for establishments.
Is the French SIREN Luhn check tool free?
The browser tool is free and runs locally.
How is the SIREN check digit calculated?
Working from the right, double every second digit and subtract 9 from any result above 9, then add everything up. The check digit is chosen so the total is divisible by ten. For 732 829 32 it is 0, which gives 732 829 320.
Can I paste a SIREN with spaces or dots?
Yes. Groups separated by spaces or dots, as often printed on French invoices and Kbis extracts, are accepted, for example 732 829 320 or 732.829.320. Letters, hyphens and other punctuation are rejected rather than silently removed.
Related tools
For developers — API access
Everything on this page is available programmatically. This section is for teams who want to wire it into their own systems; everyone else can just use the tool above.
API endpoint
Prefer to automate it? One authenticated POST creates the task; the result comes back by webhook or a signed link. The same capability also runs here on the web, by email and from Telegram — and soon from our app too.
Call it from your stack
curl -X POST https://api.kit.forhosting.com/enc/siren-france \
-H "Authorization: Bearer $KIT_KEY" \
-H "Content-Type: application/json" \
-d '{"siren":"73282932"}'const res = await fetch("https://api.kit.forhosting.com/enc/siren-france", {
method: "POST",
headers: {
"Authorization": `Bearer ${process.env.KIT_KEY}`,
"Content-Type": "application/json"
},
body: JSON.stringify({
"siren": "73282932"
})
});
const { task_id } = await res.json();import os, requests
res = requests.post(
"https://api.kit.forhosting.com/enc/siren-france",
headers={"Authorization": f"Bearer {os.environ['KIT_KEY']}"},
json={
"siren": "73282932"
},
)
task_id = res.json()["task_id"]<?php
$res = file_get_contents("https://api.kit.forhosting.com/enc/siren-france", false, stream_context_create([
"http" => [
"method" => "POST",
"header" => "Authorization: Bearer " . getenv("KIT_KEY") . "\r\nContent-Type: application/json",
"content" => '{"siren":"73282932"}',
],
]));
$task = json_decode($res, true);body := bytes.NewBufferString(`{"siren":"73282932"}`)
req, _ := http.NewRequest("POST", "https://api.kit.forhosting.com/enc/siren-france", body)
req.Header.Set("Authorization", "Bearer "+os.Getenv("KIT_KEY"))
req.Header.Set("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)Example request
{
"siren": "73282932"
}Example response
{
"task_id": "tsk_a1b2c3d4e5f6a1b2c3d4e5f6",
"type": "enc.siren_france",
"status": "queued",
"_links": {
"result": "/tasks/tsk_…/result"
}
}The API is asynchronous: the call returns a task_id immediately and the result arrives by webhook. Polling is capped at 1 req/s per task.
Pricing
Published price — no tokens, no invented credits. A failed task is never charged.
Errors
| HTTP | Code | Meaning |
|---|---|---|
401 | unauthorized | Missing or invalid API key. |
402 | insufficient_balance | Your balance doesn't cover the task price. |
404 | unknown_type | That task type doesn't exist. |
429 | rate_limited | Too many requests. Use the webhook instead of polling. |
Technical notes
This capability computes that French SIREN Luhn check digit from an eight-digit payload, or validates a full nine-digit SIREN that already includes the trailing digit, and it reports bad input instead of silently stripping letters or punctuation. Use it free in the browser or call the KIT API at the published price; both paths run the same deterministic arithmetic with no network call and no INSEE or Sirene registry query.
What a French SIREN is and how the Luhn check digit works
Compared with a general-purpose Luhn utility that accepts any length, this capability enforces the eight-digit payload and nine-digit full forms required by SIREN so you cannot accidentally accept a fourteen-digit SIRET or a short account fragment as a company ID.
How to compute a check digit or validate a full nine-digit SIREN
Send a siren field that contains digits zero through nine, optionally grouped with spaces or dots as often printed on French documents (for example 732 829 32 or 732.829.320). Mode validate expects a complete nine-digit number including the trailing check digit. Empty strings, missing siren, invalid mode values, and wrong lengths (not eight digits for compute, not nine for validate) fail before any doubling runs and are not billed. Leading and trailing whitespace is trimmed; letters, hyphens used as primary separators, other punctuation, and mixed alphanumerics are rejected as non-numeric input with invalid_input so you never accept a silently cleaned value. Mode compute is the default: provide exactly eight digits without the check digit, and the engine returns check_digit as a one-character string, with_check as the full nine-digit string including that digit, and formatted as the spaced XXX XXX XXX form used on invoices and forms. The response reports valid true when the full weighted sum is divisible by ten, and always includes check_digit, expected_check_digit recomputed from the eight-digit payload alone, payload without the last digit, and formatted for consistent display. Because the path is pure parse with no clock, random source, or network, the same input always yields the same JSON on the free browser tool and on the API. At $0.002 per successful request you can gate bulk supplier imports, onboarding forms, and ETL jobs without negotiating a custom tier. Prefer compute when you assemble a SIREN from a known eight-digit body; prefer validate when a user, partner file, or scanned label supplies a full number and you need a boolean gate before a Sirene or internal master-data lookup.
Where French SIREN checks fit invoicing, KYC, and data-quality workflows
Validate mode at entry blocks the save when valid is false and can show expected_check_digit so the clerk corrects the form before the record is written.
Integration use cases
Gate SIREN fields on supplier and customer forms
When a user submits a full nine-digit SIREN, call validate mode and block the save when valid is false, showing expected_check_digit to help correct a single mistype before the ERP record is written.
Compute check digits when completing or minting IDs
From an eight-digit body, call compute mode and store with_check or formatted so every new SIREN string carries the correct trailing Luhn digit before print or export.
Technical questions
How do I compute a SIREN check digit with this API?
POST with siren set to the eight payload digits (spaces or dots optional) and mode compute (or omit mode). The response includes check_digit, with_check, and formatted as XXX XXX XXX.
How do I validate a full nine-digit SIREN?
POST with the full nine-digit string and mode validate. The response includes valid, check_digit, expected_check_digit, payload, and formatted.