node.jstypescriptdependency-injectioninversion-of-controlinversifyjs

How to initialise a class constructor using inversify which has other dependency


config.ts

export const bindings = new AsyncContainerModule(async (bind) => {
  await getDbConnection();
  await AppSubscribers;
  await Locators;
  await RouterClass;

  bind<AppSubscribers>(TYPES.AppSubscribers).to(AppSubscribers);
  bind<Locators>(TYPES.Locators).to(Locators);
  bind<IRepository>(TYPES.IRepository).to(Repository);

locator.ts

import { inject, injectable } from 'inversify';
import TYPES from '@shared/di/types/types';
import Locator from '../.Locators';
import { AfterTypeCreated } from './AfterTypeCreated';
import { logger } from '@shared/core/logger/logger';
export class AppSubscribers {
  constructor(
    @inject(TYPES.Locators)
    private locators: Locators
  ) {
    logger.info('SUBSCRIBER STARTED');
    new AfterDataCreated(this._locators);
  }
}

AppSubscriber needs to inject Locators which further injects Repo and other services.

I need to initialise app subscriber at the start of the application to add all the subscribers (observers) to the registry.


Solution

  • You probably need to use toDynamicValue, toFactory or toProvider. This is an example of toDynamicValue:

    container.bind<AppSubscribers>(TYPES.AppSubscribers).toDynamicValue((context) => {
        const locators = context.container.get(TYPES.Locators)
        const appSubscribers = new AppSubscribers();
        appSubscribers.initialize(); // Do something then call AfterDataCreated
        return appSubscribers;
    }).inSingletonScope();
    

    Take a look to the docs if this is not the perfect solution for you: