doshprompt/angular-localization

Add support for preloading dictionaries

tolbahadi opened this issue · 9 comments

For small apps it will be better if they can bundle their dictionaries with the source code at build time (using grunt or gulp) and set them directly and synchronously when the app loads. Instead of having to make another trip to the server to get the dictionaries.

Something like this;

app.config(function (locale, $window) {
  locale.loadBundle('common', 'en-US', $window.__languages['en-US'].common);
  locale.loadBundle('common', 'fr-FR', $window.__languages['fr-FR'].common);
});

Thoughts?

Thanks

@tolbahadi let me think about this, the purpose of this library was to support async loading, but having said that, you are right, for smaller apps it might not be worth it.

I can consider adding a setDictionary method to locale that can be called at run time, does that make sense? It can then be populate by gulp/grunt as a .js file as part of your build process

Yes! That makes sense.

Thanks..

@doshprompt any chance you've made progress on this? in our small app, the lazy loading of the language files is noticeable when clicking around from screen to screen.

related to this, angularjs supports resolve whenever a controller loads, to ensure by the time controller is rendered, all necessary data is ready.

currently we can use locale service like this:

locale.ready('common').then(function () {
  //logic here
});

how about this:

.when('/Foo', {
            templateUrl: 'foo.html',
            controller: 'fooCtrl',
            resolve: {
                localeData: function () {
                    return locale.ready('common'); //HERE
                }
            }
        })

and then, use it like this:

myApp.controller('fooCtrl', function (locale, localeData) {
  //no need to wait for locale ready any more
   $scope.message = locale.getString('demo.foo', {
        firstName: 'John',
        lastName: 'Smith'
    });
}

@unruledboy yes I think you can already do that? Is it not the case? If not let me know and I can debug and push a fix, that was always the intention.

yes, I just used that way, and it works like a charm.

however, still do not know for those controllers without using route, for example, those header/footer controllers, how to resolve. need to read more docs from angularjs.

this is a great project, thanks for the effort!

@unruledboy in those cases you will have to use the filter or the directive (recommended) as there won't be a way to load those if there is no route (and therefore no resolve)

got it, thanks mate, will let you know it goes.

@unruledboy You could also use $httpBackend to mock requests to certain files (in your case, the lang files for header, footer) like so:

angular.module('myExample')
  .run(function($httpBackend) {
    $httpBackend.whenGET('languages/en-US/common.lang.json')
      .respond(angular.toJson({
        helloWorld: "Hello World!"
      }));
    $httpBackend.whenGET('languages/fr-FR/common.lang.json')
      .respond(angular.toJson({
        helloWorld: "Bonjour le Monde"
      }));
    $httpBackend.whenGET(/.*/).passThrough();
  });

and then you could keep your .lang.json files intact but use some build-time tool to generate from those files a .js files that looks like the code snippet above. (None of these are ideal, I know, sorry)