Question : How to use typed-inject in sub package?

#69 · open · 3 comments

View on GitHub ↗

stevebeauge

Hello, I'm looking for a simple, type safe, IOC container and I found typed-inject. I'm only starting my journey, so I hope my question won't be obvious. I'm maintaining a large mono repository which contains several applications and a bunch of private packages. AFAIK, type safety come thanks to the `createInjector` typings which "stacks" the tokens and requirement for all injections (via the `inject` property). It works well in a single package application, because all injections are known. However, in a sub package, I don't have access to the actual app injector, because it's instantiated at the top level package. A concrete example in our case, is that we have multiple apps that have not the same authentication behavior (some are vite web apps, some are browser extension and some are MS Office addins), but we still want to share common component. We have a IHttpService interface, and multiple implementations that will take care of the specificities. In a shared component library, how can we get the actual service implementation ? Currently, we have one react context for each sort of service, but it's reaching a hard-to-maintain state compared to what an IOC container would provide. How can typed-inject could help ?

Comments

stevebeauge

As a previous IOC container, I used https://www.vrdmn.com/2019/03/using-service-scopes-to-decouple.html, which I cannot use anymore (it only works in the Microsoft SharePoint framework) Microsoft introduced in this container the concept of "ServiceKey", this is similar to what the token typed-inject supports, but the type is included in the ServiceKey. This way, I could query the service by the service key, and I will get the typed object directly (or fail if not present). Maybe we could achive something similar with typedinject ?

nicojs

Hi @stevebeauge, I'm here to help you on your journey. This use case is exactly what I'm using TypedInject for in StrykerJS. It consists of [packages](https://github.com/stryker-mutator/stryker-js/tree/master/packages) that all use typed-inject in one symphony of dependency injection. You can see a guide on what users can do to hook into typed inject here: https://stryker-mutator.io/docs/stryker-js/guides/create-a-plugin/#declaring-your-plugin You can follow these rough steps: 1. Create a shared package containing all shared types you want to use for dependency injection. (in our case, it is [`@stryker-mutator/api`](https://github.com/stryker-mutator/stryker-js/tree/master/packages/api). It should include the dependency injection contexts for your plugins (the stuff you want to allow to be injected inside your packages/plugins). 2. Bonus: Inside the shared package, create a helper function to declare plugins, like here: https://github.com/stryker-mutator/stryker-js/blob/master/packages/api/src/plugin/plugins.ts#L60 3. Export functions or classes that can be injected from the main package from your packages. If they want to participate in and enhance the dependency injection container, they can let the injector be injected and build from that, as described in the "declare your plugin" guide. 4. Import those things from the main package, create instances, etc. Did this help?

stevebeauge

Thanks for the help. I finally choose Brandi as ioc container. I like how tokens work. A service only has to know its actual dependencies token. No need to create a central list of tokens, which is against ioc design I think (not a big deal in a monorepo). Thx