Laravel localization in French Français
Everything you need to ship French in a Laravel app: the right locale codes,
the exact plural forms trans_choice() expects,
real localized Carbon output and Latin-script considerations.
Every value on this page was generated by running ICU, CLDR and Carbon — not copied from another article.
ISO 639-1
fr
Script / Direction
Latin · LTR
Plural forms (Laravel)
2
Text vs English
Expands
Locale codes
Set the base locale in config/app.php. For regional variants,
French commonly uses:
fr_FR, fr_CA, fr_BE, fr_CH
// config/app.php
'locale' => 'fr',
'fallback_locale' => 'en',
// Or switch at runtime
App::setLocale('fr');
Plural rules: what French actually needs
CLDR defines 3 cardinal categories for French. The sample numbers below were computed by ICU for this exact locale:
| CLDR category | Numbers that select it |
|---|---|
| one | 0–1, 1.5 |
| many | 1000000 |
| other | 2–130, 200, 1000 |
Laravel's trans_choice() maps numbers to
2 pipe-separated
forms for this locale:
| Form index | Numbers that select it |
|---|---|
| 0 | 0–1 |
| 1 | 2–130, 200, 1000 |
// lang/fr/messages.php
'items' => ':count item|:count items'
// Usage
trans_choice('messages.items', $count, ['count' => $count]);
Try any number live in the pluralization tester.
Localized dates with Carbon
Real output for French (fr locale),
generated by Carbon for March 21, 2026:
$date = now()->locale('fr');
$date->translatedFormat('l, j F Y');
// "samedi, 21 mars 2026"
$date->isoFormat('LLLL');
// "samedi 21 mars 2026 14:30"
$date->isoFormat('L');
// "21/03/2026"
$date->subDays(3)->diffForHumans();
// "il y a 3 mois"
What to watch out for in French
- Tu/vous distinction; most product UI uses vous, but decide before translating.
- Nouns are gendered and adjectives agree; elision (l', d') makes article + placeholder concatenation fragile.
- French typography requires a (narrow non-breaking) space before : ; ! ? and inside « guillemets ».
- Decimal comma with space as thousands separator (1 234,56).
The spacing rules that make French look wrong in HTML
French typography requires a space before certain punctuation marks, which is unlike almost every other language using the Latin script. The colon, semicolon, question mark and exclamation mark all take a preceding space, and guillemets take spaces inside them.
| Mark | French usage | Space required |
|---|---|---|
: |
Attention : erreur | Non-breaking space before |
? ! |
Continuer ? | Thin non-breaking space before |
; |
oui ; non | Thin non-breaking space before |
« » |
« bonjour » | Inside both guillemets |
, . |
Bonjour, monde. | None |
The space must be non-breaking. An ordinary space allows the browser to wrap the line between the word and its punctuation, leaving a question mark stranded at the start of the next line. Use \u{202F} (narrow no-break space) or \u{00A0} rather than a plain space.
Non-breaking spaces in a French lang file
// lang/fr/messages.php — the space before ? is U+202F
return [
'confirm' => "Voulez-vous continuer\u{202F}?",
'error' => "Erreur\u{00A0}: le fichier est introuvable",
];
Trim functions are the usual culprit. A trim() or whitespace-normalising regex that collapses runs of space will convert your carefully placed narrow no-break spaces into ordinary ones, or delete them, and the typography quietly degrades.
Quebec French follows the same rules with one relaxation: the space before the question and exclamation marks is often omitted, while the space before the colon is retained. If you serve both France and Quebec, this is one of several reasons to keep fr_FR and fr_CA apart.
Tu, vous, and a stricter convention than Spanish
French distinguishes informal tu from formal vous, and the software convention leans considerably more formal than in Spanish or German. Vous is the safe default for almost any product addressing adults, and using tu with someone who expects vous reads as genuinely rude rather than merely casual.
| English | Informal (tu) | Formal (vous) |
|---|---|---|
| Your account | ton compte | votre compte |
| You have 3 messages | Tu as 3 messages | Vous avez 3 messages |
| Save your changes | Enregistre tes modifications | Enregistrez vos modifications |
| Are you sure? | Es-tu sûr ? | Êtes-vous sûr ? |
Consumer products aimed at teenagers and some gaming or social apps use tu, but the threshold is much higher than in Spanish. Unless you have a specific reason, choose vous.
French interfaces also lean heavily on the infinitive for buttons and actions, which sidesteps the question entirely. Enregistrer, Annuler, Supprimer — these work regardless of register, and they are what French users expect on a button.
Gender agreement and elision
Every French noun is masculine or feminine, and adjectives and past participles agree with it. As in Spanish, this makes assembling sentences from fragments unreliable — but French adds a second complication that Spanish does not have: elision.
Articles and several short words contract before a vowel or a silent h. Le and la both become l', de becomes d', and je becomes j'. So the correct form depends on the first letter of the following word, which a template cannot know.
Elision defeats template assembly
// le fichier (consonant)
// l'utilisateur (vowel — elided)
// l'historique (silent h — elided)
// le héros (aspirated h — not elided!)
// So this is unfixable by rule:
'Supprimer le ' . __("types.{$type}")
The aspirated h is the detail that defeats even a clever implementation. Héros takes le while historique takes l', and nothing in the spelling distinguishes them — it is lexical knowledge, held per word. Write complete sentences as single translation keys and the problem disappears.
Past participle agreement adds another layer: le fichier est supprimé but la photo est supprimée, and plural forms add an s to both. A status message assembled from a shared "deleted" string will be wrong roughly half the time.
Text expansion and the accent rules
French expands about fifteen to twenty per cent over English, less than German but enough to matter in constrained layouts. The bigger issue is that French favours longer, more explicit constructions where English is terse.
| English | French | Growth |
|---|---|---|
| Save | Enregistrer | +175% |
| Settings | Paramètres | +25% |
| Sign in | Se connecter | +71% |
| Delete | Supprimer | +50% |
| Search | Rechercher | +67% |
Accents are mandatory and carry meaning. Ou (or) and où (where) are different words, as are a (has) and à (to). Stripping accents for URL slugs or search keys is fine; stripping them from displayed text is an error.
Capital letters keep their accents in modern usage — École, not Ecole. The old typewriter convention of dropping accents on capitals is considered incorrect by the Académie française, though you will still see it in older material. Uppercase transformations must preserve them, which PHP's strtoupper() does not do for multi-byte characters.
Uppercasing French safely
<?php
strtoupper('école'); // 'éCOLE' — broken
mb_strtoupper('école'); // 'ÉCOLE' — correct
// In Blade, prefer Str::upper()
{{ Str::upper($label) }}
Plurals, dates and numbers
French takes two plural forms in CLDR, but with one notable difference from English: the singular form covers both 0 and 1. French writes 0 fichier in the singular, where English writes "0 files" in the plural.
The zero case differs from English
// lang/fr/messages.php
'files' => ':count fichier|:count fichiers',
// 0 → "0 fichier" (singular — correct in French)
// 1 → "1 fichier"
// 2 → "2 fichiers"
This is handled correctly by Laravel when the locale is set properly, and handled incorrectly by any hand-rolled $count === 1 ? $singular : $plural check. It is a small detail that native speakers notice immediately.
Numbers use a space as the thousands separator and a comma for decimals: 1 234 567,89. That separator should be a non-breaking space so a figure never wraps across lines. Currency follows the amount: 1 234,56 €, not €1 234,56.
| France (fr_FR) | Canada (fr_CA) | Switzerland (fr_CH) | |
|---|---|---|---|
| Thousands | 1 234 567 | 1 234 567 | 1'234'567 |
| Decimal | 1234,56 | 1234,56 | 1234.56 |
| Currency | 1 234,56 € | 1 234,56 $ | CHF 1234.56 |
| Short date | 21/03/2026 | 2026-03-21 | 21.03.2026 |
Canadian French uses ISO-style dates, which is a significant divergence from France and a common source of ambiguity if you serve both. Month and weekday names are lowercase in all French locales — 21 mars 2026, never 21 Mars 2026.
France and Quebec are different products
French Canada is not a formatting variant of France. The vocabulary diverges in ways that are immediately visible to users, and Quebec has legal requirements around French-language software that no other market imposes.
| English | France (fr_FR) | Quebec (fr_CA) |
|---|---|---|
| e-mail / courriel | courriel | |
| To chat | chatter | clavarder |
| Shopping | shopping | magasinage |
| Weekend | week-end | fin de semaine |
| Parking | parking | stationnement |
| Download | télécharger | télécharger |
The pattern is that France borrows English words freely while Quebec, protective of the language, coins French equivalents. Shipping France French to Quebec reads as careless; shipping Quebec French to France reads as quaint. Neither is neutral.
Quebec's Charter of the French Language requires that software sold in the province be available in French, with French at least as prominent as any other language. If you sell into Quebec, this is a compliance matter and not only a quality one, and it applies to the interface, documentation and customer support alike.
The formatting differences compound the vocabulary ones. Quebec uses ISO-style dates (2026-03-21) where France uses day-first (21/03/2026), and Quebec places the dollar sign after the amount in the French convention (1 234,56 $) rather than before it as in English Canada. A single fr locale cannot be right for both markets.
If budget forces one French, France French reaches more users globally and is broadly understood in Quebec. But if Quebec is a target market in its own right, treat it as a separate locale from the start — retrofitting fr_CA after building on a shared fr means auditing every string rather than adding a file.
Getting the locale wiring right
French formatting depends on the region far more than the translation does. The same French sentence needs different numbers, dates and currency placement depending on whether the reader is in Paris, Montreal, Geneva or Brussels, and none of that is decided by the contents of your language files.
Set the full locale for formatting rather than the bare language code. Carbon, the Number helper and PHP's intl formatters all need the region to choose between a space and an apostrophe as the thousands separator, or between day-first and ISO date order. Passing fr gets you French defaults, which are France's defaults, and they are wrong for Canada and Switzerland.
Non-breaking spaces deserve a dedicated guard. Because they are invisible, they survive review and die in refactors — a whitespace-normalising helper, an over-eager trim(), or a copy-paste through an editor that normalises exotic spaces. A test asserting that specific strings still contain U+202F or U+00A0 costs nothing and catches a regression that no human reviewer will spot.
Install the Laravel-Lang French files for framework strings instead of writing them. They are professionally translated, they already apply the punctuation spacing rules correctly, and getting those rules right across several hundred validation messages by hand is not a good use of anyone's time.
A missing French key falls back to English, which in a French interface reads as an outright fault rather than a minor gap. Check key parity across locales in CI so the gap is caught before a user finds it.
What ships broken most often
- Missing or breaking spaces before punctuation. Usually destroyed by whitespace normalisation rather than by the translator.
-
Accents lost on capitals.
strtoupper()on multi-byte text, producing ECOLE or worse. - The zero case in the plural. "0 fichiers" instead of "0 fichier", from a hand-written plural check.
- Concatenated strings ignoring elision. le utilisateur instead of l'utilisateur.
- Capitalised months. Mars instead of mars, from English date formatting.
- Currency before the amount. €1 234 rather than 1 234 €.
- Quebec served France conventions. Different date format, different spacing tolerance, different vocabulary.
French is the language where typography matters most. The grammar problems are shared with other Romance languages, but the spacing rules are unique, invisible to English-speaking developers, and fragile in exactly the places where code touches strings.
Framework strings already translated
Laravel's own validation, auth and pagination strings are maintained in French by the open-source Laravel-Lang project (MIT). Install them, then manage your app's own strings live:
composer require laravel-lang/common --dev
php artisan lang:add fr
php artisan lang:update
Translate your app into French today
Import your lang files, translate every key into French with one AI click, and publish changes live — no deploy. Set up in 5 minutes.