InversifyJS icon indicating copy to clipboard operation
InversifyJS copied to clipboard

Binding inside a factory method

Open 1b0x opened this issue 3 years ago • 2 comments

Hello there, I have a question about this piece of code:

This is how my factory looks like. As you can see I'm binding/unbinding some classes inside this factory method.

export function SceneFactory(context: interfaces.Context) {
    return (key: string, scene: any) => {
        // Unbind the scene if it exists
        if (context.container.isBound(key)) {
            context.container.unbind(key);
        }
       
        // Bind the new scene class
        context.container.bind<IScene>(key).to(scene);
        return context.container.get<IScene>(key);
    };
}

I'm using it like that:

@injectable()
export class SceneManager implements ISceneManager {
    scenes: IScene[];

    constructor(
        @inject(ISceneFactory)
        protected sceneFactory: (key: string, scene: any) => IScene
    ) { }

    add(key: string, scene: IScene) {
        const sceneInstance = this.sceneFactory(key, scene);

        this.scenes.push(sceneInstance);
    }
}

class SceneA extends Scene {}
class SceneB extends Scene {}
sceneManager.add('sceneA', SceneA);
sceneManager.add('sceneB', SceneB);

So, the question is: Is it okay to bind/unbind classes in a factory method? Is it a good approach to do that?

1b0x avatar Dec 29 '21 22:12 1b0x

A better approach is to create a child container in the factory. This way, the original container isn't modified:

export function SceneFactory(context: interfaces.Context) {
    return (key: string, scene: any) => {
        const childContainer = context.container.createChild();
       
        // Bind the new scene class (since this is bound in the child container, it will override any existing binds)
        childContainer.bind<IScene>(key).to(scene);
        return childContainer.get<IScene>(key);
    };
}

More info here: https://github.com/inversify/InversifyJS/blob/master/wiki/hierarchical_di.md

kyle-johnson avatar Jan 17 '22 19:01 kyle-johnson

Thank you! I really appreciate it!

Is it good to create multiple child containers for other manager classes? Let's say that If I have Sound Manager (which has SoundFactory), should I create a new child container?

1b0x avatar Jan 17 '22 20:01 1b0x