I've been looking if it's possible for TSyringe to inject all classes that implements some interface (or extends from an abstract class), like this:
@injectable()
export interface IService {
foo(): void;
}
@injectable()
export class Service1 implements IService {
foo() { console.out("bar"); }
}
@injectable()
export class Service2 implements IService {
foo() { console.out("baz"); }
}
export class CollectorService {
constructor(
@inject('Service')
services: IService[]
) {
services.forEach(s => s.foo());
}
}
I just started using TSyringe a month ago, so I'm not familiar with all features and I don't know how to register this kind of dependency (if it's possible to achieve what I'm proposing) in the DI container.
I'm trying to mimic Spring @Autowire
annotation.
I couldn't get the registry
per class to work as in Aníbal Deboni Neto asnwer, but using an proxy class to place all the registries worked for me. I also used a Symbol
so that I don't have any magic strings.
interface IBar {}
@injectable()
class Foo implements IBar {}
@injectable()
class Baz implements IBar {}
@registry([
{token: Bar.token, useToken: Foo},
{token: Bar.token, useToken: Baz}
])
abstract class Bar {
static readonly token = Symbol("IBar");
}
@injectable()
class User{
constructor(@injectAll(Bar.token) private bars: IBar[]) {
}
}
const bars: IBar[] = container.resolveAll<IBar>(Bar.token);
const user: User = container.resolve(User);