¿Es una mala práctica que los servicios compartan una base de datos en SOA?

17

Recientemente he estado leyendo Patrones de integración empresarial de Hohpe y Woolf, algunos de los libros de Thomas Erl sobre SOA y viendo varios videos y podcasts de Udi Dahan et al. en sistemas CQRS y Event Driven.

Los sistemas en mi lugar de trabajo sufren de alto acoplamiento. Aunque en teoría cada sistema tiene su propia base de datos, hay muchas uniones entre ellos. En la práctica, esto significa que hay una gran base de datos que utilizan todos los sistemas. Por ejemplo, hay una tabla de datos del cliente.

Gran parte de lo que he leído parece sugerir desnormalizar datos para que cada sistema use solo su base de datos, y cualquier actualización de un sistema se propague a todos los demás mediante mensajería.

Pensé que esta era una de las formas de imponer los límites en SOA: cada servicio debería tener su propia base de datos, pero luego leí esto:

/programming/4019902/soa-joining-data-across-multiple-services

y sugiere que esto es lo incorrecto que hacer.

Segregar las bases de datos parece una buena manera de desacoplar los sistemas, pero ahora estoy un poco confundido. ¿Es esta una buena ruta a tomar? ¿Se recomienda alguna vez segregar una base de datos en, por ejemplo, un servicio SOA, un contexto limitado DDD, una aplicación, etc.?

Paul T Davies
fuente
La pregunta original que vincula es incorrecta. La pregunta en sí es incorrecta, ya que la mayoría de las respuestas eluden. SOA no se trata de dividir una sola aplicación en servicios discretos y particionar sus datos.
Jeremy
Entiendo que la pregunta es incorrecta. Fueron las respuestas las que me hicieron reevaluar mi pensamiento.
Paul T Davies
Creo que los servicios deben estar acoplados
B Seven

Respuestas:

12

El desacoplamiento solo funciona si realmente hay separación. Considere si tiene un sistema de pedidos:

  • Mesa: CLIENTE
  • Mesa: ORDEN

Si eso es todo lo que tienes, no hay razón para desacoplarlos. Por otro lado, si tienes esto:

  • Mesa: CLIENTE
  • Mesa: ORDEN
  • Tabla: CUSTOMER_NEWSLETTER

Entonces podría argumentar que ORDER y CUSTOMER_NEWSLETTER son parte de dos módulos totalmente separados (pedidos y marketing). Quizás tenga sentido moverlos a bases de datos separadas (una para cada tabla), y hacer que ambos módulos compartan el acceso a la tabla CUSTOMER común en su propia base de datos.

Al hacerlo, está simplificando cada módulo, pero está aumentando la complejidad de su capa de datos. A medida que su aplicación crece más y más, puedo ver una ventaja en la separación. Habrá más y más "islas de datos" que realmente no tienen relación entre sí. Sin embargo, siempre habrá algunos datos que crucen todos los módulos.

La decisión de colocarlos en diferentes bases de datos físicas generalmente se basaría en restricciones del mundo real, como la frecuencia de las copias de seguridad, las restricciones de seguridad, la replicación en diferentes ubicaciones geográficas, etc. No separaría las tablas en diferentes bases de datos físicas solo por cuestiones de separación. Eso se puede manejar de manera más simple con diferentes esquemas o vistas.

Scott Whitlock
fuente
55
-1. Solo deben estar en bases de datos separadas si hay una razón para colocarlas allí. Necesita "sacar algo de eso" porque sin duda hace que su aplicación sea más compleja.
scottschulthess
1
Creo que vale la pena poner énfasis en la importancia de separar las dos áreas de funcionalidad en la capa de datos (ya sea usando esquemas separados u otra cosa). Cada módulo solo debe acceder a los datos del otro módulo a través de la API del otro módulo; esto es similar a los principios de encapsulación OO. Es decir, no comparto un esquema entre múltiples módulos. Además, recomendaría contra vistas, en lugar de preferir exponer datos a través de. una API
Chris Snow
@scottschulthess sí, debe sopesar el costo de la complejidad y si no vale la pena, simplemente no puede dividirse en servicios. Dividir pero usar una base de datos compartida que he encontrado es la peor de las 3 opciones.
Adamantish
8

Donde trabajo tenemos un ESBa las cuales están conectadas 6 aplicaciones diferentes (o debería decir "puntos finales"). Esas 6 aplicaciones funcionan con 3 esquemas de Oracle diferentes en 2 instancias de bases de datos. Algunas de estas aplicaciones coexisten en el mismo esquema no porque estén relacionadas, sino porque nuestra infraestructura de base de datos es administrada por un proveedor externo y obtener un nuevo esquema solo lleva una eternidad (además, por supuesto, no tenemos acceso a DBA) ... Realmente lleva tanto tiempo que en un momento pensamos en reutilizar un esquema existente "temporalmente" para poder continuar el desarrollo. Para imponer la "separación" de datos, los nombres de las tablas tienen el prefijo, por ejemplo, "CST_" para el cliente. Además, tenemos que trabajar con un esquema que, por algunas razones válidas, no podemos cambiar absolutamente ... Es extraño, lo sé. Por supuesto, como siempre sucede, "temporalmente"

Nuestras diferentes aplicaciones se conectan a sus respectivos esquemas de bases de datos y trabajan con sus propios paquetes PL / SQL y nos prohibimos absolutamente interactuar directamente con tablas / datos que están fuera del dominio de nuestra aplicación.

Cuando una de las aplicaciones conectadas al ESB necesita información fuera de su dominio, llama al servicio relacionado en el ESB para obtener los datos, incluso si esa información está de hecho en el mismo esquema, lo que requiere en teoría solo una pequeña declaración de unión en Una de las solicitudes SQL .

Hacemos eso para poder dividir el dominio de nuestra aplicación en diferentes esquemas / bases de datos, y para que los servicios en el ESB sigan funcionando correctamente cuando suceda (es Navidad pronto, estamos entrecruzados)

Ahora, esto puede parecer extraño y horrible desde el exterior, pero hay razones para eso y solo quería compartir esta experiencia concreta para mostrarle que una o más bases de datos no son tan importantes. ¡Espera, lo es! , por muchas razones (+1 para Scott Whitlock, vea el último párrafo sobre copia de seguridad y tal que pueda llevarlo a problemas) Pero es igualmente importante que creo que sus servicios SOA estén diseñados correctamente, al menos esa es mi opinión, y yo No soy un DBA. En definitiva, todas sus bases de datos pertenecen a su "datawarehouse empresarial", ¿verdad?

Finalmente, no voy a reformular el último párrafo de Scott Whitlock, particularmente este

No separaría las tablas en diferentes bases de datos físicas solo por las preocupaciones de separación.

Es realmente super importante. No lo hagas si no hay razón.

Jalayn
fuente
8

He visto las peores pesadillas posibles en la arquitectura de software debido a la integración de datos, y la mejor arma contra este tipo de desorden que he encontrado hasta ahora en contextos limitados de estilo DDD. Que no está muy lejos de "SOA hecho bien", en cierto sentido.

Sin embargo, los datos en sí no son la mejor manera de atacar el problema. Uno debe enfocarse en el comportamiento esperado / necesario y llevar los datos a donde sea importante. Podríamos terminar teniendo alguna duplicación de esta manera, pero esto normalmente no es un problema en comparación con los bloques para la evolución del sistema casi siempre asociados con arquitecturas integradas en datos.

En pocas palabras: si está buscando sistemas acoplados libremente, no permanezca acoplado a los datos. Busque sistemas encapsulados en weel y un canal de comunicación bien estructurado en el medio, actuando como "lingua franca".

ZioBrando
fuente
1
Y ... respondiendo directamente a la pregunta del título: "Sí, consideraría una práctica arriesgada compartir una base de datos en una SOA". Si parece que es lo más razonable, probablemente exista un serio defecto de diseño.
ZioBrando
7

Desacoplar bases de datos y mantener los datos consistentes entre ellas es una tarea de nivel experto. Es muy fácil equivocarse y terminar con los problemas de duplicados, etc., que el sistema actual está diseñado para evitar. Francamente, tomar un sistema de trabajo y hacer esto es más o menos una garantía de introducir nuevos errores sin ningún valor real para los usuarios.

HLGEM
fuente
1

Si se hace correctamente, separar las preocupaciones comerciales en diferentes bases de datos (o al menos diferentes esquemas) es una virtud .

Consulte la descripción de Martin Fowler del patrón CQRS :

A medida que nuestras necesidades se vuelven más sofisticadas, nos alejamos constantemente de [tratar un sistema de información como un almacén de datos CRUD] ... El cambio que introduce CQRS es dividir ese modelo conceptual en modelos separados para actualizar y mostrar ... Hay espacio para una variación considerable aquí. Los modelos en memoria pueden compartir la misma base de datos, en cuyo caso la base de datos actúa como la comunicación entre los dos modelos. Sin embargo, también pueden usar bases de datos separadas , creando efectivamente la base de datos del lado de la consulta mediante ReportingDatabase en tiempo real. En este caso, debe existir algún mecanismo de comunicación entre los dos modelos o sus bases de datos.

Y los principios arquitectónicos de NServiceBus :

Separación de consulta de comando

Una solución que evita este problema separa los comandos y las consultas a nivel del sistema, incluso por encima del cliente y el servidor. En esta solución hay dos "servicios" que abarcan tanto el cliente como el servidor: uno a cargo de los comandos (crear, actualizar, eliminar) y el otro a cargo de las consultas (lectura). Estos servicios se comunican solo a través de mensajes: uno no puede acceder a la base de datos del otro ...

Y segregación de responsabilidad de comando y consulta (CQRS)

Segregación de responsabilidad de comando y consulta

La mayoría de las aplicaciones lee datos con más frecuencia de la que escriben datos. Basado en esa declaración, sería una buena idea hacer una solución donde fácilmente pueda agregar más bases de datos para leer, ¿verdad? Entonces, ¿qué pasa si configuramos una base de datos dedicada solo para la lectura? Aun mejor; ¿Qué pasa si diseñamos la base de datos de manera tal que sea más rápido leerla? Si diseña sus aplicaciones en función de los patrones descritos en la arquitectura CQRS, tendrá una solución escalable y rápida para leer datos.

Jim G.
fuente