AngularJS routeProvider with lazy loading to use values from WebAPI

871 Views Asked by At

I have a routeProvider that lazy loads various modules. I based my implementation on these two articles:

https://codereview.stackexchange.com/questions/42581/dynamic-routing-with-lazy-load-controllers http://ify.io/lazy-loading-in-angularjs/

It looks like this and works just fine:

myApp.config(function ($routeProvider) {

    $routeProvider.
    when('/', {
        templateUrl: 'templates/startpage.html',
        controller: 'startPageController',
    }).
    otherwise({
        resolve: {
            deps: function ($q, $rootScope, $location) {
                var deferred = $q.defer();
                var path = $location.path();
                var modulename = $location.path().split("/")[1];
                if (modulename != null) {
                    var scriptfile = '/Scripts/' + modulename + 'controller.js';
                    $script(scriptfile, function () {
                        $rootScope.$apply(function () {
                            //reprocess the route
                            $rootScope.$broadcast('$locationChangeSuccess', path, path);
                        });
                    });
                }
                return deferred.promise;
            }
        }
    });
});

Now I would like to check the modulename variable against values returned from a WebAPI. If the value of modulename is not in the returned array, I want the AngularJS to be redirected to the root (/).

I tried injecting $http in the deps function, but using it there causes it to be loaded several times. This is also not very efficient as the data should be retrieved once and then the result used. I cannot, however, find a way to retrieve the data from the WebAPI outside of the deps function (because $http can't be injected into the myApp.config).

How could I go about changing the myApp.config to get a list of approved "modules" from the WebAPI, then using this list to generate the routes?

1

There are 1 best solutions below

0
On BEST ANSWER

I ended up using something entirely different.

Because each route is defined in each module's controller, I use the WebAPI to get all the available module, then I lazy load that module's controller, which sets up the correct routes. I do this in the AngularJS app's run method, as that has access to the $http variable.

This is the result:

myApp.config(function ($routeProvider) {
    $routeProvider.
    when('/', {
        templateUrl: 'templates/startpage.html',
        controller: 'startPageController',
    }).
    otherwise({
        redirectTo: '/'
    });
});

myApp.run(function($http) {
    $http.get('/webapi/modules').success(function(data) {
        angular.forEach(data, function (module, key) {
            var scriptfile = '/Scripts/' + module + 'controller.js';
            $script(scriptfile, function () {});
        });
    });
});

Probably not the most elegant or sofisticated solution, but it works.