Zum Hauptinhalt springen

Kernkomponente FormatJS Intl

Inoffizielle Beta-Übersetzung

Diese Seite wurde von PageTurner AI übersetzt (Beta). Nicht offiziell vom Projekt unterstützt. Fehler gefunden? Problem melden →

Diese Bibliothek enthält die Kern-Intl-API, die von react-intl verwendet wird.

Installation

npm i -S @formatjs/intl

Das intl-Objekt

Das Herzstück von @formatjs/intl ist das intl-Objekt (vom Typ IntlShape), das als Instanz einen Cache für alle Intl.*-APIs, Konfigurationen, kompilierten Nachrichten etc. speichert. Die Lebensdauer des intl-Objekts ist typischerweise an das locale und die Liste der enthaltenen messages gebunden. Das bedeutet, dass bei einem Wechsel des locale dieses Objekt neu erstellt werden sollte.

Tipp

Das intl-Objekt sollte aus Performance-Gründen möglichst wiederverwendet werden.

createIntl

Ermöglicht die Erstellung eines IntlShape-Objekts, das alle format*-Methoden enthält. Beispiel:

import {createIntl, createIntlCache} from '@formatjs/intl'

// This is optional but highly recommended
// since it prevents memory leak
const cache = createIntlCache()

const intl = createIntl(
{
locale: 'fr-FR',
messages: {},
},
cache
)

// Call imperatively
intl.formatNumber(20)

createIntlCache

Erstellt eine Cache-Instanz für die globale Nutzung über alle Locales hinweg. Dies memoisiert zuvor erstellte Intl.*-Konstruktoren für bessere Performance und ist lediglich ein In-Memory-Cache.

IntlShape

interface IntlConfig {
locale: string
timeZone?: string
fallbackOnEmptyString?: boolean
formats: CustomFormats
messages: Record<string, string> | Record<string, MessageFormatElement[]>
defaultLocale: string
defaultRichTextElements?: Record<string, FormatXMLElementFn<React.ReactNode>>
defaultFormats: CustomFormats
onError(err: string): void
onWarn(warning: string): void
}

interface IntlFormatters {
formatDate(value: number | Date | string, opts?: FormatDateOptions): string
formatTime(value: number | Date | string, opts?: FormatDateOptions): string
formatDateToParts(
value: number | Date | string,
opts?: FormatDateOptions
): Intl.DateTimeFormatPart[]
formatTimeToParts(
value: number | Date | string,
opts?: FormatDateOptions
): Intl.DateTimeFormatPart[]
formatRelativeTime(
value: number,
unit?: FormattableUnit,
opts?: FormatRelativeTimeOptions
): string
formatNumber(value: number, opts?: FormatNumberOptions): string
formatNumberToParts(
value: number,
opts?: FormatNumberOptions
): Intl.NumberFormatPart[]
formatPlural(
value: number | string,
opts?: FormatPluralOptions
): ReturnType<Intl.PluralRules['select']>
formatMessage(
descriptor: MessageDescriptor,
values?: Record<string, PrimitiveType | FormatXMLElementFn<string, string>>
): string
formatMessage(
descriptor: MessageDescriptor,
values?: Record<string, PrimitiveType | T | FormatXMLElementFn<T, R>>
): R
formatList(values: Iterable<string>, opts?: FormatListOptions): string
formatList(
values: Iterable<string | T>,
opts?: FormatListOptions
): T | string | Array<string | T>
formatListToParts(
values: Iterable<string | T>,
opts?: FormatListOptions
): Part[]
formatDisplayName(
value: string,
opts?: FormatDisplayNameOptions
): string | undefined
}

type IntlShape = IntlConfig & IntlFormatters

Die obige Definition zeigt, wie das intl-Objekt aufgebaut ist. Es besteht aus zwei Teilen:

  • IntlConfig: Die Intl-Metadaten, die als Props an das übergeordnete <IntlProvider>-Element übergeben werden.

  • IntlFormatters: Die imperative Formatierungs-API, wie unten beschrieben.

locale, formats und messages

Das aktuelle Locale des Benutzers und in welchem die App gerendert werden soll. defaultLocale und defaultFormats dienen als Fallback oder während der Entwicklung und repräsentieren die Standardeinstellungen der App. Beachten Sie, dass es kein defaultMessages gibt, da jeder Nachrichtendeskriptor ein defaultMessage bereitstellt.

defaultLocale und defaultFormats

Standard-Locale und -Formate für den Fall, dass eine Nachricht nicht übersetzt ist (fehlt in messages). defaultLocale sollte das Locale sein, in dem die defaultMessages deklariert sind, um Satzkohärenz in einem Locale zu gewährleisten. Ohne defaultLocale oder bei falscher Konfiguration kann es vorkommen, dass ein Satz auf Englisch ist, aber eingebettete Datums-/Zeitangaben auf Spanisch erscheinen.

onError

Ermöglicht die Bereitstellung eines benutzerdefinierten Fehlerhandlers. Standardmäßig werden Fehlermeldungen via console.error protokolliert, sofern NODE_ENV nicht auf production gesetzt ist.

defaultRichTextElements

Eine Zuordnung von Tags zu Rich-Text-Formatierungsfunktionen. Dient der zentralisierten Formatierung gängiger Tags wie <b>, <p> oder der Durchsetzung von Design-Systemen im Codebase (z.B. standardisierte <a> oder <button>). Siehe https://github.com/formatjs/formatjs/issues/1752 für weitere Details.

fallbackOnEmptyString

Standardwert ist true.

Diese boolesche Option ist nützlich, wenn Sie für bestimmte Locales bewusst leere Werte via Leerzeichen bereitstellen möchten. Wenn fallbackOnEmptyString false ist, werden Leerzeichen zurückgegeben statt den Fallback-Prozess auszulösen. Dieses Verhalten ermöglicht das "Überspringen" von Inhalten in spezifischen Locales.

Siehe dieses Issue für weitere Details.

formatDate

function formatDate(
value: number | Date,
options?: Intl.DateTimeFormatOptions & {format?: string}
): string

Diese Funktion gibt eine formatierte Datumszeichenkette zurück. Erwartet einen als Datum parsbaren value (d.h. isFinite(new Date(value)) ist wahr) und akzeptiert options, die DateTimeFormatOptions entsprechen.

Live Editor
intl.formatDate(Date.now(), {
  year: 'numeric',
  month: 'numeric',
  day: 'numeric',
})
Result

formatTime

function formatTime(
value: number | Date,
options?: Intl.DateTimeFormatOptions & {format?: string}
): string

Diese Funktion gibt ebenfalls eine formatierte Datumszeichenkette zurück, unterscheidet sich jedoch von formatDate durch folgende Standardoptionen:

{
hour: 'numeric',
minute: 'numeric',
}

Erwartet einen als Datum parsbaren value (d.h. isFinite(new Date(value)) ist wahr) und akzeptiert options, die DateTimeFormatOptions entsprechen.

Live Editor
intl.formatTime(Date.now()) // "4:03 PM"
Result

formatRelativeTime

Browser-Unterstützung

Dies erfordert Intl.RelativeTimeFormat, das nur eingeschränkte Browserunterstützung bietet. Verwenden Sie unser Polyfill, wenn Sie diese unterstützen möchten.

type Unit =
| 'second'
| 'minute'
| 'hour'
| 'day'
| 'week'
| 'month'
| 'quarter'
| 'year'

type RelativeTimeFormatOptions = {
numeric?: 'always' | 'auto'
style?: 'long' | 'short' | 'narrow'
}

function formatRelativeTime(
value: number,
unit: Unit,
options?: Intl.RelativeTimeFormatOptions & {
format?: string
}
): string

Gibt eine formatierte relative Zeitzeichenkette zurück (z.B. "vor 1 Stunde"). Erwartet einen numerischen value, eine unit und options, die Intl.RelativeTimeFormatOptions entsprechen.

Live Editor
intl.formatRelativeTime(0)
Result
Live Editor
intl.formatRelativeTime(-24, 'hour', {style: 'narrow'})
Result

formatNumber

Verwendet Optionen von Intl.NumberFormat.

function formatNumber(
value: number,
options?: Intl.NumberFormatOptions & {format?: string}
): string

Gibt eine formatierte Zahlenzeichenkette zurück. Erwartet einen als Zahl parsbaren value und akzeptiert options, die NumberFormatOptions entsprechen.

Live Editor
intl.formatNumber(1000, {style: 'currency', currency: 'USD'})
Result

Zahlenformatierung mit unit

