Creating Reusable Angular Providers

Last night at the AngularJS meetup, I talked with AJ and Joe Eames about how to make a reusable providers. They didn’t know exactly but I finally figured it out so I thought I’d share.

See this plunker demo.

Basically, I wanted to make a provider similar to ngResource that could simplify data resolution. I wanted to make it reusable so I put it into its own module.

It had to be a provider so that I could inject it into my main app’s .config() function. Services and factories cannot be injected into .config(). The Angular docs haveĀ a helpful table to explain that.

I needed the provider available in .config() so I could define my routes there and use the provider for the resolve objects.

So my provider needs to rely on $http and $route. The problem is that those are not defined at the .config() phase of a module. So I couldn’t define any provider functions that rely on those.

That is where the concept of $get comes in with providers. $get is processed by $injector.invoke() which allows $get to be a function with a dependency. Usually you see an array like this:

this.$get = ['$http', '$route', function($http, $route) { ...
    return this; // or any other object
}];

So in .config() my provider can’t do anything with $http or $route, but it can queue up tasks that will be handled by $http and $route later. In my case when a route was fired.

So when I write a controller that relies on ApiProvider I access it as Api instead of ApiProvider. And the controller will receive the object returned by this.$get() so the provider is guaranteed to have those dependencies by then.

That was probably hard to follow but hopefully that helps someone.

Leave a Reply

Your email address will not be published. Required fields are marked *