angular-dynamic-locale icon indicating copy to clipboard operation
angular-dynamic-locale copied to clipboard

Sync loading with Webpack

Open andreialecu opened this issue 9 years ago • 7 comments

I was looking into preloading a few locales so that async loading wouldn't be required (I'm using this in cordova so it wouldn't make much sense) and I came up with this:

  function getInjectedLocale() {
    var localInjector = angular.injector(['ngLocale']);
    return localInjector.get('$locale');
  }

  // put de-de language into cache
  require('angular-i18n/de-de');
  tmhDynamicLocaleCache.put('de-de', getInjectedLocale());

  // put en-gb language into cache
  require('angular-i18n/en-gb');
  tmhDynamicLocaleCache.put('en-gb', getInjectedLocale());

  // later on:
  tmhDynamicLocale.set('en-gb'); // or de-de

Seems to work very well, I'm leaving this here as a possible addition to the readme. A possible improvement might be to create a method in tmhDynamicLocale, like tmhDynamicLocale.cacheLastLoadedLocale('de-de') for instance, which can be called right after the require.

andreialecu avatar Dec 11 '15 20:12 andreialecu

@andreialecu thanks!

lgalfaso avatar Dec 11 '15 20:12 lgalfaso

@andreialecu This is something I need as well, but could you please elaborate further on how to achieve this or point me to a working plunker / ? I am sure I might wrap my head around it, but if you have any clues (where (files), when (phase) to use your above code), that would be helpful...

ChristianUlbrich avatar Mar 28 '16 10:03 ChristianUlbrich

@ChristianUlbrich The above code assumes you're using webpack.

You can just put it inside a .run call like this:

app.run(function(tmhDynamicLocale, tmhDynamicLocaleCache) {
  ...
});

If you're not using webpack, then I'm not sure how this helps you or why you would need it. Care to elaborate?

andreialecu avatar Mar 28 '16 11:03 andreialecu

@andreialecu Thanks! That's all I needed. Sorry, for using "elaborate" :) Actually I can only guess, why your approach works, but do I care? No! Works like a charm.

And yes we are using webpack and I need to pre-bundle the available locales, just like you wanted to.

If I were to wish for something, I think that the localeCache should be synchronously set by a provider.

ChristianUlbrich avatar Mar 29 '16 14:03 ChristianUlbrich

You're welcome! English is not my first language but I don't think there's anything wrong with the word "elaborate", I just wasn't sure what you were asking, that is all. :)

andreialecu avatar Mar 29 '16 14:03 andreialecu

This chunk of code was helpful to get started but I took another path with webpack to tackle async issues. It's using ui-router.

In webpack make a bare copy of the locals so they are packaged but not (yet) imported.

var copyStatic = new CopyWebpackPlugin([
  {from: './node_modules/angular-i18n/angular-locale_de-de.js', to: path.resolve(APP_ROOT, appConfig.buildDir + '/i18n')},
  {from: './node_modules/angular-i18n/angular-locale_en-gb.js', to: path.resolve(APP_ROOT, appConfig.buildDir + '/i18n')},
]);

Set the path to the locales in the angular config.

tmhDynamicLocaleProvider.localeLocationPattern('i18n/angular-locale_{{locale}}.js');

Finally created a ui-router hook to make sure that the locale is always set before your logic starts executing.

$transitionsProvider.onBefore({}, setLocale, { priority: 20 });
function setLocale(transition) {
  const tmhDynamicLocale = transition.injector().get('tmhDynamicLocale');
  return tmhDynamicLocale.set('fr')
    .catch((err) => {
      console.warn('Error setting locale. Using default locale.', err);
    });
}

mehl321 avatar Feb 01 '17 17:02 mehl321

Here is how I did it with dynamic imports:

    let inject = (lang) => tmhDynamicLocaleCache.put(lang, angular.injector(['ngLocale']).get('$locale'));

    $q.all([
        System.import('angular-i18n/angular-locale_de')
            .then(() => inject('de')),
        System.import('angular-i18n/angular-locale_en')
            .then(() => inject('en')),
        System.import('angular-i18n/angular-locale_es')
            .then(() => inject('es')),
        System.import('angular-i18n/angular-locale_fr')
            .then(() => inject('fr')),
        System.import('angular-i18n/angular-locale_pl')
            .then(() => inject('pl')),
        System.import('angular-i18n/angular-locale_pt')
            .then(() => inject('pt'))
    ]).then(() => tmhDynamicLocale.set('en'));

reda-alaoui avatar May 27 '17 09:05 reda-alaoui