Search code examples
reactjsinternationalizationreact-intl

React-Intl Changing language does not change the translations


I have a small issue with React-Intl.

When the app is loaded, the translations are ok, but when I change the language, i18nConfig is changed but the translations are not updated.

I tried several things but I can't make it work.

App.js :

let i18nConfig = {
  locale: navigator.language.split(/[-_]/)[0],
  messages: getMessagesFromLang(navigator.language.split(/[-_]/)[0])
};

function getMessagesFromLang(lang) {
  switch (lang) {
    case "fr":
      return locale_fr;
    case "en":
      return locale_en;
    default:
      return locale_en;
  }
}

function onChangeLanguage(lang) {
  switch (lang) {
    case "fr": i18nConfig.messages = locale_fr; break;
    case "en": i18nConfig.messages = locale_en; break;
    default: i18nConfig.messages = locale_en; break;
  }
  i18nConfig.locale = lang;
}

function getCurrentLang() {
  return i18nConfig.locale;
}

export default function App() {
  return (
    <IntlProvider key={i18nConfig.locale} locale={i18nConfig.locale} messages={i18nConfig.messages}>
      <Content onChangeLanguage={onChangeLanguage} getCurrentLang={getCurrentLang} />
    </IntlProvider>
  );
}

Content.js :

const options = [{ value: "en", label: "English" },{ value: "fr", label: "Français" }];    
export default class Content extends React.Component {
  state = {
    selectedOption: null
  };

  handleChange = selectedOption => {
    this.setState({ selectedOption }, () =>
      console.log(`Option selected:`, this.state.selectedOption)
    );

    this.props.onChangeLanguage(selectedOption.value);
  };

  render() {
    return (
        <span><FormattedMessage id="app.content.link.rules" defaultMessage="Rules" /></span>
        <Select value={this.state.selectedOption} onChange={this.handleChange} options={options} />
    );
  }

Solution

  • Alright, so basically react isn't aware of that change, I made some changes so that react would know when its changed:

    export default function App() {
      const [lang, setLang] = React.useState(i18nConfig.locale) // keeps state of lang in App
      function onChangeLanguage(lang) {
        setLang(lang) // changes the lang when selec value changes
      }
      return (
        <IntlProvider key={lang} locale={lang} messages={getMessagesFromLang(lang)}>
          /* note how props are changed in order to stay updated */
          <Content onChangeLanguage={onChangeLanguage} getCurrentLang={getCurrentLang} />
        </IntlProvider>
      );
    }