How to Integrate React Intl
-
Merge
feature/react-intl
branch with git. Because react-intl integration is built on top offeature/redux
, you'll also get all the features. -
Adjust
INTL_REQUIRE_DESCRIPTIONS
constant intools/webpack.config.js
around line 17:const INTL_REQUIRE_DESCRIPTIONS = true;
When this boolean is set to true, the build will only succeed if a
description
is set for every message descriptor. -
Adjust
locales
settings insrc/config.js
:// default locale is the first one export const locales = ['en-GB', 'cs-CZ'];
-
Add locale support in
src/client.js
:import en from 'react-intl/locale-data/en'; import cs from 'react-intl/locale-data/cs'; ... [en, cs].forEach(addLocaleData);
-
Execute
npm run extractMessages
ornpm start
to strip out messages. Message files are created insrc/messages
directory. -
Edit
src/messages/*.json
files, change onlymessage
property. -
Execute
npm run build
, your translations should be copied tobuild/messages/
directory.
Just import the appropriate component from react-intl
-
For localizable text use
<FormattedMessage>
. -
You can also use it with the
defineMessages()
helper. -
For date and time:
<FormattedDate>
<FormattedTime>
<FormattedRelative>
-
For numbers and currencies:
<FormattedNumber>
<FormattedPlural>
-
If possible, do not use
<FormattedHTMLMessage>
, see how to use Rich Text Formatting with<FormattedMessage>
-
When you need an imperative formatting API, use the
injectIntl
High-Order Component.
import { defineMessages, FormattedMessage, injectIntl, intlShape } from 'react-intl';
const messages = defineMessages({
text: {
id: 'example.text',
defaultMessage: 'Example text',
description: 'Hi Pavel',
},
textTemplate: {
id: 'example.text.template',
defaultMessage: 'Example text template',
description: 'Hi {name}',
},
});
function Example(props) {
const text = props.intl.formatMessage(messages.textTemplate, { name: 'Pavel'});
return (
<div>
<FormattedMessage
id="example.text.inlineDefinition"
defaultMessage="Hi Pavel"
description="Example of usage without defineMessages"
/>
<FormattedMessage {...messages.text} />
<FormattedMessage
{...messages.textTemplate}
values={{
name: <b>Pavel</b>
}}
/>
</div>
);
}
Example.propTypes = {
intl: intlShape,
}
export default injectIntl(Example);
When running the development server, every source file is watched and parsed for changed messages.
Messages files are updated on the fly.
If a new definition is found, this definition is added to the end of every used src/messages/xx-XX.json
file so when commiting, new translations will be at the tail of file.
When an untranslated message is removed and its message
field is empty as well, the message will be deleted from all translation files. This is why the files
array is present.
When editiong a translation file, it should be copied to build/messages/
directory.
Intl documentation on MDN
- express-request-language – for more details how initial language negotiation works.