API Intl.DurationFormat
Formatez les durées en JavaScript avec localisation automatique
Introduction
Lorsque vous affichez la durée d'une action, vous devez formater les valeurs de durée pour les utilisateurs. Un lecteur vidéo affiche la durée d'exécution, une réservation de vol affiche le temps de trajet, une application de fitness affiche la durée d'entraînement. Sans localisation, vous pourriez écrire du code comme ceci :
const hours = 1;
const minutes = 46;
const seconds = 40;
const duration = `${hours}h ${minutes}m ${seconds}s`;
Cela produit "1h 46m 40s" pour tous les utilisateurs quelle que soit la langue. Les utilisateurs français voient "1h 46m 40s" alors qu'ils attendent "1 h 46 min 40 s". Les utilisateurs allemands voient les mêmes abréviations anglaises. Les utilisateurs espagnols n'obtiennent pas de conjonction "y" entre les unités.
L'API Intl.DurationFormat résout ce problème. Elle formate les durées selon la langue de l'utilisateur et les conventions culturelles sans bibliothèques externes ni construction manuelle de chaînes.
const duration = { hours: 1, minutes: 46, seconds: 40 };
new Intl.DurationFormat('fr-FR', { style: 'short' }).format(duration);
// "1 h, 46 min et 40 s"
Le formateur gère automatiquement les abréviations, les conjonctions, l'ordre des mots et l'espacement pour n'importe quelle locale.
Que sont les durées
Une durée représente un intervalle de temps, pas un point dans le temps. Les dates et heures marquent quand quelque chose se produit. Les durées mesurent combien de temps quelque chose prend.
Cette distinction est importante pour le formatage. Les dates impliquent des calendriers, des fuseaux horaires et des règles historiques. Les durées sont plus simples : elles mesurent le temps écoulé en unités standard sans contexte calendaire.
L'API Intl.DurationFormat gère les durées. L'API Intl.DateTimeFormat gère les dates et heures. Utilisez le bon outil pour chaque tâche.
Créer un formateur de durée
Le constructeur prend une locale et un objet d'options. La locale détermine la langue de sortie. Les options contrôlent le style de formatage et l'affichage des unités.
const formatter = new Intl.DurationFormat('en', { style: 'long' });
Appelez format() avec un objet durée. L'objet contient des propriétés numériques pour les unités de temps. Incluez uniquement les unités que vous souhaitez afficher.
const duration = { hours: 2, minutes: 30 };
formatter.format(duration);
// "2 hours and 30 minutes"
L'API prend en charge ces unités de temps : years, months, weeks, days, hours, minutes, seconds, milliseconds, microseconds, nanoseconds. Utilisez les unités qui correspondent à vos données.
Choisir un style de formatage
L'option style contrôle la densité de l'affichage. Quatre styles sont disponibles : long, short, narrow et digital.
Le style long utilise des mots complets. Utilisez-le pour la prose et l'accessibilité.
const duration = { hours: 1, minutes: 46, seconds: 40 };
new Intl.DurationFormat('en', { style: 'long' }).format(duration);
// "1 hour, 46 minutes and 40 seconds"
Le style court utilise des abréviations courantes. Utilisez-le lorsque l'espace est limité mais que la lisibilité est importante.
new Intl.DurationFormat('en', { style: 'short' }).format(duration);
// "1 hr, 46 min and 40 sec"
Le style étroit utilise un minimum de caractères. Utilisez-le pour les affichages compacts comme les interfaces mobiles.
new Intl.DurationFormat('en', { style: 'narrow' }).format(duration);
// "1h 46m 40s"
Le style numérique produit un affichage de type minuteur avec des deux-points. Utilisez-le pour les lecteurs multimédias et les affichages de compte à rebours.
new Intl.DurationFormat('en', { style: 'digital' }).format(duration);
// "1:46:40"
Localisation dans différentes langues
La même durée se formate différemment dans chaque langue. L'API gère toute la localisation automatiquement.
const duration = { hours: 1, minutes: 46, seconds: 40 };
new Intl.DurationFormat('en', { style: 'long' }).format(duration);
// "1 hour, 46 minutes and 40 seconds"
new Intl.DurationFormat('fr', { style: 'long' }).format(duration);
// "1 heure, 46 minutes et 40 secondes"
new Intl.DurationFormat('de', { style: 'long' }).format(duration);
// "1 Stunde, 46 Minuten und 40 Sekunden"
new Intl.DurationFormat('es', { style: 'long' }).format(duration);
// "1 hora, 46 minutos y 40 segundos"
new Intl.DurationFormat('ja', { style: 'long' }).format(duration);
// "1時間46分40秒"
Remarquez comment chaque locale utilise des mots, des abréviations et des conjonctions différents. Le français utilise « et », l'allemand utilise « und », l'espagnol utilise « y », le japonais n'utilise pas de conjonctions. L'API connaît ces règles.
Les styles court et étroit se localisent également correctement.
new Intl.DurationFormat('fr', { style: 'short' }).format(duration);
// "1 h, 46 min et 40 s"
new Intl.DurationFormat('de', { style: 'narrow' }).format(duration);
// "1 Std. 46 Min. 40 Sek."
Construire des objets de durée à partir de calculs de temps
Les objets de durée sont de simples objets JavaScript avec des propriétés d'unités de temps. Créez-les à partir de n'importe quel calcul de temps.
Convertissez les millisecondes en unités de durée en divisant par les facteurs appropriés.
const milliseconds = 6400000; // 1 hour, 46 minutes, 40 seconds
const hours = Math.floor(milliseconds / 3600000);
const minutes = Math.floor((milliseconds % 3600000) / 60000);
const seconds = Math.floor((milliseconds % 60000) / 1000);
const duration = { hours, minutes, seconds };
new Intl.DurationFormat('en', { style: 'short' }).format(duration);
// "1 hr, 46 min and 40 sec"
Calculez la durée à partir de deux dates en soustrayant les horodatages.
const start = new Date('2025-01-01T10:00:00');
const end = new Date('2025-01-01T11:46:40');
const diffMs = end - start;
const hours = Math.floor(diffMs / 3600000);
const minutes = Math.floor((diffMs % 3600000) / 60000);
const seconds = Math.floor((diffMs % 60000) / 1000);
const duration = { hours, minutes, seconds };
Incluez uniquement les unités dont vous avez besoin. Omettez les valeurs nulles sauf si vous souhaitez qu'elles soient affichées.
const duration = { minutes: 5, seconds: 30 };
new Intl.DurationFormat('en', { style: 'long' }).format(duration);
// "5 minutes and 30 seconds"
Contrôler les unités affichées
Par défaut, le formateur affiche toutes les unités que vous fournissez dans l'objet de durée. Contrôlez l'affichage des unités avec l'objet d'options.
Spécifiez le style d'affichage pour chaque unité individuellement. Les options sont long, short, narrow, numeric et 2-digit.
const duration = { hours: 1, minutes: 5, seconds: 3 };
new Intl.DurationFormat('en', {
hours: 'long',
minutes: 'numeric',
seconds: '2-digit'
}).format(duration);
// "1 hour, 5:03"
Le style numeric affiche le nombre sans étiquettes. Le style 2-digit ajoute un remplissage par des zéros. Utilisez-les pour des affichages compacts mélangeant texte et nombres.
Masquez les unités en les omettant à la fois de l'objet de durée et des options.
const duration = { hours: 2, minutes: 30 };
new Intl.DurationFormat('en', { style: 'short' }).format(duration);
// "2 hr and 30 min"
Le style numérique nécessite que toutes les unités, de la plus grande à la plus petite, soient présentes ou explicitement configurées.
const duration = { minutes: 5, seconds: 30 };
new Intl.DurationFormat('en', { style: 'digital' }).format(duration);
// "5:30"
Formater les durées de lecteur vidéo
Les lecteurs vidéo affichent la durée dans les contrôles. Utilisez le style étroit ou numérique pour un affichage compact.
function formatVideoDuration(seconds) {
const hours = Math.floor(seconds / 3600);
const minutes = Math.floor((seconds % 3600) / 60);
const secs = Math.floor(seconds % 60);
const duration = hours > 0
? { hours, minutes, seconds: secs }
: { minutes, seconds: secs };
const locale = navigator.language;
return new Intl.DurationFormat(locale, { style: 'digital' }).format(duration);
}
formatVideoDuration(6400); // "1:46:40"
formatVideoDuration(330); // "5:30"
Cela gère à la fois les vidéos courtes et longues en incluant conditionnellement les heures.
Formater les durées de vol et de voyage
Les interfaces de réservation de voyages affichent la durée du trajet. Utilisez le style court pour une lisibilité dans un espace limité.
function formatFlightDuration(departureDate, arrivalDate, locale) {
const diffMs = arrivalDate - departureDate;
const hours = Math.floor(diffMs / 3600000);
const minutes = Math.floor((diffMs % 3600000) / 60000);
const duration = { hours, minutes };
return new Intl.DurationFormat(locale, { style: 'short' }).format(duration);
}
const departure = new Date('2025-06-15T10:30:00');
const arrival = new Date('2025-06-15T18:45:00');
formatFlightDuration(departure, arrival, 'en');
// "8 hr and 15 min"
formatFlightDuration(departure, arrival, 'fr');
// "8 h et 15 min"
Formater les durées d'entraînement et d'activité
Les applications de fitness suivent la durée de l'exercice. Utilisez le style long pour les résumés de session et le style étroit pour les vues en liste.
function formatWorkoutDuration(startTime, endTime, locale) {
const diffMs = endTime - startTime;
const hours = Math.floor(diffMs / 3600000);
const minutes = Math.floor((diffMs % 3600000) / 60000);
const duration = hours > 0
? { hours, minutes }
: { minutes };
return new Intl.DurationFormat(locale, { style: 'long' }).format(duration);
}
const workoutStart = new Date('2025-06-15T07:00:00');
const workoutEnd = new Date('2025-06-15T08:15:00');
formatWorkoutDuration(workoutStart, workoutEnd, 'en');
// "1 hour and 15 minutes"
Obtenir les parties formatées pour un affichage personnalisé
La méthode formatToParts() renvoie un tableau d'objets représentant chaque élément de la sortie formatée. Utilisez cela pour styliser des parties individuelles ou créer des mises en page personnalisées.
const duration = { hours: 1, minutes: 46, seconds: 40 };
const parts = new Intl.DurationFormat('en', { style: 'long' }).formatToParts(duration);
Chaque partie possède un type et une value. Les types incluent hour, minute, second, literal et des étiquettes d'unités comme hourUnit, minuteUnit.
[
{ type: "integer", value: "1" },
{ type: "literal", value: " " },
{ type: "unit", value: "hour" },
{ type: "literal", value: ", " },
{ type: "integer", value: "46" },
{ type: "literal", value: " " },
{ type: "unit", value: "minutes" },
{ type: "literal", value: " and " },
{ type: "integer", value: "40" },
{ type: "literal", value: " " },
{ type: "unit", value: "seconds" }
]
Parcourez les parties pour appliquer un style personnalisé.
function StyledDuration({ duration }) {
const parts = new Intl.DurationFormat('en', { style: 'long' }).formatToParts(duration);
return parts.map((part, i) => {
if (part.type === 'integer') {
return <strong key={i}>{part.value}</strong>;
}
return <span key={i}>{part.value}</span>;
});
}
Réutiliser les instances de formateur pour les performances
Créer un nouveau formateur pour chaque durée ajoute une surcharge. Créez le formateur une fois et réutilisez-le.
const formatter = new Intl.DurationFormat('en', { style: 'short' });
const durations = [
{ hours: 1, minutes: 30 },
{ hours: 2, minutes: 15 },
{ hours: 0, minutes: 45 }
];
durations.map(d => formatter.format(d));
// ["1 hr and 30 min", "2 hr and 15 min", "45 min"]
Ce modèle améliore les performances lors du formatage de nombreuses durées dans des boucles ou des rendus.
Migrer depuis la construction manuelle de chaînes
Remplacez la concaténation manuelle de chaînes par l'API. Cela réduit le code et ajoute la localisation.
Avant :
function formatDuration(hours, minutes) {
if (hours > 0 && minutes > 0) {
return `${hours}h ${minutes}m`;
} else if (hours > 0) {
return `${hours}h`;
} else {
return `${minutes}m`;
}
}
Après :
function formatDuration(hours, minutes, locale) {
const duration = {};
if (hours > 0) duration.hours = hours;
if (minutes > 0) duration.minutes = minutes;
return new Intl.DurationFormat(locale, { style: 'narrow' }).format(duration);
}
La version API gère automatiquement toute la logique conditionnelle et prend en charge plusieurs langues.
Migrer depuis les bibliothèques
Les bibliothèques comme Moment.js et date-fns fournissent le formatage de durée mais augmentent la taille du bundle. L'API native élimine cette dépendance.
Remplacez le formatage de durée Moment.js :
// Before: Moment.js
const duration = moment.duration(6400, 'seconds');
const formatted = duration.hours() + 'h ' + duration.minutes() + 'm';
// After: Intl.DurationFormat
const duration = {
hours: Math.floor(6400 / 3600),
minutes: Math.floor((6400 % 3600) / 60)
};
new Intl.DurationFormat('en', { style: 'narrow' }).format(duration);
Remplacez le formatage de durée date-fns :
// Before: date-fns
import { formatDuration, intervalToDuration } from 'date-fns';
const duration = intervalToDuration({ start: 0, end: 6400000 });
const formatted = formatDuration(duration);
// After: Intl.DurationFormat
const ms = 6400000;
const duration = {
hours: Math.floor(ms / 3600000),
minutes: Math.floor((ms % 3600000) / 60000),
seconds: Math.floor((ms % 60000) / 1000)
};
new Intl.DurationFormat('en', { style: 'long' }).format(duration);
L'API native fournit la même fonctionnalité sans dépendances.
Support des navigateurs et polyfills
L'API Intl.DurationFormat est devenue Baseline en mars 2025. Elle fonctionne dans les dernières versions de Chrome, Edge, Firefox et Safari.
Vérifiez le support avant utilisation :
if (typeof Intl.DurationFormat !== 'undefined') {
const formatter = new Intl.DurationFormat('en', { style: 'short' });
return formatter.format(duration);
} else {
// Fallback for older browsers
return `${duration.hours}h ${duration.minutes}m`;
}
Pour une prise en charge plus large, utilisez un polyfill. Le projet FormatJS fournit @formatjs/intl-durationformat.
npm install @formatjs/intl-durationformat
Importez et ajoutez le polyfill si nécessaire :
if (!Intl.DurationFormat) {
await import('@formatjs/intl-durationformat/polyfill');
}
Le polyfill ajoute environ 15 Ko compressés. Chargez-le de manière conditionnelle pour éviter toute surcharge pour les navigateurs modernes.
Quand utiliser DurationFormat
Utilisez Intl.DurationFormat pour afficher le temps écoulé, le temps restant ou les mesures de durée. Cela inclut les lecteurs vidéo, les minuteurs, les comptes à rebours, les applications de suivi, les réservations de voyage et l'affichage de la durée des sessions.
Ne l'utilisez pas pour les dates, les heures ou les horodatages. Utilisez Intl.DateTimeFormat pour ceux-ci. Ne l'utilisez pas pour les expressions de temps relatif comme « il y a 2 heures ». Utilisez Intl.RelativeTimeFormat pour celles-ci.
L'API formate les durées, pas les calculs de temps. Vous devez calculer vous-même les valeurs de durée à partir de dates, d'horodatages ou d'autres sources. Le formateur gère uniquement l'affichage.