Hoy iniciamos una serie de artículos sobre el manejo de la transaccionalidad distribuida en entornos de microservicios, en esta entrada hablaremos de algunos conceptos que son claves para entender esta temática. La consistencia a través de la transaccionalidad distribuida es a mi entender el segundo reto más grande que enfrenta una arquitectura microservicios (El reto más grande es un diseño adecuado). En otra entrada hablamos sobre diseño y sobre el patrón Saga, en este ocasión seremos un poco más conceptuales para entender las bases.

¿ Qué es una transacción ?

Una transacción puede definirse como un grupo de eventos que deben ser llevados a cabo como una unidad indivisible; existe si todos y cada uno de los eventos es exitoso o todos son rechazados. Debe ser atómica y consistente.

Gráficamente podemos ilustrarla como se muestra.

Transacción

En una transacción el sistema debe ir de un estado consistente a otro pasando por estados intermedios, si ocurre un error en el camino la operación debe virarse hacia atrás (hacer rollback). Una transacción tiene que dejar el sistema en un estado consistente.

Cuando la operación es “feliz” todo sale bien, el problema radica en preparar los sistemas para que puedan hacer el rollback correctamente.

¿Qué es una transacción distribuida?

El reto de los microservicios, radica en que esa transaccionalidad hay que mantenerla ejecutando operaciones intermedias entre sistemas distribuidos.

Una transacción distribuida cumple los mismos principios que una transacción, con la única diferencia que se ejecuta sobre dos o mas fuentes de datos. En este punto, tiene especial importancia tener en cuenta “La falacias de la computación distribuida”. Al final del artículo te dejaré un vídeo sobre las falacias de la computación distribuida.

Representación de un ejemplo donde tiene lugar una transacción distribuida.

Ejemplo de escenario para transacción distribuida
El concepto de transaccionalidad distribuida

Conceptos relacionados con la transaccionalidad distribuida

Commander

Cuando hablamos del patrón Saga nos referimos a este concepto. El commander es el encargado de manejar la transacción distribuida, conoce las acciones a ejecutar y coordina las mismas; incluidas las acciones para hacer el rollback a través de las operaciones compensatorias.

Reintentos

Es una política que se debe seguir para intentar que la transacción se ejecute, se guía por la implementación del patrón de reintentos y el commander es el encargado de aplicarlos. Puede ver más sobre reintentos en los siguientes artículos: Implementando reintentos con Spring Retry, y con Resilience4j.

Idempotencia

La idempotencia es un concepto que debe estar presente siempre en el desarrollo de las operaciones sobre recursos. Es una propiedad que garantiza que al intentar hacer algo varias veces se obtenga siempre el mismo resultado (viene del ámbito de las matemáticas). Como resultado de los reintentos puede pasar que enviemos a hacer una operación y luego tenga lugar un fallo sin que tengamos una respuesta, al reintentar la operación debe completarse si el sistema se recuperó sin repetirse varias veces.

Consistencia eventual

Tras la ejecución de un operación el sistema va lograr una consistencia en un período de tiempo que será distinto de cero. En los sistemas de bases de datos como MySQL cuando no se usa una implementación maestro-esclavo, o se usa una sola instancia se logra consistencia inmediata, en los microservicios, la consistencia se logra comúnmente de manera eventual.

En los siguientes artículos estaremos hablando sobre técnicas específicas para la implementación de la transaccionalidad distribuida.

Acá les dejo un par de vídeos de nuestro canal de Youtube relacionados con el tema.

1 thought on “Transaccionalidad distribuida (Parte I)

Comments are closed.