Reputation: 307
I am struggling to find a way to inject a service into an class object in angular2.
* NOTE: This is not a component, just a class. *
export class Product {
id: number;
name: string;
manufacturer: string;
constructor(product: any) {
this.id = product.id;
this.name = product.name;
this.manufacturer = product.manufacturer;
}
The only solution I have come up with is to pass the service reference to the constructor whenever I create a new product... ie: instead of new Product(product)
I would do new Product(product, productService)
. This seems tedious and error prone. I would rather import the reference from the class and not messy up the constructor.
I have tried the ReflectiveInjector:
let injector = ReflectiveInjector.resolveAndCreate([ProductService]);
this.productService = injector.get(ProductService);
However, this creates an error No provider for Http! (ProductService -> Http) at NoProviderError.BaseError [as constructor]
(Also I'm pretty sure this creates a new productService when I simple want to reference my singleton that is instantiated at the app level).
If anyone knows of a working solution I would be glad to hear it. For now i will pass the reference through the constructor.
Thanks
Upvotes: 6
Views: 6438
Reputation: 266
I was struggling with a similar issue, and what I ended up doing, was making the service a singleton as well as an Angular injectable.
This way you can inject via DI into Angular classes and call the static getInstance()
method to get the singleton instance of the class.
Something like this:
import {Injectable} from "@angular/core";
@Injectable()
export class MyService {
static instance: MyService;
static getInstance() {
if (MyService.instance) {
return MyService.instance;
}
MyService.instance = new MyService();
return MyService.instance;
}
constructor() {
if (!MyService.instance) {
MyService.instance = this;
}
return MyService.instance;
}
}
Upvotes: 8
Reputation: 658057
There is no way to inject a service into a plain class. Angular DI only injects into components, directives, services, and pipes - only classes where DI creates the instance, because this is when injection happens.
To get Http
from a custom injector, you need to add to it's providers like shown in Inject Http manually in angular 2
or you pass a parent injector that provides them
// constructor of a class instantiated by Angulars DI
constructor(parentInjector:Injector){
let injector = ReflectiveInjector.resolveAndCreate([ProductService]);
this.productService = injector.get(ProductService, parentInjector);
}
See also https://angular.io/docs/ts/latest/api/core/index/ReflectiveInjector-class.html
Upvotes: 4