es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Jeringa: ¿Cómo cambiar un parámetro de un objeto inyectado?

Tengo una aplicación con varios componentes diferentes, cada componente tiene sus propias dependencias y estoy utilizando TSyringe para gestionar la inyección de dependencias. Uno de los componentes es un operador como este:

// myoperator.ts

@injectable()
export class MyOperator {
    constructor(
        private dependencyA: DependencyA,
        protected dependencyB: DependencyB,
        protected dependencyC: DependencyC,
        protected operationType: string
    ){
         // inicializar el operador, etc.
    }

    // ...
}

Es una clase que realiza una operación, depende de varias otras clases y tiene un único parámetro de tipo string que especifica la forma en la que operará.

En la aplicación principal estoy inicializando todos los diferentes componentes que utiliza la aplicación principal y necesito inicializar MyOperator con varios tipos de operación diferentes.

// mainapp.ts

@singleton()
export class MainApp {
    constructor(
        componentA: ComponentA,
        componentB: ComponentB,
        componentC: ComponentC,
        operatorWithOperationTypeFoo: MyOperator, // el operationType debería ser "foo"
        operatorWithOperationTypeBar: MyOperator, // el operationType debería ser "bar"
        operatorWithOperationTypeBaz: MyOperator // el operationType debería ser "baz"
    ) {
         // inicializar la aplicación principal, etc.
    }

    public start() {
    // iniciar la aplicación principal, etc.

    }
}

// main.ts

const app = container.resolve(MainApp);
app.start();

Mi pregunta es, ¿cómo puedo cambiar ese único parámetro operationType en la clase MyOperator al definirlos en los parámetros del constructor de MainApp?

Tags:  , ,

Answer

  1. Avatar for davy.ai

    Puedes utilizar el decorador @inject() de la librería tsyringe para especificar el valor del parámetro operationType para cada instancia de MyOperator.

    Primero, necesitas definir un token para el parámetro operationType:

    // myoperator.ts
    
    export const OPERATION_TYPE_TOKEN = Symbol('OperationTypeToken');
    

    Luego, en la clase MyOperator, puedes utilizar este token como una dependencia:

    // myoperator.ts
    
    @injectable()
    export class MyOperator {
        constructor(
            private dependencyA: DependencyA,
            protected dependencyB: DependencyB,
            protected dependencyC: DependencyC,
            @inject(OPERATION_TYPE_TOKEN) protected operationType: string
        ){
             // inicializar operador, etc.
        }
    
        // ...
    
    }
    

    Ahora, en el constructor de MainApp, puedes utilizar el método register() del objeto Container para vincular un valor al token OPERATION_TYPE_TOKEN para cada instancia de MyOperator:

    // mainapp.ts
    
    @singleton()
    export class MainApp {
        constructor(
            componentA: ComponentA,
            componentB: ComponentB,
            componentC: ComponentC,
            operatorWithOperationTypeFoo: MyOperator,
            operatorWithOperationTypeBar: MyOperator,
            operatorWithOperationTypeBaz: MyOperator,
            container: Container // <-- inyectar el contenedor
        ) {
            // registrar los tipos de operación
            container.register<string>(OPERATION_TYPE_TOKEN, { useValue: 'foo' }).resolve(operatorWithOperationTypeFoo);
            container.register<string>(OPERATION_TYPE_TOKEN, { useValue: 'bar' }).resolve(operatorWithOperationTypeBar);
            container.register<string>(OPERATION_TYPE_TOKEN, { useValue: 'baz' }).resolve(operatorWithOperationTypeBaz);
    
            // inicializar la aplicación principal, etc.
        }
    
        public start() {
            // iniciar la aplicación principal, etc.
        }
    }
    

    Ten en cuenta que necesitas inyectar el objeto Container en el constructor de MainApp para poder registrar los tipos de operación. Además, puedes utilizar cualquier valor para el token OPERATION_TYPE_TOKEN, pero debe ser único dentro del contenedor de tsyringe.

Comments are closed.