Dies ist Teil von ES2020 NumberFormat. Wir bieten ein Polyfill hier an, und die Typen von @formatjs/intl erlauben Nutzern die Verwendung einer sanktionierten Einheit:

Live Editor
intl.formatNumber(1000, {
  style: 'unit',
  unit: 'kilobyte',
  unitDisplay: 'narrow',
})
Result
Live Editor
intl.formatNumber(1000, {
  unit: 'fahrenheit',
  unitDisplay: 'long',
  style: 'unit',
})
Result

formatPlural

type PluralFormatOptions = {
type?: 'cardinal' | 'ordinal' = 'cardinal'
}

function formatPlural(
value: number,
options?: Intl.PluralFormatOptions
): 'zero' | 'one' | 'two' | 'few' | 'many' | 'other'

Gibt eine Pluralkategoriezeichenkette zurück: "zero", "one", "two", "few", "many" oder "other". Erwartet einen als Zahl parsbaren value und akzeptiert options, die PluralFormatOptions entsprechen.

Niedrige Abstraktionsebene – die Ausgabe kann in einer switch-Anweisung verwendet werden, um spezifische Anzeigetexte auszuwählen.

Live Editor
intl.formatPlural(1)
Result
Live Editor
intl.formatPlural(3, {style: 'ordinal'})
Result
Live Editor
intl.formatPlural(4, {style: 'ordinal'})
Result
Mehrsprachigkeit

Nur für Apps mit einer Sprache geeignet. Für mehrsprachige Apps stattdessen formatMessage verwenden.

formatList

Browser-Unterstützung

Dies erfordert Intl.ListFormat, das nur eingeschränkte Browserunterstützung bietet. Verwenden Sie unser Polyfill, wenn Sie diese unterstützen möchten.

type ListFormatOptions = {
type?: 'disjunction' | 'conjunction' | 'unit'
style?: 'long' | 'short' | 'narrow'
}

function formatList(
elements: Iterable<string | React.ReactNode>,
options?: Intl.ListFormatOptions
): string | React.ReactNode[]

Diese Funktion ermöglicht die i18n-sichere Verkettung von Listen. Beispiel bei en-Locale:

Live Editor
intl.formatList(['Me', 'myself', 'I'], {type: 'conjunction'})
Result
Live Editor
intl.formatList(['5 hours', '3 minutes'], {type: 'unit'})
Result

formatDisplayName

Browser-Unterstützung

Dies erfordert Intl.DisplayNames, das nur eingeschränkte Browserunterstützung bietet. Verwenden Sie unser Polyfill, wenn Sie diese unterstützen möchten.

type FormatDisplayNameOptions = {
style?: 'narrow' | 'short' | 'long'
type?: 'language' | 'region' | 'script' | 'currency'
fallback?: 'code' | 'none'
}

function formatDisplayName(
value: string | number | Record<string, unknown>,
options: FormatDisplayNameOptions
): string | undefined

Anwendungsbeispiele:

Live Editor
intl.formatDisplayName('zh-Hans-SG', {type: 'language'})
Result
Live Editor
// ISO-15924 four letters script code to localized display name
intl.formatDisplayName('Deva', {type: 'script'})
Result
Live Editor
// ISO-4217 currency code to localized display name
intl.formatDisplayName('CNY', {type: 'currency'})
Result
Live Editor
// ISO-3166 two letters region code to localized display name
intl.formatDisplayName('UN', {type: 'region'})
Result

formatMessage

Nachrichtensyntax

Die String-/Nachrichtenformatierung ist eine Kernfunktion von React Intl und basiert auf ICU Message Formatting unter Verwendung der ICU Message Syntax. Diese Syntax ermöglicht die Definition, Übersetzung und Laufzeitformatierung einfacher bis komplexer Nachrichten.

Einfache Nachricht:

Hello, {name}

Komplexe Nachricht:

