简体   繁体   English

React-Router和React-Intl:是否有更好的方法来动态加载翻译的路由?

[英]React-Router and React-Intl: Is there a better way to load dynamically the translation's route?

I would to load dynamically the page's translation when its route change. 当页面的路线更改时,我将动态加载页面的翻译。 I done it using onEnter for each route. 我为每个路由使用了onEnter。

Is there a better way to implement this? 有没有更好的方法来实现这一目标? Can I avoid to use onEnter callback function for each route? 我可以避免对每个路由使用onEnter回调函数吗?

var  Root = React.createClass({       
    baseTranslations : {},

    getInitialState: function(){    
        return {
            lang: 'it',
            translations: null,
        };    
    },    

    componentWillMount: function() {    
        // load the common translation for all routes            
        this.setState({
            lang: this.getLocale().lang
        }); 
        this.loadTranslation("base");
    },

    onChangeRoute: function(nextState, replace){
        // load the specific route's translation
        this.loadTranslation(nextState.location.pathname);
    },

    getLocale: function(what){
        // return lang and user region (ex: it-IT)    
    },

    loadTranslation: function(route){    
        var lcl = route;    
        var mapping = {
            '/'     : 'home',
            'auth'  : 'dashboard'
        };

        if(route in mapping){
            lcl = mapping[route];
        }

        $.ajax({
            url: './locales/' + this.state.lang +'/' + lcl + '.json',
            dataType: "text",
        }).done(function(res) {

            if(lcl === "base"){
                this.baseTranslations = JSON.parse(res);
            }

            this.setState({
                translations: $.extend(true, this.baseTranslations, JSON.parse(res))
            });

        }.bind(this));

    },

    render: function() {
        var children;

        if (this.state.translations) {
            children = (
                <IntlProvider locale={this.state.lang} messages={this.state.translations}>
                    <Router history={browserHistory}>
                        <Route path="/" component={App}>
                            <IndexRoute component={Home}/>

                            <Route path="signup"  onEnter={this.onChangeRoute} getComponents={(location, cb) => {

                                 require.ensure([], (require) => {
                                        cb(null, require('./components/Signup.jsx'))
                                 }, "Signup")

                            }} />     

                            <Route path="*" component={NoMatch}/>
                        </Route>
                    </Router>
                </IntlProvider>
            );
        }

        return <div>{children}</div>;
    }
});


ReactDOM.render(
    <Root/>,
    document.getElementById('rct-cont')
);

As it's hard to say which Flux implementation you are going to use, I'll give you pseudocode and the key ideas here instead: 因为很难说出要使用哪种Flux实现,所以我在这里给您伪代码和关键思想:

i18nActions i18n动作

  • loadLanguage(language, route) - If a language for the given route hasn't been loaded, this triggers a query and then delegates the result to the store. loadLanguage(language, route) -如果尚未加载给定路线的语言,则会触发查询,然后将结果委托给商店。
  • You can implement a caching layer here ( localStorage ) if you want. 如果需要,可以在此处实现缓存层( localStorage )。 You need to be careful about invalidation, though. 但是,您需要小心无效。 You should have some way of telling that data has become stale and needs to be refreshed. 您应该以某种方式告诉您数据已经过时并且需要刷新。

i18nStore i18nStore

  • Maintains i18n state visible to the user. 保持用户可见的i18n状态。 You would consume this state from your UI level components. 您将通过UI级别组件使用此状态。

Root

  • Triggers loadLanguage at onEnter to update the store. onEnter上触发loadLanguage以更新商店。
  • Consumes the store and passes the data to IntlProvider . IntlProvider存储并将数据传递给IntlProvider Other components can dig the i18n data from that context. 其他组件可以从该上下文中挖掘i18n数据。

There are additional questions like what to do while the translations are loading. 还有其他问题,例如在加载翻译时该怎么做。 What should you show then? 那你应该显示什么? You can either defer displaying the UI to the user or you can use placeholders that will get replaced once the data has been received. 您可以推迟向用户显示UI,也可以使用占位符,一旦接收到数据,这些占位符将被替换。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM