Pregunta simple: entiendo que la serialización en C # requiere constructores predeterminados. Esto eliminaría la posibilidad de usar el DI inyectado por el constructor (que generalmente es el estilo preferido de DI, en mi lectura [cita requerida] ). Entonces, ¿es realmente una situación de uno u otro, o me estoy perdiendo algo?
(Pregunta secundaria): ¿Los contenedores de IoC evitan esta compensación de alguna manera?
This would eliminate the possibility of using Constructor injected DI
-- ¿Por qué? Todavía puede tener instructores parametrizados, siempre que incluya un constructor predeterminado para fines de serialización (el constructor predeterminado puede ser privado, si lo desea).Respuestas:
No es posible deserializar un objeto y también inyectar una dependencia a otro objeto ya existente, en un paso en C #, utilizando los mecanismos de serialización estándar. En su lugar, deberá usar la inyección de propiedades, primero construyendo el objeto usando el deserializador, luego inyectando la dependencia. Para la mayoría de las aplicaciones del mundo real, no considero que esto sea un verdadero inconveniente: si tiene una clase de modelo de datos serializable, que también depende de otras clases de modelos que no son de datos, debe verificar si su clase de modelo de datos puede tener Demasiadas responsabilidades ya.
Si eso realmente le molesta, puede considerar envolver su objeto serializable con una clase de decorador, donde puede pasar el deserializador y las dependencias adicionales a través del constructor. Ese contenedor luego ejecuta los dos pasos (deserialización del objeto envuelto e inyección de propiedad) en su constructor.
fuente
Estoy resolviendo este problema así: inyectando fábricas de dependencias. En esas fábricas, primero resuelva la dependencia tal como está registrada en el contenedor, luego "deserialice" todos los datos restantes: json.net permite llenar campos en objetos existentes.
Como el código de las fábricas va junto con el código de cableado del contenedor de IoC, no creo que el uso
container.Resolve
dentro de la fábrica viole la regla, quecontainer
debe usarse solo en un lugar en el código: donde ocurre todo el cableado.A partir de ahora, estoy tratando de hacer que este proceso sea automático (a diferencia de lo que he estado probando con ese enfoque) usando la reflexión. Sí, no queda mucho de lo que queda de la deserialización de json.net, parte de ella se sustituye con un código personalizado, pero creo que por qué molestarse.
Además, ¿cuál fue su opinión / decisión final sobre el asunto? Después de leer esta publicación, veo dos formas: deserializar, luego inyectar; o inyectar, luego deserializar (poblar). Y todavía encuentro que mi camino es mejor. Estaré encantado de escuchar argumentos en oposición a esto (estoy considerando que mi camino puede ser mejor para mi caso, pero no puedo imaginar vívidamente buenos casos alternativos, donde falla, solo algunas conjeturas menores)
fuente