Estoy considerando un proyecto para migrar parte de nuestra SOA basada en WCF a un modelo de bus de servicio (probablemente nServiceBus) y estoy usando algún pub-sub básico para lograr la separación de consulta de comandos .
No soy nuevo en SOA, ni siquiera en los modelos de bus de servicio, pero confieso que hasta hace poco mi concepto de "separación" se limitaba a la duplicación y replicación de bases de datos habituales. Aún así, me atrae la idea porque parece proporcionar todos los beneficios de un sistema eventualmente consistente , mientras que evita muchos de los inconvenientes obvios (especialmente la falta de soporte transaccional adecuado).
Leí mucho sobre el tema de Udi Dahan, quien es básicamente el gurú de las arquitecturas ESB (al menos en el mundo de Microsoft), pero una cosa que dice realmente me desconcierta:
A medida que obtenemos entidades más grandes con más campos en ellas, también obtenemos más actores que trabajan con esas mismas entidades, y mayor es la probabilidad de que algo toque algún atributo de ellas en un momento dado, lo que aumenta el número de conflictos de concurrencia.
[...]
Un elemento central de CQRS es repensar el diseño de la interfaz de usuario para permitirnos capturar la intención de nuestros usuarios de tal manera que hacer que un cliente sea preferido es una unidad de trabajo diferente para el usuario que indicar que el cliente se ha mudado o que se ha conseguido casado. El uso de una interfaz de usuario similar a Excel para los cambios de datos no captura la intención, como vimos anteriormente.
- Udi Dahan, CQRS aclarado
Desde la perspectiva descrita en la cita, es difícil discutir con esa lógica. Pero parece ir contra la corriente con respecto a las SOA. Se supone que una SOA (y realmente los servicios en general) se ocupan de los mensajes de grano grueso para minimizar el parloteo de la red, entre muchos otros beneficios.
Me doy cuenta de que la charla en la red es un problema menor cuando tienes sistemas altamente distribuidos con una buena cola de mensajes y nada del equipaje de RPC, pero no parece prudente descartar el problema por completo. Udi casi parece estar diciendo que cada cambio de atributo (es decir, actualización de campo) debería ser su propio comando, lo cual es difícil de imaginar en el contexto de un usuario que potencialmente actualiza cientos o miles de entidades y atributos combinados, como suele ocurrir con un sistema tradicional. servicio web.
Una actualización por lotes en SQL Server puede tomar una fracción de segundo dada una buena consulta altamente parametrizada, un parámetro con valores de tabla o una inserción masiva en una tabla de ensayo; procesar todas estas actualizaciones de una en una es lento, lento, lento , y el hardware de la base de datos OLTP es el más costoso de escalar / escalar.
¿Hay alguna manera de conciliar estas preocupaciones en competencia? ¿Estoy pensando en eso de manera incorrecta? ¿Este problema tiene una solución bien conocida en el mundo CQS / ESB?
Si no es así, ¿cómo se decide cuál debería ser el "nivel correcto" de granularidad en un Comando? ¿Existe algún "estándar" que se pueda usar como punto de partida, como el 3NF en las bases de datos, y que solo se desvíe cuando un perfil cuidadoso sugiera un beneficio de rendimiento potencialmente significativo?
¿O es posiblemente una de esas cosas que, a pesar de que varios expertos expresan varias opiniones fuertes, es realmente solo una cuestión de opinión?
fuente
El mensaje que Udi está tratando de transmitir es que CQRS es más que solo CRUD. ¿Por qué creé este registro? ¿Por qué estoy cambiando este registro? ¿Por qué se elimina / marca como eliminado?
Los comandos deben corresponder a acciones / casos de uso que el usuario realiza con el sistema y expresar la intención de la acción en lugar de simplemente decir cambiar esto. Además, puede parecer que es más fino, pero podría ser mucho más grueso de lo que parece. Por ejemplo, la actualización al estado de oro podría implicar un cambio en varios atributos y una serie de otros agregados podrían incluso responder y cambiar en respuesta al evento correspondiente.
CQRS se trata de capturar el idioma de la empresa en la capa de Servicio para que la interfaz de usuario no tenga que preocuparse por lo que sucede cuando realizo esa actualización de estado de oro o el transportista ha marcado que el envío no ha sido entregado o el empleado ha sido promovido al gerente del grupo de tecnología. Bueno, técnicamente estoy hablando de Event Sourcing ahora, pero me entiendes. Hay mensajes más distintos, pero no son necesariamente más detallados que los CUD estándar.
fuente