Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

How to inject a mix of runtime value and normal dependencies #193

Open
ericxinzhang opened this issue Mar 29, 2022 · 3 comments
Open

How to inject a mix of runtime value and normal dependencies #193

ericxinzhang opened this issue Mar 29, 2022 · 3 comments

Comments

@ericxinzhang
Copy link

I'd like to implement something like the following:

A orchestration service whose constructor accepts dependency services (can be injected using @inject decorator) and a runtime value:

@injectable()
class OrchestrationService {
  constructor(
    @inject(ServiceA) private dependencyA: ServiceA,
    @inject(ServiceA) private dependencyB: ServiceB,
    runtimeValue: string,
  ) {
    this.init(runtimeValue);
  }
}

And then I can somehow resolve the instance using the runtime value:

const orchestrationService = container.resolve<OrchestrationService>(runtimeValue);

I think I have two problems here:

  • How to resolve the instance based on a runtime value which cannot be registered beforehand.
  • How to inject the runtime value as one of the dependencies into the constructor.

Any suggestion / help will be really appreciated.

@megastels
Copy link

megastels commented Mar 31, 2022

you can register value in container

const SomeToken:InjectionToken<string> = "MyToken";

class Service{
  constructor(
    @inject(ServiceA) private dependencyA: ServiceA,
    @inject(ServiceA) private dependencyB: ServiceB,
    @inject(SomeToken) runtimeValue: string,
  )
}

container.registerInstance(SomeToken, "runtimeValue");
container.resolve(SomeToken); // runtimeValue
container.resolve(Service); // Service instance

https://github.com/microsoft/tsyringe#injecting-primitive-values-named-injection

@ericxinzhang
Copy link
Author

you can register value in container

const SomeToken:InjectionToken<string> = "MyToken";

class Service{
  constructor(
    @inject(ServiceA) private dependencyA: ServiceA,
    @inject(ServiceA) private dependencyB: ServiceB,
    @inject(SomeToken) runtimeValue: string,
  )
}

container.registerInstance(SomeToken, "runtimeValue");
container.resolve(SomeToken); // runtimeValue
container.resolve(Service); // Service instance

https://github.com/microsoft/tsyringe#injecting-primitive-values-named-injection

Thank you. Registering the runtime value at runtime just before resolving looks a bit weird but I reckon that's the best we can get.

@MeltingMosaic
Copy link
Collaborator

I think that @autoInjectable() allows for this kind of behavior (so you could do new OrchestrationService(runtimeParam)), but it wouldn't work with container.resolve().

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants