AngularJS - Get List of All Registered Services?

Can I get a list of all registered directives, services, controllers, etc. at runtime . . . ?


Solution 1:

You can get a list of the providers (ie services/directives/controllers/factories/etc) for each module, although the list is kind of cryptic.

Say you have the following:

var mod = angular.module('myModule', []);
mod.factory('fact1', function($dependency1, $dependency2){ ... });
mod.service('serv1', function($dependency3, $dependency4){ ... });
mod.controller('ctrl1', function($dependency2, $dependency3){ ... });
mod.factory('fact2', function($dependency1, $dependency4){ ... });
...

Then the mod variable will contain an attribute called mod._invokeQueue that will contain an array of all the providers that are part of that module. The _invokeQueue will look something like this:

[
    ['$provide', 'factory', Arguments['fact1', ['$dependency1', '$dependency2', function(){}],
    ['$provide', 'service', Arguments['serv1', ['$dependency3', '$dependency4', function(){}],
    ['$provide', 'controller', Arguments['ctrl1', ['$dependency2', '$dependency3', function(){}],
    ['$provide', 'factory', Arguments['fact2', ['$dependency1', '$dependency4', function(){}]
    ...
]

So you can search through that mod._invokeQueue for each provider that it contains.

But that will only contain the list of providers for that specific module. If you want to get a list of all of the dependent modules, you will need to loop through the mod.requires array.

If the module has module-level dependencies, like so:

var mod = angular.module('myModule', ['otherModule1','otherModule2']);

Then the mod object will also have a mod.requires array that contains the names of those module dependencies, like so:

angular.forEach(mod.requires, function(requiredModuleName){
    // first get a reference to the required module by calling angular.module()
    var requiredMod = angular.module(requiredModuleName);
    // requiredMod will have its own ._invokeQueue
    // requiredMod._invokeQueue will look like the _invokeQueue from above
    ...
    // do something with the additional providers in _invokeQueue
});

Hope that helps.

Solution 2:

Try this:

angular.module('MyApp')['_invokeQueue'].forEach(function(value){ 
    console.log(value[1] + ": " + value[2][0]);
})

Solution 3:

Here's how you can get most services

Ie: constants, values, factories, services.

    function allServices(mod, r) {
      var inj = angular.element(document).injector().get;
      if (!r) r = {};
      angular.forEach(angular.module(mod).requires, function(m) {allServices(m,r)});
      angular.forEach(angular.module(mod)._invokeQueue, function(a) {
        try { r[a[2][0]] = inj(a[2][0]); } catch (e) {}
      });
      return r;
    };

    allMyServices = allServices('myApp');

Now when you type in the console allMyServices. you'll get an auto-complete list of them.


The function above can fail in certain situations where angular.element(document).injector() returns undefined. You can use the function below instead...


Alternate Method

    var inj;
    function allServices(mod, r) {
      if (!r) {
        r = {};
        inj = angular.element(document.querySelector('[ng-app]')).injector().get;
      }
      angular.forEach(angular.module(mod).requires, function(m) {allServices(m,r)});
      angular.forEach(angular.module(mod)._invokeQueue, function(a) {
        try { r[a[2][0]] = inj(a[2][0]); } catch (e) {}
      });
      return r;
    };

    allMyServices = allServices('myApp');

Now when you type in the console allMyServices. you'll get an auto-complete list of them.


Note: With either method, be sure to replace 'MyApp' with your module name.