Uso de pgl_ddl_deploy
Introducción
Hay muchas bases de datos que requieren la replicación de datos a otras bases de datos para diversos fines. Una de las tecnologías de base de datos más útiles que se utiliza para mover datos del punto A al punto B se denomina "replicación lógica". En la jerga de la base de datos, hay dos categorías de sentencias SQL: DML y DDL. Por una serie de razones, DDL tiene que ser manejado por separado. Durante la migración, el DBA es necesario para desplegar manualmente el SQL en el orden correcto para todos los clústeres de base de datos involucrados, gestionar la contención de bloqueo y agregar nuevas tablas a la replicación si es necesario. Construido sobre pglogical, pgl_ddl_deploy permite que cualquier sentencia SQL DDL se propague directamente a los suscriptores. Esto resuelve el problema de que pglogical no puede sincronizar sentencias DDL.
Para obtener más información, consulte documentación oficial de pgl_ddl_deploy.
Versiones compatibles
Este complemento está disponible para las últimas versiones secundarias de RDS for PostgreSQL 12, 13 y 14. Puede ejecutar la siguiente sentencia SQL para comprobar si su instancia de base de datos admite este complemento:
SELECT * FROM pg_available_extension_versions WHERE name = 'pgl_ddl_deploy';
Si este complemento no es compatible, actualice la versión secundaria de su instancia de base de datos o actualice la versión principal mediante volcado y restauración.
Para obtener más información sobre los complementos soportados por RDS for PostgreSQL, consulte Complementos soportados.
Características
RDS for PostgreSQL soporta complemento pgl_ddl_deploy, que se utiliza para sincronizar automáticamente sentencias DDL. En muchos casos, la mayoría de las sentencias DDL ejecutadas en entornos de aplicación se pueden sincronizar.
- Cualquier sentencia DDL se puede sincronizar con los suscriptores.
- Las tablas se pueden agregar automáticamente a la replicación al crearse.
- Se admite el filtrado por una expresión regular o un conjunto específico de tablas.
- Hay una opción para desplegar de forma segura con bloqueo en los suscriptores.
- Hay una opción para fallar ciertos eventos en el suscriptor para ser reintentado más tarde.
- En algunos casos periféricos, las alertas se pueden construir alrededor del registro proporcionado para el DBA para luego manejar posibles despliegues manuales.
- Las sentencias ALTER TABLE se pueden filtrar por etiquetas de subcomando.
- El soporte para eliminar automáticamente los procesos de bloqueo que impiden la ejecución de DDL en el sistema del suscriptor es opcional.
Instalación y desinstalación de complementos
- Instalación del complemento
SELECT control_extension ('create', 'pgl_ddl_deploy');
- Eliminación del complemento
SELECT control_extension ('drop', 'pgl_ddl_deploy');
Para obtener más información, consulte Instalación y desinstalación de un complemento en la consola de RDS y Instalación y desinstalación de un complemento mediante comandos SQL.
Uso básico
Este complemento implica la publicación y suscripción y depende de pglpgical. Es necesario agregar y configurar parámetros.
wal_level = 'logical' shared_preload_libraries = 'pglogical'
Para obtener más información acerca de cómo modificar el parámetro shared_preload_libraries, consulte Modificación de parámetro shared_preload_libraries.
-- Configuring parameters on the provider SELECT control_extension ('create', 'pglogical'); SELECT control_extension ('create', 'pgl_ddl_deploy'); CREATE TABLE foo (id INT PRIMARY KEY); -- Creating a publication CREATE PUBLICATION testpub FOR TABLE foo; -- Configuring a replication set INSERT INTO pgl_ddl_deploy.set_configs (set_name, include_schema_regex, driver) VALUES ('testpub', '.*', 'native'::pgl_ddl_deploy.driver); -- Deploying the publication SELECT pgl_ddl_deploy.deploy('testpub'); -- Adding roles for the user SELECT pgl_ddl_deploy.add_role(oid) FROM pg_roles WHERE rolname='root'; -- Configuring parameters on the subscriber SELECT control_extension ('create', 'pglogical'); SELECT control_extension ('create', 'pgl_ddl_deploy'); CREATE TABLE foo (id INT PRIMARY KEY); -- Creating a subscription CREATE SUBSCRIPTION testsub CONNECTION conninfo PUBLICATION testpub; ALTER SUBSCRIPTION testsub REFRESH PUBLICATION;
Una vez completada la configuración, ejecute las siguientes sentencias DDL en el proveedor:
ALTET TABLE foo ADD COLUMN bla INT; CREATE TABLE bra (id INT PRIMARY KEY);
Puede verificar lo siguiente en el suscriptor:
\d foo Table "public.foo" Column | Type | Collation | Nullable | Default --------+---------+-----------+----------+--------- id | integer | | not null | bla | integer | | | Indexes: "foo_pkey" PRIMARY KEY, btree (id) \dt List of relations Schema | Name | Type | Owner --------+---------+-------+---------- public | bar | table | root public | foo | table | root (2 rows)
Restricciones
Este complemento tiene algunas limitaciones. Aunque la mayoría de las sentencias DDL ejecutadas en entornos de aplicaciones se pueden sincronizar, no cubre el 100% de los casos de borde.
DDL que implica múltiples tablas
No se puede admitir una única sentencia DDL SQL que altere las tablas replicadas y no replicadas. Por ejemplo, si establece el parámetro include_schema_regex en '^replicated.*':
DROP TABLE replicated.foo, notreplicated.bar;
Se mostrará el siguiente mensaje en el proveedor:
WARNING: Unhandled deployment logged in pgl_ddl_deploy.unhandled DROP TABLE
La tabla replicated.foo existe en el abonado.
\d replicated.foo Table "replicated.foo" Column | Type | Collation | Nullable | Default --------+---------+-----------+----------+--------- id | integer | | not null | Indexes: "foo_pkey" PRIMARY KEY, btree (id)
Del mismo modo, si se utiliza replicación filtrada, puede producirse un error al ejecutar la siguiente sentencia:
ALTER TABLE replicated.foo ADD COLUMN bar_id INT REFERENCES notreplicated.bar (id);
La sentencia no está sincronizada con el abonado.
\d replicated.foo Table "replicated.foo" Column | Type | Collation | Nullable | Default --------+---------+-----------+----------+--------- id | integer | | not null | Indexes: "foo_pkey" PRIMARY KEY, btree (id)
Comandos no admitidos
CREATE TABLE AS y SELECT INTO no son compatibles para replicar DDL debido a las limitaciones en la consistencia transaccional. Es decir, si se crea una tabla a partir de un conjunto de datos en el proveedor, ejecutar el mismo SQL en el suscriptor no garantizará de ninguna manera datos consistentes. Por ejemplo:
CREATE TABLE foo AS SELECT field_1, field_2, now() AS refreshed_at FROM table_1;
Similar a CREATE TABLE AS, se mostrará el siguiente mensaje para SELECT INTO:
WARNING: Unhandled deployment logged in pgl_ddl_deploy.unhandled
Limitaciones de SQL de cliente de sentencias múltiples
Las complejidades y limitaciones vienen cuando el cliente envía todas las sentencias SQL como una sola cadena a PostgreSQL. Supongamos las siguientes sentencias SQL:
CREATE TABLE foo (id serial primary key, bla text); INSERT INTO foo (bla) VALUES ('hello world');
Si esto estaba en un archivo al que se invocó usando psql, se ejecutaría como dos cadenas de comandos SQL separadas. Sin embargo, si en Python o en el ActiveRecord de Ruby crea una sola cadena como la anterior y la ejecuta, entonces se enviaría a PostgreSQL como una sola cadena de comandos SQL. La replicación depende del valor del parámetro allow_multi_statements:
- Si el valor es false, pgl_ddl_deploy solo replicará automáticamente una sentencia SQL cliente que contenga una etiqueta de comando que coincida con la etiqueta de comando de activador de evento. Eso es realmente seguro, pero significa que puede tener muchas más despliegues no controlados.
- Si el valor es true, pgl_ddl_deploy solo replicará automáticamente DDL que contiene etiquetas de comando safe para propagar. Por ejemplo, está prohibido mezclar DDL y DML. Si un comando contiene más de dos sentencias DDL y las sentencias se utilizan en tablas replicadas y no replicadas, se produce el problema descrito en el documento DDL que implica múltiples tablas.
En cualquier caso que una sentencia SQL no se pueda ejecutar automáticamente en el suscriptor basado en estos análisis, en su lugar se registrará como un WARNING y se colocará en la tabla no controlada para su procesamiento manual. Para obtener más detalles y soluciones a los problemas que se producen durante la replicación, consulte documentación oficial de pgl_ddl_deploy.