Hello, {name}, you have {itemCount, plural,
=0 {no items}
one {# item}
other {# items}
}.

Siehe: Die Nachrichtensyntax-Anleitung.

Nachrichtendeskriptor

React Intl verwendet Nachrichtendeskriptoren zur Definition von Standardnachrichten, die an formatMessage übergeben werden. Sie enthalten alle notwendigen Daten für Übersetzungen mit folgenden Eigenschaften:

  • id: Eindeutige, stabile Kennung der Nachricht

  • description: Kontextinformation für Übersetzer zur Verwendung in der UI

  • defaultMessage: Standardnachricht (üblicherweise auf Englisch)

type MessageDescriptor = {
id: string
defaultMessage?: string
description?: string | object
}
Message Descriptor extrahieren

Sie können Inline-deklarierte Nachrichten aus Quellcode-Dateien mit unserem CLI extrahieren.

Fallbacks bei der Nachrichtenformatierung

Die Nachrichtenformatierungs-APIs gehen einen Schritt weiter, um Fallbacks für häufige Fehlersituationen bereitzustellen; mindestens sollte immer ein nicht-leerer String zurückgegeben werden. Hier ist der Fallback-Algorithmus für die Nachrichtenformatierung:

  1. Formatierung der übersetzten Nachricht via id aus <IntlProvider>

  2. Fallback: defaultMessage formatieren.

  3. Fallback auf Originaltext der übersetzten Nachricht via id

  4. Fallback auf Originaltext von defaultMessage

  5. Fallback: Literale Nachricht id ausgeben.

"Originaltext" bezeichnet hier die unveränderte Vorlage ohne Substitutionen.

Verwendung

type MessageFormatPrimitiveValue = string | number | boolean | null | undefined
function formatMessage(
descriptor: MessageDescriptor,
values?: Record<string, MessageFormatPrimitiveValue>
): string
function formatMessage(
descriptor: MessageDescriptor,
values?: Record<
string,
MessageFormatPrimitiveValue | React.ReactElement | FormatXMLElementFn
>
): string | React.ReactNode[]

Diese Funktion formatiert Nachrichtenstrings. Erwartet wird ein MessageDescriptor mit mindestens id und ein values-Objekt zur Platzhalterfüllung.

Wenn eine übersetzte Nachricht mit der id via messages-Prop an den <IntlProvider> übergeben wurde, wird diese formatiert, andernfalls wird auf die Formatierung von defaultMessage zurückgegriffen. Details siehe Formatierungsfallbacks.

Live Editor
function () {
  const messages = defineMessages({
    greeting: {
      id: 'app.greeting',
      defaultMessage: 'Hello, {name}!',
      description: 'Greeting to welcome the user to the app',
    },
  })

  return intl.formatMessage(messages.greeting, {name: 'Eric'})
}
Result

mit ReactElement

Live Editor
function () {
  const messages = defineMessages({
    greeting: {
      id: 'app.greeting',
      defaultMessage: 'Hello, {name}!',
      description: 'Greeting to welcome the user to the app',
    },
  })

  return intl.formatMessage(messages.greeting, {name: <b>Eric</b>})
}
Result

mit Rich-Text-Formatierung

Live Editor
function () {
  const messages = defineMessages({
    greeting: {
      id: 'app.greeting',
      defaultMessage: 'Hello, <bold>{name}</bold>!',
      description: 'Greeting to welcome the user to the app',
    },
  })

  return intl.formatMessage(messages.greeting, {
    name: 'Eric',
    bold: str => <b>{str}</b>,
  })
}
Result

Die Nachricht wurde mittels defineMessages für Extraktion via babel-plugin-formatjs definiert, ist aber ohne Babel-Plugin optional.

Einfache Nachrichten

Nachrichten ohne Platzhalter sind zulässig und stellen den häufigsten Typ dar.

defineMessages/defineMessage

interface MessageDescriptor {
id?: string
description?: string | object
defaultMessage?: string
}

function defineMessages(
messageDescriptors: Record<string, MessageDescriptor>
): Record<string, MessageDescriptor>

function defineMessage(messageDescriptor: MessageDescriptor): MessageDescriptor

Diese Funktionen werden vom @formatjs/intl-Paket exportiert und dienen als Hook für unser CLI sowie Babel/TS-Plugins bei der Kompilierung von Standardnachrichten in JavaScript-Quelldateien. Die Funktion gibt lediglich das übergebene Message Descriptor Map-Objekt zurück.

import {defineMessages, defineMessage} from '@formatjs/intl'

const messages = defineMessages({
greeting: {
id: 'app.home.greeting',
description: 'Message to greet the user.',
defaultMessage: 'Hello, {name}!',
},
})

const msg = defineMessage({
id: 'single',
defaultMessage: 'single message',
description: 'header',
})