47.9. Transmisión de transacciones grandes para la decodificación lógica #

Las devoluciones de llamada del plugin de salida básica (por ejemplo, begin_cb, change_cb, commit_cb y message_cb) solo se invocan cuando la transacción se confirma realmente. Los cambios todavía se decodifican desde el registro de transacciones, pero solo se pasan al plugin de salida en la confirmación (y se descartan si la transacción se aborta).

Esto significa que mientras la decodificación ocurre de forma incremental y puede volcarse al disco para mantener bajo control el uso de la memoria, todos los cambios decodificados deben transmitirse cuando la transacción finalmente se confirma (o más precisamente, cuando la confirmación se decodifica desde el registro de transacciones). Dependiendo del tamaño de la transacción y del ancho de banda de la red, el tiempo de transferencia puede aumentar significativamente el retraso de aplicación (apply lag).

Para reducir el retraso de aplicación causado por transacciones grandes, un plugin de salida puede proporcionar devoluciones de llamada adicionales para admitir la transmisión incremental de transacciones en curso. Existen varias devoluciones de llamada de transmisión requeridas (stream_start_cb, stream_stop_cb, stream_abort_cb, stream_commit_cb y stream_change_cb) y dos devoluciones de llamada opcionales (stream_message_cb y stream_truncate_cb). Además, si se va a admitir la transmisión de comandos en dos fases, se deben proporcionar devoluciones de llamada adicionales. (Consulta la Section 47.10 para obtener detalles).

Al transmitir una transacción en curso, los cambios (y mensajes) se transmiten en bloques delimitados por las devoluciones de llamada stream_start_cb y stream_stop_cb. Una vez transmitidos todos los cambios decodificados, la transacción se puede confirmar mediante la devolución de llamada stream_commit_cb (o posiblemente abortar mediante la devolución de llamada stream_abort_cb). Si se admiten las confirmaciones en dos fases, la transacción se puede preparar mediante la devolución de llamada stream_prepare_cb, confirmar la preparación con COMMIT PREPARED mediante la devolución de llamada commit_prepared_cb o abortar mediante la devolución de llamada rollback_prepared_cb.

Una secuencia de ejemplo de llamadas de devolución de llamada de transmisión para una transacción puede ser la siguiente:

stream_start_cb(...);   <-- inicio del primer bloque de cambios
  stream_change_cb(...);
  stream_change_cb(...);
  stream_message_cb(...);
  stream_change_cb(...);
  ...
  stream_change_cb(...);
stream_stop_cb(...);    <-- fin del primer bloque de cambios

stream_start_cb(...);   <-- inicio del segundo bloque de cambios
  stream_change_cb(...);
  stream_change_cb(...);
  stream_change_cb(...);
  ...
  stream_message_cb(...);
  stream_change_cb(...);
stream_stop_cb(...);    <-- fin del segundo bloque de cambios


[a. cuando se utiliza la confirmación normal]
stream_commit_cb(...);    <-- confirmación de la transacción transmitida

[b. cuando se utiliza la confirmación en dos fases]
stream_prepare_cb(...);   <-- preparar la transacción transmitida
commit_prepared_cb(...);  <-- confirmación de la transacción preparada

La secuencia real de llamadas de devolución de llamada puede ser más complicada, por supuesto. Puede haber bloques para múltiples transacciones transmitidas, algunas de las transacciones pueden abortarse, etc.

De manera similar al comportamiento de volcado a disco, la transmisión se activa cuando la cantidad total de cambios decodificados del WAL (para todas las transacciones en curso) supera el límite definido por la configuración de logical_decoding_work_mem. En ese momento, se selecciona y se transmite la transacción más grande de nivel superior (medida por la cantidad de memoria utilizada actualmente para los cambios decodificados). Sin embargo, en algunos casos todavía tenemos que volcar a disco incluso si la transmisión está habilitada porque superamos el umbral de memoria pero todavía no hemos decodificado la tupla completa, por ejemplo, solo hemos decodificado la inserción de la tabla toast pero no la inserción de la tabla principal.

Incluso cuando se transmiten transacciones grandes, los cambios se siguen aplicando en el orden de confirmación, conservando las mismas garantías que en el modo sin transmisión.