Contenedor DI / IoC vs fábricas: ¿Dónde configuro mi aplicación y por qué?

9

Estoy tratando de averiguar cuándo usar el registro DIC / IoC para configurar mi software y cuándo usar fábricas, junto con el razonamiento detrás de cada enfoque.


Estoy usando StructureMap como mi contenedor DI (DIC), que es fácil de configurar mediante registros. En el DIC, prácticamente todos los objetos registrados son estáticos en el sentido de que no necesito cambiar / intercambiar ninguna implementación / instancia en tiempo de ejecución, una vez que el DIC se configura y se configura en el DIC como singletons. Sin embargo, dado que mi software (SW) se ejecutará en diferentes dispositivos , necesito seleccionar un registro específico del dispositivo dependiendo del dispositivo en el que se ejecute mi SW para configurar el hardware en consecuencia.

Dado que la construcción de algunos de mis objetos requiere lectura en los archivos de configuración, estoy usando fábricas para devolver estas instancias al DIC, con el fin de separar la lectura de la configuración de la creación del objeto. Registré los captadores de fábrica en el DIC para los tipos de complementos correspondientes.

Ahora digamos que tengo un tipo de complemento IMotorcon tipos concretos Motor1y Motor2, que debería manejar una fábrica. Ahora hay dos formas en que puedo decidir cómo configurar mi dispositivo:

  1. Paso información sobre el dispositivo en el que se ejecuta el SW MotorFactoryy devuelve el motor correcto, ya sea Motor1o Motor2. En este caso, la lógica para decidir está dentro de la Fábrica.
  2. Configuro el DIC de acuerdo con el dispositivo en el que se está ejecutando y creo dos fábricas Motor1Factoryy Motor2Factory, donde una crea Motor1y la otra Motor2. En este caso, tendría entradas de registro diferentes para IMotorlos registros específicos del dispositivo que usan Motor1Factoryo Motor2Factory.

Ahora mi pregunta es: ¿Cuál de estos dos métodos es preferible y por qué? Para mí, parece que el primer caso no es sencillo y complicado, ya que estoy extendiendo la lógica que decide qué tipo de instancia en toda la base de código. Mientras que en el segundo caso, estoy multiplicando efectivamente el número de fábricas en mi código, ya que necesitaré una fábrica para (casi) cada tipo de concreto. Se vuelve aún más confuso para mí, cuando se agregan fábricas abstractas a la mezcla.

Así que de nuevo: ¿Cuándo debo usar un método u otro? Y lo más importante: ¿Cuáles son buenos indicadores para decidir qué camino tomar?

Packoman
fuente
2
¿Qué camino es más simple? ¿Los beneficios del enfoque más complejo superan el costo de la complejidad adicional?
Robert Harvey

Respuestas:

2

Si usa ambos, iré por algo simple:

  • DI / IoC: para cada configuración que no cambiará en tiempo de ejecución.
  • Fábrica: para crear una instancia de objetos en tiempo de ejecución que depende de los parámetros de entrada de tiempo de ejecución. Las instancias de la fábrica son inyectadas por el contenedor DI.
Walfrat
fuente
1

Las fábricas abstractas se usan cuando tiene objetos relacionados a través de una jerarquía que necesita variar juntos. No veo eso aquí.

Lo que veo es que te preguntas si una fábrica debería elegir el motor o si el DIC debería elegir una fábrica que produzca un motor en particular.

Es difícil elegir precisamente porque una fábrica y un DIC hacen cosas muy similares. La diferencia es que la fábrica se centra en un tema en particular y el DIC es más general.

Todo se reduce a esta pregunta: ¿necesita un código específico para este problema que vivirá en la fábrica? ¿O es más general como leer detalles de configuración de un archivo?

Tenga en cuenta que si bien solo puede elegir entre Motor1y Motor2hoy, mañana puede haber un Motor3. Favorezca el diseño que haría Motor3fácil agregar.

naranja confitada
fuente
0

Separaría la lógica "qué motor usar" en una Fábrica especial llamada Constructor (patrón) y usaría el Contenedor IOC para ambos motores como detalle de implementación del constructor.

Como regla general:

  • necesita una fábrica (o un generador) si tiene que crear muchos objetos dinámicos de la clase / interfaz. (es decir, para cada automóvil que produzca, debe crear un motor nuevo)
  • si solo necesita una instancia estática de una clase, ioc / di puede hacer el trabajo por usted (es decir, solo necesita una instancia estática del servicio de pagos y una instancia estática del MotorBuilderService)
k3b
fuente