---
id: translations
sidebar_position: 5
title: Translation and i18n
---

import Diacritics from '../../assets/Diacritics.png';
import Localization1 from '../../assets/Localization1.png';
import Localization2 from '../../assets/Localization2.png';
import Transliteration from '../../assets/Transliteration.png';

The Stream Chat React component library uses the [`i18next`](https://www.npmjs.com/package/i18next) dependency to create a [`Streami18n`](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/Streami18n.ts)
class constructor that handles language translation of our UI components. The Stream Chat API also supports automatic translation of
chat messages, [learn more](https://getstream.io/chat/docs/react/translation/?language=javascript).

## Supported Languages

The library provides built-in translations for the following languages:

1. [English](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/en.json) (en) - default
2. [Dutch](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/nl.json) (nl)
3. [French](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/fr.json) (fr)
4. [German](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/de.json) (de)
5. [Hindi](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/hi.json) (hi)
6. [Italian](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/it.json) (it)
7. [Japanese](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/ja.json) (ja)
8. [Korean](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/ko.json) (ko)
9. [Portuguese](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/pt.json) (pt)
10. [Russian](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/ru.json) (ru)
11. [Spanish](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/es.json) (es)
12. [Turkish](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/tr.json) (tr)

If you wish to change the default language in your app without initiating an instance of `Streami18n`, pass the `defaultLanguage` prop
to the `Chat` component on load of your application. The below code snippet will change the default language from English to
Italian.

```tsx
const defaultLanguage = 'it';

<Chat client={client} defaultLanguage={defaultLanguage}>
  ...
</Chat>;
```

The following screenshots show the state of the UI components in the app before and after setting the `defaultLanguage` to Italian.

**Default language not specified:**

<img src={Localization1} alt='Localization1' width='700' />

**Default language set to Italian:**

<img src={Localization2} alt='Localization2' width='700' />

:::note
The `defaultLanguage` prop is only applicable as a fallback language. If the connected user's preferred browser language is supported
for translation, the component library will preferentially render the browser language. Meaning, if `defaultLanguage` was set to
Italian but the user's preferred browser language was Spanish, the component library would render Spanish.
:::

## Enable Localization

The library supports two different methods for manually setting the language of the connected user and automatically translates all
text built into the UI components. The simpler and less customizable way is to set the `language` value in the `connectUser` method on
mount of the chat application.

```tsx
client.connectUser({ id: userId, language: 'es' }, userToken);
```

:::caution
If [auto translation](https://getstream.io/chat/docs/react/translation/?language=javascript#automatic-translation) of messages is enabled
in the application, setting the `language` value on `connectUser` will result in the auto translation of all message text. If this behavior
is undesired, follow the steps below to create a translation instance.
:::

### Create a Streami18n Instance

Additionally, you can create a class instance of `Streami18n` and pass as a prop into the `Chat` component. The below
example changes the current user's language to Spanish.

```jsx
const i18nInstance = new Streami18n({ language: 'es' });

<Chat client={client} i18nInstance={i18nInstance}>
  ...
</Chat>;
```

### Override Default Translations

Taking it one step further, the below example shows how to override the default text values built into the components.

```jsx {3-5}
const i18nInstance = new Streami18n({
  language: 'es',
  translationsForLanguage: {
    'Nothing yet...': 'Nada!', // default is 'Nada aun...'
  },
});

<Chat client={client} i18nInstance={i18nInstance}>
  ...
</Chat>;
```

If you wish to completely override one of our language files, provide your custom translations via the `translationsForLanguage` key.
Your custom language file must include all of the keys of the [default file](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/es.json).

```tsx
import esUpdated from 'path/to/esUpdated.json';

const i18nInstance = new Streami18n({
  language: 'es',
  translationsForLanguage: esUpdated,
});

<Chat client={client} i18nInstance={i18nInstance}>
  ...
</Chat>;
```

If the language for the connected user is not manually set by passing a `Streami18n` object to the `Chat` component, the component library
detects the user's default browser language. If the component library has translation support for the detected browser language, either through
the languages provided or by a custom added language (described below), the connected user's language is automatically set to this value. If the browser language
is not supported for translation, the library defaults to English.

:::note
All [available translations](https://github.com/GetStream/stream-chat-react/tree/master/src/i18n) are found on GitHub and the
JSON objects can be imported from the library.

`import { esTranslations } from 'stream-chat-react';`
:::

### Overriding ARIA labels

ARIA labels that are used for interactive elements are also subject to localization. Translation keys for ARIA labels are prefixed by `aria/`:

```jsx
import { useTranslationContext } from 'stream-chat-react';

const Component = () => {
  const { t } = useTranslationContext();
  return (
    <button type='button' aria-label={t('aria/Send')}>
      📨
    </button>
  );
};
```

To override the default translations, add an `aria`-prefixed key to the `translationsForLanguage` object:

```jsx
const i18nInstance = new Streami18n({
  language: 'en',
  translationsForLanguage: {
    'aria/Send': 'Send Message',
  },
});

<Chat client={client} i18nInstance={i18nInstance}>
  {/* ... */}
</Chat>;
```

## Add a Language

In the following example, we will demonstrate how to add translation support for an additional language not currently supported
by the component library. We will add translations for Simplified Chinese, which uses language code `zh`, by following these
steps:

1. Create a JSON file in your project (ex: `zh.json` if creating a translation file for Simplified Chinese)
2. Copy the content of an existing [translation file](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/en.json)
3. Change the values to your desired translations
4. Register the translation file and set the new language
5. Pass as a prop to the `Chat` component

:::note
The `setLanguage` method on the class instance of `Streami18n` is asynchronous, so it's response needs to be
awaited before the language translations can be updated.
:::

We can initialize the instance dynamically:

```tsx
import zhTranslation from 'path/to/zh.json';

const i18nInstance = new Streami18n();

const App = () => {
  const [languageLoaded, setLanguageLoaded] = useState(false);

  useEffect(() => {
    const loadLanguage = async () => {
      i18nInstance.registerTranslation('zh', zhTranslations);
      await i18nInstance.setLanguage('zh');
      setLanguageLoaded(true);
    };

    loadLanguage();
  }, []);

  if (!languageLoaded) return null;

  return (
    <Chat client={client} i18nInstance={i18nInstance}>
      ...
    </Chat>
  );
};
```

Or we can have a pre-configured `Streami18n` instance:

```tsx
import zhTranslation from 'path/to/zh.json';

const i18nInstance = new Streami18n({
  language: 'zh',
  translationsForLanguage: zhTranslations,
  dayjsLocaleConfigForLanguage: {
    // see the next section about Datetime translations
    months: [...],
    monthsShort: [...],
    calendar: {
      sameDay: ...'
    }
  }
});

const App = () => {
  return (
    <Chat client={client} i18nInstance={i18nInstance}>
      ...
    </Chat>
  );
};
```

### Datetime translations

The SDK components use [`Dayjs`](https://day.js.org/en/) internally by default to format dates and times. It has [locale support](https://day.js.org/docs/en/i18n/i18n) being a lightweight alternative to `Momentjs` with the same modern API. `Dayjs` provides [locale config for plenty of languages](https://github.com/iamkun/dayjs/tree/dev/src/locale).

You can either provide the `Dayjs` locale config while registering language with `Streami18n` (either via constructor or `registerTranslation()`) or you can provide your own `Dayjs` or `Momentjs` instance to `Streami18n` constructor, which will be then used internally (using the language locale) in components.

:::note
The `dayjsLocaleConfigForLanguage` object is a union of configuration objects for [`Dayjs` calendar plugin](https://day.js.org/docs/en/plugin/calendar) and `Dayjs` locale configuration(examples are available in [`Dayjs` default locale configurations](https://github.com/iamkun/dayjs/tree/dev/src/locale))
:::

1. Via language registration

```js
const i18n = new Streami18n({
 language: 'nl',
 dayjsLocaleConfigForLanguage: {
   months: [...],
   monthsShort: [...],
   calendar: {
     sameDay: ...'
   }
 }
});
```

Similarly, you can add locale config for `Momentjs` while registering translation via `registerTranslation` function.

```js
const i18n = new Streami18n();

i18n.registerTranslation(
 'mr',
 {
   'Nothing yet...': 'काहीही नाही  ...',
   '{{ firstUser }} and {{ secondUser }} are typing...': '{{ firstUser }} आणि {{ secondUser }} टीपी करत आहेत ',
 },
 {
   months: [...],
   monthsShort: [...],
   calendar: {
     sameDay: ...'
   }
 }
);
```

2. Provide your own `Momentjs` object

```js
import 'moment/locale/nl';
import 'moment/locale/it';
// or if you want to include all locales
import 'moment/min/locales';

import Moment from moment

const i18n = new Streami18n({
 language: 'nl',
 DateTimeParser: Moment
})
```

3. Provide your own Dayjs object

```js
import Dayjs from 'dayjs';

import 'dayjs/locale/nl';
import 'dayjs/locale/it';
// or if you want to include all locales
import 'dayjs/min/locales';

const i18n = new Streami18n({
  language: 'nl',
  DateTimeParser: Dayjs,
});
```

If you would like to stick with english language for dates and times in Stream components, you can set `disableDateTimeTranslations` to true.

### Timezone location

To display date and time in different than machine's local timezone, provide the `timezone` parameter to the `Streami18n` constructor. The `timezone` value has to be a [valid timezone identifier string](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones). If no `timezone` parameter is provided, then the machine's local timezone is applied.

```ts
import { Streami18n } from 'stream-chat-react';

const streamI18n = new Streami18n({ timezone: 'Europe/Prague' });
```

If you are using `moment` as your datetime parser engine and want to start using timezone-located datetime strings, then we recommend to use `moment-timezone` instead of `moment` package. Moment Timezone will automatically load and extend the moment module, then return the modified instance. This will also prevent multiple versions of `moment` being installed in a project.

```ts
import type momentTimezone from 'moment-timezone';
import { Streami18n } from 'stream-chat-react';

const i18n = new Streami18n({
  DateTimeParser: momentTimezone,
  timezone: 'Europe/Prague',
});
```

### Translating Messages

Stream Chat provide the ability to run users' messages through automatic translation.
While machine translation is never perfect it can enable two users to communicate with
each other without speaking the same language. For more information, see the full guide
to [adding automatic translation](https://getstream.io/chat/docs/react/translation/?language=javascript).

## Diacritics and Transliteration

Searching for users when utilizing the '@' mentions command supports diacritics and, optionally, transliteration using [Transliterate](https://github.com/sindresorhus/transliterate). To add transliteration to your search functionality with the external Transliterate
library, use the `useMentionsTransliteration` prop in the `MessageInput`. This library is dynamically imported if the prop is true. Diacritics support is available by default.

<img src={Diacritics} alt='Diacritics' width='700' />

<img src={Transliteration} alt='Transliteration' width='700' />

## Streami18n API Reference

The `Streami18n` class wraps [`i18next`](https://www.npmjs.com/package/i18next) and provides a set of values and methods.

### Class Constructor Options

| Option                       | Description                                                                                                                                                          | Type     | Default                                         |
| ---------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -------- | ----------------------------------------------- |
| DateTimeParser               | custom date time parser                                                                                                                                              | function | Day.js                                          |
| dayjsLocaleConfigForLanguage | internal Day.js [config object](https://github.com/iamkun/dayjs/tree/dev/src/locale) and [calendar locale config object](https://day.js.org/docs/en/plugin/calendar) | object   | 'enConfig'                                      |
| debug                        | enables i18n debug mode                                                                                                                                              | boolean  | false                                           |
| disableDateTimeTranslations  | disables translation of date times                                                                                                                                   | boolean  | false                                           |
| language                     | connected user's language                                                                                                                                            | string   | 'en'                                            |
| logger                       | logs warnings/errors                                                                                                                                                 | function | () => {}                                        |
| parseMissingKeyHandler       | function executed, when a key is not found among the translations                                                                                                    | function | (key: string, defaultValue?: string) => string; |
| translationsForLanguage      | overrides existing component text                                                                                                                                    | object   | {}                                              |
| timezone                     | valid timezone identifier string (https://en.wikipedia.org/wiki/List_of_tz_database_time_zones)                                                                      | function | Day.js                                          |

#### parseMissingKeyHandler

The default implementation returns the default value provided to the translator function, for example the component below will display string `'hello'` if the key `'some-key'` is not found among the translations for a given language:

```tsx
import { useTranslationContext } from 'stream-chat-react';

const Component = () => {
  const { t } = useTranslationContext('useCommandTrigger');

  return <div>{t('some-key', { defaultValue: 'hello' })}</div>;
};
```

The custom handler may log missing key warnings to the console in the development environment:

```ts
import { Streami18n, Streami18nOptions } from 'stream-chat-react';

const parseMissingKeyHandler: Streami18nOptions['parseMissingKeyHandler'] = (
  key: string,
  defaultValue?: string,
) => {
  console.warn(`Streami18n: Missing translation for key: ${key}`);
  return defaultValue ?? key;
};

const i18nInstance = new Streami18n({ parseMissingKeyHandler });
```

### Class Instance Methods

#### getAvailableLanguages

Returns an array of language code strings corresponding to available languages.

```tsx
const availableLanguages = streami18n.getAvailableLanguages();
```

#### geti18Instance

Returns the instance of `i18next` used within the `Streami18n` instance.

```tsx
const i18nInstance = streami18n.geti18Instance();
```

#### getTranslations

Returns the current translation dictionaries for all languages.

```tsx
const translations = streami18n.getTranslations();
```

#### getTranslators

Asynchronous function that returns the current translator functions.

```tsx
const { t, tDateTimeParser } = await streami18n.getTranslators();
```

#### registerTranslation

Allows you to register a custom translation, which overrides an existing translation for the given language.
The third parameter, which is an optional Day.js locale, is structured the same as [dayjsLocaleConfigForLanguage](https://github.com/iamkun/dayjs/tree/dev/src/locale).

Review the [`enTranslations`](https://github.com/GetStream/stream-chat-react/blob/master/src/i18n/en.json) JSON file exported from `stream-chat-react` for a current list of translation keys.

```tsx
streami18n.registerTranslation('es', {
  'Nothing yet...': 'Nada!',
});
```

##### Parameters

| Name              | Type   | Required           |
| ----------------- | ------ | ------------------ |
| language          | string | :heavy_check_mark: |
| translation       | object | :heavy_check_mark: |
| customDayjsLocale | object |                    |

#### setLanguage

Asynchronous function that changes the current language and returns a new translation function.
If not initialized, `undefined` will be returned. If the language fails to update, the current translation function will be returned.

```tsx
const t = await streami18n.setLanguage('nl');
```

##### Parameters

| Name     | Type   | Required           |
| -------- | ------ | ------------------ |
| language | string | :heavy_check_mark: |
