2

I'm trying to make a language switcher with a react-inlt and redux, but when i try to switch, then view is not rendered (< FormattedMessage> dosen't change), but redux work and locale in < IntlProvider> is changed. I haven't got any error in chrome console.

index.js

import React from 'react';
import ReactDOM from 'react-dom';
import { BrowserRouter, Route } from 'react-router-dom';
import { createStore, applyMiddleware } from 'redux'; 
import { Provider } from 'react-redux';
import thunk from 'redux-thunk'; 
import { addLocaleData } from 'react-intl';
import en from "react-intl/locale-data/en";
import pl from "react-intl/locale-data/pl";
import App from './App';
import { localeSet } from './actions/locale';
import rootReducer from './rootReducer';
...
...
addLocaleData([...en, ...pl]);
...

App.js

import React from 'react';
import { connect } from 'react-redux';
import { Route } from 'react-router-dom';
import { IntlProvider } from 'react-intl';
import messages from "./messages";
...

class App extends React.Component {

  render() {
    const { lang } = this.props;
    return (
      <IntlProvider locale={lang} messages={messages[lang]}>
        <div className="ui container">
          <TopNavigation />
        </div> 
      </IntlProvider>
    );
  }
}

function mapStateToProps(state) {
  return {
    lang: state.locale.lang
  }
}

export default connect(mapStateToProps)(App);

TopNavigation.js

import { FormattedMessage } from 'react-intl';
import { setLocale } from '../../actions/locale';
...

class TopNavigation extends React.Component {

    render() {

        return (

          <FormattedMessage id="nav.dashboard" defaultMessage="Dashboard" />

           <a role="button" onClick={() => this.props.setLocale("en")}>
             EN
           </a>{" "}
           |
           <a role="button" onClick={() => this.props.setLocale("pl")}>
             PL
           </a>

        );
    }
}

export default connect(null, { setLocale })(TopNavigation);

messages.js

export default {
    en: {
        'nav.dashboard' : "Dashboard"
    },
    pl: {
        'nav.dashboard' : "Panel Administracyjny"        
    }
}

actions/locale.js

import { LOCALE_SET } from "../types";

export const localeSet = lang => ({
  type: LOCALE_SET,
  lang
});

export const setLocale = lang => dispatch => {
  localStorage.alhubLang = lang;
  dispatch(localeSet(lang));
};

reducers/locale.js

import { LOCALE_SET } from "../types";

export default function locale(state ={ lang: "pl"}, action = {}) {
    switch(action.type) {
        case LOCALE_SET:
            return { lang: action.lang };
        default: 
            return state;
    }
}

types.js

export const LOCALE_SET = "LOCALE_SET";
JanuszO
  • 1,140
  • 12
  • 25
  • this looks like a similar issue as here: https://stackoverflow.com/questions/48006705/react-redux-componentwillreceiveprops-not-triggered-using-api-data The way you are accessing lang: state.locale.lang is similar to that user's nested state object. It triggered a re-render due to prop change when using a selector. You could also just define the prop as locale: state.locale and reference locale.lang when rendering IntlProvider. – brub Dec 28 '17 at 16:29
  • Did you add the function `injectIntl` on your components? – Damien Feb 21 '18 at 12:38

0 Answers0