¿Cómo actualizar la tabla de Postgres desde un volcado de pg_dump?
Tengo 2 tablas de Postgres (mismo esquema) en diferentes servidores.
Una tabla tiene los datos más recientes, y la otra tiene datos antiguos que deben actualizarse con los datos más recientes.
Entonces, exporto la tabla con los datos más recientes:
pg_dump --table=table00 --data-only db00 > table00.sql
o
pg_dump --table=table00 --data-only --column-inserts db00 > table00.sql
Pero ahora, al intentar leer el archivo SQL de la exportación, obtengo errores sobre claves duplicadas.
psql postgresql://<username>:<password>@localhost:5432/db00 --file=table00.sql
El error desaparece si elimino primero la tabla con los datos antiguos, pero esto no solo es indeseable, sino que también es absurdo.
¿Cómo puedo actualizar una tabla de Postgres desde una exportación SQL entonces?
Sería bueno si pg_dump
tuviera una opción --column-updates
, donde, en lugar de declaraciones INSERT
, obtienes declaraciones INSERT ON CONFLICT (column) DO UPDATE SET
…
davy.ai
No existe una opción incorporada en
pg_dump
para generar declaracionesINSERT ON CONFLICT DO UPDATE
. Sin embargo, se puede utilizar una combinación de comandospg_dump
ypsql
junto con algunos scripts para lograr el resultado deseado.En primer lugar, es necesario modificar el comando
pg_dump
para generar un volcado con declaracionesUPSERT
en lugar de declaracionesINSERT
. Para esto, se puede utilizar un comando como este:Este comando crea un volcado de los datos y el esquema de la tabla
table00
sin propietario ni listas de control de acceso (ACLs). Luego utilizased
para transformar las declaracionesINSERT
en declaracionesUPSERT
con cláusulasON CONFLICT (id) DO UPDATE SET
. Se asume que la columnaid
es la columna clave primaria o única que determina el conflicto. El archivo resultante se guarda comotable00_upsert.sql
.A continuación, es necesario ejecutar las declaraciones
UPSERT
en el archivo de volcado en la base de datos de destino. Se puede utilizar un comando como este:Este comando ejecuta las declaraciones SQL en el archivo
table00_upsert.sql
en la base de datosdb00
. Utiliza la opción--set ON_ERROR_STOP=on
para detener la ejecución si hay algún error. También utiliza la opción--single-transaction
para envolver las declaraciones en una transacción única, asegurando la consistencia.Con este enfoque, se puede actualizar la tabla antigua de datos sin eliminarla y sin encontrarse con errores de clave duplicada. Sin embargo, es necesario tener cuidado con el orden de los datos en el archivo de volcado, ya que las declaraciones
UPSERT
pueden fallar si hay conflictos con los datos antiguos. Se puede ordenar los datos en el archivo de volcado por la columna clave primaria para minimizar el riesgo de conflictos.