COPY — copiar datos entre un archivo y una tabla
COPYtable_name[ (column_name[, ...] ) ] FROM { 'filename' | PROGRAM 'command' | STDIN } [ [ WITH ] (option[, ...] ) ] [ WHEREcondition] COPY {table_name[ (column_name[, ...] ) ] | (query) } TO { 'filename' | PROGRAM 'command' | STDOUT } [ [ WITH ] (option[, ...] ) ] dondeoptionpuede ser uno de: FORMATformat_nameFREEZE [boolean] DELIMITER 'delimiter_character' NULL 'null_string' DEFAULT 'default_string' HEADER [boolean| MATCH ] QUOTE 'quote_character' ESCAPE 'escape_character' FORCE_QUOTE { (column_name[, ...] ) | * } FORCE_NOT_NULL { (column_name[, ...] ) | * } FORCE_NULL { (column_name[, ...] ) | * } ON_ERRORerror_actionREJECT_LIMITmaxerrorENCODING 'encoding_name' LOG_VERBOSITYverbosity
COPY mueve datos entre tablas de
PostgreSQL y archivos del sistema de archivos estándar.
COPY TO copia el contenido de una tabla
hacia un archivo, mientras que COPY FROM copia
datos desde un archivo hacia una tabla (añadiendo los datos a
lo que ya se encuentre en la tabla). COPY TO
también puede copiar los resultados de una consulta SELECT.
Si se especifica una lista de columnas, COPY TO copia únicamente
los datos de las columnas especificadas en el archivo. Para COPY
FROM, cada campo en el archivo se inserta, en orden, en la
columna especificada. Las columnas de la tabla no especificadas en la lista de columnas de
COPY FROM recibirán sus valores por defecto.
COPY con un nombre de archivo le indica al servidor
PostgreSQL que lea o escriba directamente en un archivo.
El archivo debe ser accesible por el usuario de PostgreSQL
(el ID de usuario bajo el cual se ejecuta el servidor) y el nombre debe especificarse
desde el punto de vista del servidor. Cuando se especifica PROGRAM,
el servidor ejecuta el comando dado y lee de la salida estándar del programa, o escribe
en la entrada estándar del mismo. El comando debe especificarse desde el punto de vista
del servidor y debe ser ejecutable por el usuario de PostgreSQL.
Cuando se especifica STDIN o STDOUT, los datos
se transmiten a través de la conexión entre el cliente y el servidor.
Cada proceso de respaldo (backend) que ejecute COPY informará de su progreso
en la vista pg_stat_progress_copy. Consulta
Section 27.4.3 para obtener más detalles.
Por defecto, COPY fallará si encuentra un error durante el procesamiento.
Para casos de uso donde se desee un intento de mejor esfuerzo para cargar todo el archivo,
se puede utilizar la cláusula ON_ERROR para especificar algún otro
comportamiento.
table_nameEl nombre (opcionalmente calificado por esquema) de una tabla existente.
column_nameUna lista opcional de columnas a copiar. Si no se especifica ninguna lista de columnas, se copiarán todas las columnas de la tabla excepto las columnas generadas.
query
Un comando SELECT,
VALUES,
INSERT,
UPDATE,
DELETE o
MERGE
cuyos resultados se van a copiar. Ten en cuenta que se requieren paréntesis
alrededor de la consulta.
Para las consultas INSERT, UPDATE,
DELETE y MERGE, se debe proporcionar una
cláusula RETURNING, y la relación de destino no debe tener
una regla condicional, ni una regla ALSO, ni una regla
INSTEAD que se expanda a múltiples instrucciones.
filename
La ruta del archivo de entrada o salida. El nombre de un archivo de entrada puede ser
una ruta absoluta o relativa, pero el nombre de un archivo de salida debe ser una ruta
absoluta. Los usuarios de Windows pueden necesitar usar una cadena E'' y
duplicar las barras invertidas utilizadas en la ruta.
PROGRAM
Un comando a ejecutar. En COPY FROM, la entrada se lee de la
salida estándar del comando, y en COPY TO, la salida se escribe
en la entrada estándar del comando.
Ten en cuenta que el comando es invocado por el intérprete de comandos (shell), por lo que si necesitas pasar argumentos que provengan de una fuente no confiable, debes tener cuidado de quitar o escapar cualquier carácter especial que pueda tener un significado especial para el shell. Por razones de seguridad, es mejor usar una cadena de comando fija, o al menos evitar incluir cualquier entrada de usuario en ella.
STDINEspecifica que la entrada proviene de la aplicación cliente.
STDOUTEspecifica que la salida va a la aplicación cliente.
boolean
Especifica si la opción seleccionada debe activarse o desactivarse.
Puedes escribir TRUE, ON o
1 para activar la opción, y FALSE,
OFF o 0 para desactivarla. El
valor boolean también puede
omitirse, en cuyo caso se asume TRUE.
FORMAT
Selecciona el formato de datos a leer o escribir:
text,
csv (valores separados por comas)
o binary.
El valor por defecto es text.
Consulta la sección Formatos de archivo a continuación para más detalles.
FREEZE
Solicita copiar los datos con las filas ya congeladas, tal como quedarían después
de ejecutar el comando VACUUM FREEZE. Esto está pensado como una
opción de rendimiento para la carga inicial de datos. Las filas se congelarán únicamente
si la tabla cargada se ha creado o truncado en la subtransacción actual, no hay cursores
abiertos y no hay instantáneas más antiguas mantenidas por esta transacción. Actualmente
no es posible realizar un COPY FREEZE en una tabla particionada o
tabla foránea. Esta opción solo se permite en COPY FROM.
Ten en cuenta que todas las demás sesiones podrán ver los datos inmediatamente una vez que se hayan cargado correctamente. Esto viola las reglas normales de visibilidad MVCC y los usuarios deben ser conscientes de los posibles problemas que esto podría causar.
DELIMITER
Especifica el carácter que separa las columnas dentro de cada fila (línea) del archivo.
El valor por defecto es un carácter de tabulación en formato de texto, y una coma en
formato CSV. Debe ser un único carácter de un solo byte.
Esta opción no se permite cuando se utiliza el formato binary.
NULL
Especifica la cadena que representa un valor nulo. El valor por defecto es
\N (barra invertida-N) en formato de texto, y una cadena vacía sin
comillas en formato CSV. Es posible que prefieras una cadena vacía
incluso en formato de texto para casos en los que no desees distinguir los nulos de las
cadenas vacías. Esta opción no se permite cuando se utiliza el formato binary.
Al usar COPY FROM, cualquier elemento de datos que coincida con esta
cadena se almacenará como un valor nulo, por lo que debes asegurarte de usar la misma
cadena que utilizaste con COPY TO.
DEFAULT
Especifica la cadena que representa un valor por defecto. Cada vez que se encuentre la cadena
en el archivo de entrada, se utilizará el valor por defecto de la columna correspondiente.
Esta opción se permite únicamente en COPY FROM, y solo cuando no se utiliza
el formato binary.
HEADER
Especifica que el archivo contiene una línea de encabezado con los nombres de cada columna
en el archivo. En la salida, la primera línea contiene los nombres de las columnas de la
tabla. En la entrada, la primera línea se descarta cuando esta opción se establece en
true (o valor booleano equivalente). Si esta opción se establece en
MATCH, el número y los nombres de las columnas en la línea de encabezado
deben coincidir exactamente y en orden con los nombres de las columnas reales de la tabla;
de lo contrario se lanza un error. Esta opción no se permite cuando se utiliza el formato
binary. La opción MATCH solo es válida para comandos
COPY FROM.
QUOTE
Especifica el carácter de entrecomillado a utilizar cuando se entrecomilla un valor de datos.
El valor por defecto es la comilla doble. Debe ser un único carácter de un solo byte.
Esta opción se permite únicamente cuando se utiliza el formato CSV.
ESCAPE
Especifica el carácter que debe aparecer antes de un carácter de datos que coincida con el
valor de QUOTE. El valor por defecto es el mismo que el valor de
QUOTE (de modo que el carácter de entrecomillado se duplica si aparece en
los datos). Debe ser un único carácter de un solo byte. Esta opción se permite únicamente
cuando se utiliza el formato CSV.
FORCE_QUOTE
Fuerza el uso de comillas para todos los valores no NULL en cada columna
especificada. La salida NULL nunca se entrecomilla. Si se especifica
*, los valores no NULL se entrecomillarán en todas las
columnas. Esta opción se permite únicamente en COPY TO, y solo cuando se
utiliza el formato CSV.
FORCE_NOT_NULL
No compara los valores de las columnas especificadas con la cadena nula. En el caso por defecto
donde la cadena nula está vacía, esto significa que los valores vacíos se leerán como cadenas
de longitud cero en lugar de nulos, incluso cuando no estén entrecomillados. Si se especifica
*, la opción se aplicará a todas las columnas. Esta opción se permite
únicamente en COPY FROM, y solo cuando se utiliza el formato CSV.
FORCE_NULL
Compara los valores de las columnas especificadas con la cadena nula, incluso si se ha
entrecomillado, y si se encuentra una coincidencia, establece el valor a NULL.
En el caso por defecto donde la cadena nula está vacía, esto convierte una cadena vacía
entrecomillada en NULL. Si se especifica *, la opción se aplicará a todas las
columnas. Esta opción se permite únicamente en COPY FROM, y solo cuando se
utiliza el formato CSV.
ON_ERROR
Especifica cómo comportarse cuando se encuentra un error al convertir el valor de entrada de una
columna a su tipo de datos. Un valor de error_action
de stop significa que el comando falla, mientras que ignore
significa descartar la fila de entrada y continuar con la siguiente. El valor por defecto es
stop.
La opción ignore es aplicable únicamente para COPY FROM
cuando el FORMAT es text o csv.
Se emite un mensaje de tipo NOTICE que contiene el número de filas ignoradas al final del
COPY FROM si se descartó al menos una fila. Cuando la opción
LOG_VERBOSITY se establece en verbose, se emite un mensaje
NOTICE que contiene la línea del archivo de entrada y el nombre de la columna cuya
conversión de entrada ha fallado para cada fila descartada. Cuando se establece en
silent, no se emite ningún mensaje con respecto a las filas ignoradas.
REJECT_LIMIT
Especifica el número máximo de errores tolerados al convertir el valor de entrada de una columna
a su tipo de datos, cuando ON_ERROR está establecido en ignore.
Si la entrada causa más errores que el valor especificado, el comando COPY falla,
incluso con ON_ERROR establecido en ignore. Esta cláusula debe
utilizarse con ON_ERROR=ignore y
maxerror debe ser un tipo bigint positivo.
Si no se especifica, ON_ERROR=ignore permite un número ilimitado
de errores, lo que significa que COPY omitirá todos los datos erróneos.
ENCODING
Especifica que el archivo está codificado en la codificación encoding_name. Si se omite esta opción, se utiliza la codificación
actual del cliente. Consulta las Notas a continuación para obtener más detalles.
LOG_VERBOSITY
Especifica la cantidad de mensajes emitidos por un comando COPY:
default, verbose o silent.
Si se especifica verbose, se emiten mensajes adicionales durante el procesamiento.
silent suprime tanto los mensajes detallados como los predeterminados.
Actualmente, esto se utiliza en el comando COPY FROM cuando la opción
ON_ERROR se establece en ignore.
WHERE
La cláusula opcional WHERE tiene la forma general
WHERE condition
donde condition es cualquier expresión que se evalúa como
un resultado de tipo boolean. Cualquier fila que no cumpla con esta condición no se
insertará en la tabla. Una fila cumple con la condición si devuelve verdadero cuando los valores reales
de la fila se sustituyen en cualquier referencia de variable.
Actualmente, no se permiten subconsultas en las expresiones WHERE, y la evaluación
no ve ningún cambio realizado por el propio comando COPY (esto importa cuando la expresión
contiene llamadas a funciones de tipo VOLATILE).
Al completarse con éxito, un comando COPY devuelve una etiqueta de comando
de la forma
COPY count
El count es el número de filas copiadas.
psql imprimirá esta etiqueta de comando únicamente si el comando
no fue COPY ... TO STDOUT, o el metacomando equivalente de
psql \copy ... to stdout. Esto es para evitar
confundir la etiqueta del comando con los datos que se acaban de imprimir.
COPY TO se puede utilizar con tablas normales y vistas materializadas pobladas.
Por ejemplo, COPY copia las
mismas filas que table TOSELECT * FROM ONLY .
Sin embargo, no admite directamente otros tipos de relaciones, como tablas particionadas, tablas hijas
de herencia o vistas. Para copiar todas las filas de dichas relaciones, utiliza
tableCOPY (SELECT * FROM .
table) TO
COPY FROM se puede utilizar con tablas normales, foráneas o particionadas, o con
vistas que tengan disparadores (triggers) de tipo INSTEAD OF INSERT.
Debes tener el privilegio de selección (select) en la tabla cuyos valores son leídos por
COPY TO, y el privilegio de inserción (insert) en la tabla en la cual se insertan
los valores mediante COPY FROM. Es suficiente tener privilegios de columna en las
columnas enumeradas en el comando.
Si la seguridad a nivel de fila está activada para la tabla, se aplicarán las políticas de selección
SELECT pertinentes a las instrucciones COPY .
Actualmente, table TOCOPY FROM no es compatible con tablas que tengan activada la seguridad
a nivel de fila. Utiliza instrucciones INSERT equivalentes en su lugar.
Los archivos nombrados en un comando COPY son leídos o escritos directamente por el servidor,
no por la aplicación cliente. Por lo tanto, deben residir en la máquina del servidor de la base de datos o ser
accesibles para ella, no para el cliente. Deben ser accesibles y legibles o escribibles por el usuario de
PostgreSQL (el ID de usuario bajo el cual se ejecuta el servidor), no por el cliente.
Del mismo modo, el comando especificado con PROGRAM es ejecutado directamente por el servidor,
no por la aplicación cliente, y debe ser ejecutable por el usuario de PostgreSQL.
El uso de COPY para especificar un archivo o programa solo se permite a los superusuarios
de la base de datos o a los usuarios que tengan concedido alguno de los roles
pg_read_server_files, pg_write_server_files o
pg_execute_server_program, ya que permite leer o escribir cualquier archivo o ejecutar un
programa al que el servidor tenga privilegios de acceso.
No confundas COPY con la instrucción de psql
\copy. \copy invoca
COPY FROM STDIN o COPY TO STDOUT, y luego recupera/almacena los datos
en un archivo accesible para el cliente psql. Por lo tanto, la accesibilidad de los
archivos y los derechos de acceso dependen del cliente y no del servidor cuando se utiliza \copy.
Se recomienda que el nombre del archivo utilizado en COPY se especifique siempre como una ruta
absoluta. Esto es obligatorio para el servidor en el caso de COPY TO, pero para
COPY FROM tienes la opción de leer de un archivo especificado mediante una ruta relativa.
La ruta se interpretará en relación con el directorio de trabajo del proceso del servidor (normalmente el
directorio de datos del clúster), no el directorio de trabajo del cliente.
La ejecución de un comando con PROGRAM puede estar restringida por los mecanismos de control de
acceso del sistema operativo, como SELinux.
COPY FROM invocará cualquier disparador (trigger) y restricción de comprobación (check constraint)
en la tabla de destino. Sin embargo, no invocará reglas.
Para las columnas de identidad, el comando COPY FROM siempre escribirá los valores de las columnas
proporcionados en los datos de entrada, al igual que la opción OVERRIDING SYSTEM VALUE de
INSERT.
La entrada y salida de COPY se ve afectada por DateStyle. Para garantizar la
portabilidad a otras instalaciones de PostgreSQL que puedan utilizar configuraciones de
DateStyle que no sean las por defecto, DateStyle debe establecerse en
ISO antes de usar COPY TO. También es una buena idea evitar volcar datos con
IntervalStyle establecido en sql_standard, porque los valores de intervalo
negativos pueden ser malinterpretados por un servidor que tenga una configuración diferente para
IntervalStyle.
Los datos de entrada se interpretan de acuerdo con la opción ENCODING o la codificación actual del
cliente, y los datos de salida se codifican en la opción ENCODING o en la codificación actual del
cliente, incluso si los datos no pasan a través del cliente sino que el servidor los lee o escribe directamente desde
o hacia un archivo.
El comando COPY FROM inserta físicamente las filas de entrada en la tabla a medida que avanza.
Si el comando falla, estas filas quedan en un estado eliminado; estas filas no serán visibles, pero seguirán ocupando
espacio en disco. Esto podría equivaler a un desperdicio considerable de espacio en disco si el fallo ocurrió bien
avanzada una operación de copia grande. Se debe usar VACUUM para recuperar el espacio desperdiciado.
FORCE_NULL y FORCE_NOT_NULL se pueden utilizar simultáneamente en la misma
columna. Esto da como resultado la conversión de cadenas nulas entrecomilladas en valores nulos y cadenas nulas sin
entrecomillar en cadenas vacías.
Cuando se utiliza el formato text, los datos leídos o escritos consisten en un archivo de texto
con una línea por cada fila de la tabla. Las columnas de una fila están separadas por el carácter delimitador. Los
valores de las columnas son cadenas generadas por la función de salida, o aceptables por la función de entrada, del
tipo de datos de cada atributo. La cadena nula especificada se utiliza en lugar de las columnas que son nulas.
COPY FROM lanzará un error si cualquier línea del archivo de entrada contiene más o menos
columnas de las esperadas.
El final de los datos puede representarse mediante una línea que contenga únicamente barra invertida y un punto
(\.). No es necesario un marcador de fin de datos cuando se lee desde un archivo, ya que el propio
fin del archivo sirve perfectamente; en ese contexto, esta disposición existe únicamente por compatibilidad hacia
atrás. Sin embargo, psql utiliza \. para terminar una operación
COPY FROM STDIN (es decir, la lectura de datos de COPY en línea en un script
SQL). En ese contexto, la regla es necesaria para poder finalizar la operación antes del final del script.
Los caracteres de barra invertida (\) se pueden utilizar en los datos de COPY
para proteger los caracteres de datos que de otro modo podrían tomarse como delimitadores de fila o columna. En
particular, los siguientes caracteres deben estar precedidos por una barra invertida si aparecen
como parte del valor de una columna: la propia barra invertida, el salto de línea, el retorno de carro y el carácter
delimitador actual.
La cadena nula especificada es enviada por COPY TO sin añadir barras invertidas; a la inversa,
COPY FROM compara la entrada con la cadena nula antes de eliminar las barras invertidas. Por lo
tanto, una cadena nula como \N no puede confundirse con el valor de datos real \N
(que se representaría como \\N).
Las siguientes secuencias especiales de barra invertida son reconocidas por COPY FROM:
| Secuencia | Representa |
|---|---|
\b | Retroceso (Backspace, ASCII 8) |
\f | Salto de página (Form feed, ASCII 12) |
\n | Salto de línea (Newline, ASCII 10) |
\r | Retorno de carro (Carriage return, ASCII 13) |
\t | Tabulación (Tab, ASCII 9) |
\v | Tabulación vertical (Vertical tab, ASCII 11) |
\digits | Barra invertida seguida de uno a tres dígitos octales especifica el byte con ese código numérico |
\xdigits | Barra invertida x seguida de uno o dos dígitos hexadecimales especifica el byte con ese código numérico |
Actualmente, COPY TO nunca emitirá una secuencia de barra invertida con dígitos octales o hexadecimales,
pero sí utiliza las otras secuencias enumeradas anteriormente para esos caracteres de control.
Cualquier otro carácter precedido por una barra invertida que no se mencione en la tabla anterior se tomará para representarse
a sí mismo. Sin embargo, ten cuidado de no añadir barras invertidas innecesariamente, ya que podría producir accidentalmente
una cadena que coincida con el marcador de fin de datos (\.) o con la cadena nula (por defecto
\N). Estas cadenas se reconocerán antes de realizar cualquier otro procesamiento de barras invertidas.
Se recomienda encarecidamente que las aplicaciones que generen datos para COPY conviertan los retornos de
carro y saltos de línea de los datos a las secuencias \r y \n respectivamente.
Actualmente es posible representar un retorno de carro de los datos mediante una barra invertida y un retorno de carro, y un
salto de línea de los datos mediante una barra invertida y un salto de línea. Sin embargo, es posible que estas representaciones
no se acepten en futuras versiones. También son muy vulnerables a la corrupción si el archivo de COPY se
transfiere entre diferentes máquinas (por ejemplo, de Unix a Windows o viceversa).
Todas las secuencias de barra invertida se interpretan después de la conversión de codificación. Los bytes especificados con las secuencias de barra invertida de dígitos octales y hexadecimales deben formar caracteres válidos en la codificación de la base de datos.
COPY TO terminará cada fila con un salto de línea de estilo Unix (“\n”).
En su lugar, los servidores que se ejecutan en Microsoft Windows emiten retorno de carro/salto de línea
(“\r\n”), pero solo para COPY a un archivo del servidor; para mantener la
consistencia entre plataformas, COPY TO STDOUT siempre envía “\n”
independientemente de la plataforma del servidor. COPY FROM puede manejar líneas que terminan con saltos de
línea, retornos de carro o retornos de carro/saltos de línea. Para reducir el riesgo de error debido a saltos de línea o
retornos de carro sin barra invertida que se pretendían como datos, COPY FROM se quejará si las terminaciones
de línea en la entrada no son todas iguales.
Esta opción de formato se utiliza para importar y exportar el formato de archivo de valores separados por comas
(CSV) utilizado por muchos otros programas, como las hojas de cálculo. En lugar de las reglas de escape
utilizadas por el formato de texto estándar de PostgreSQL, produce y reconoce el mecanismo de
escape común de CSV.
Los valores de cada registro están separados por el carácter DELIMITER. Si el valor contiene el carácter
delimitador, el carácter QUOTE, la cadena NULL, un retorno de carro o un carácter de salto
de línea, entonces todo el valor se precede y se sucede por el carácter QUOTE, y cualquier ocurrencia de
un carácter QUOTE o del carácter ESCAPE dentro del valor se precede por el carácter de
escape. También puedes utilizar FORCE_QUOTE para forzar el uso de comillas al exportar valores no
NULL en columnas específicas.
El formato CSV no tiene una forma estándar de distinguir un valor NULL de una cadena vacía.
El comando COPY de PostgreSQL maneja esto mediante el entrecomillado. Un valor
NULL se exporta como la cadena del parámetro NULL y no se entrecomilla, mientras que un
valor no NULL que coincide con la cadena del parámetro NULL se entrecomilla. Por ejemplo,
con la configuración por defecto, un NULL se escribe como una cadena vacía sin comillas, mientras que un valor
de datos de cadena vacía se escribe con comillas dobles (""). La lectura de valores sigue reglas similares.
Puedes utilizar FORCE_NOT_NULL para evitar comparaciones de entrada de tipo NULL para
columnas específicas. También puedes usar FORCE_NULL para convertir valores de datos de cadena nula
entrecomillados en NULL.
Debido a que la barra invertida no es un carácter especial en el formato CSV, el marcador de fin de datos
utilizado en el modo de texto (\.) no se trata normalmente como especial al leer datos CSV.
Una excepción es que psql terminará una operación COPY FROM STDIN (es decir, la lectura
de datos de COPY en línea en un script SQL) en una línea que contenga únicamente \., ya sea
en modo de texto o CSV.
Las versiones de PostgreSQL anteriores a la v18 siempre reconocían un \. sin
comillas como marcador de fin de datos, incluso cuando se leía desde un archivo independiente. Para mantener la compatibilidad con
versiones anteriores, COPY TO entrecomillará \. cuando aparezca solo en una línea, aunque
esto ya no sea necesario.
En el formato CSV, todos los caracteres son significativos. Un valor entrecomillado rodeado de espacio en blanco,
o de cualquier otro carácter que no sea el DELIMITER, incluirá esos caracteres. Esto puede causar errores si
importas datos desde un sistema que rellena las líneas CSV con espacios en blanco hasta alcanzar un ancho fijo.
Si surge una situación de este tipo, es posible que necesites preprocesar el archivo CSV para eliminar el espacio
en blanco final antes de importar los datos a PostgreSQL.
El formato CSV reconocerá y producirá archivos CSV con valores entrecomillados que contengan
retornos de carro y saltos de línea embebidos. Por lo tanto, los archivos no son estrictamente de una línea por cada fila de la
tabla como los archivos en formato de texto.
Muchos programas producen archivos CSV extraños y ocasionalmente perversos, por lo que el formato de archivo es
más una convención que un estándar. Por lo tanto, es posible que encuentres algunos archivos que no se puedan importar utilizando este
mecanismo, y COPY podría producir archivos que otros programas no puedan procesar.
La opción de formato binary hace que todos los datos se almacenen/lean en formato binario en lugar de texto. Es
un poco más rápido que los formatos de texto y CSV, pero un archivo en formato binario es menos portable entre
arquitecturas de máquinas y versiones de PostgreSQL. Además, el formato binario es muy específico del tipo
de datos; por ejemplo, no funcionará exportar datos binarios de una columna smallint y leerlos en una columna
integer, aunque eso funcionaría perfectamente en formato de texto.
El formato de archivo binary consiste en un encabezado de archivo, cero o más tuplas que contienen los datos de
las filas, y un pie de página de archivo. Los encabezados y los datos están en orden de bytes de red (network byte order).
Las versiones de PostgreSQL anteriores a la 7.4 utilizaban un formato de archivo binario diferente.
El encabezado del archivo consta de 15 bytes de campos fijos, seguidos de un área de extensión del encabezado de longitud variable. Los campos fijos son:
Secuencia de 11 bytes PGCOPY\n\377\r\n\0 — ten en cuenta que el byte cero es una parte obligatoria de la firma.
(La firma está diseñada para permitir una identificación fácil de los archivos que han sido alterados por una transferencia que no sea
limpia para 8 bits. Esta firma será modificada por los filtros de traducción de fin de línea, bytes cero omitidos, bits altos omitidos
o cambios de paridad).
Máscara de bits de enteros de 32 bits para denotar aspectos importantes del formato del archivo. Los bits se numeran desde el 0 (LSB) al 31 (MSB). Ten en cuenta que este campo se almacena en orden de bytes de red (el byte más significativo primero), al igual que todos los campos enteros utilizados en el formato de archivo. Los bits 16–31 están reservados para denotar problemas críticos del formato de archivo; un lector debe abortar si encuentra un bit inesperado establecido en este rango. Los bits 0–15 están reservados para señalar problemas de formato compatibles hacia atrás; un lector debe simplemente ignorar cualquier bit inesperado establecido en este rango. Actualmente, solo está definido un bit de bandera, y el resto debe ser cero:
Si es 1, los OID se incluyen en los datos; si es 0, no. Las columnas de sistema OID ya no son compatibles en PostgreSQL, pero el formato sigue conteniendo el indicador.
Entero de 32 bits, longitud en bytes del resto del encabezado, sin incluirse a sí mismo. Actualmente, esto es cero, y la primera tupla le sigue inmediatamente. Los cambios futuros en el formato podrían permitir que haya datos adicionales en el encabezado. Un lector debe omitir silenciosamente cualquier dato de extensión de encabezado que no sepa qué hacer con él.
El área de extensión del encabezado está prevista para contener una secuencia de fragmentos (chunks) autoidentificables. El campo de banderas no está destinado a indicar a los lectores lo que hay en el área de extensión. El diseño específico del contenido de la extensión del encabezado se deja para una versión posterior.
Este diseño permite tanto adiciones al encabezado compatibles hacia atrás (añadir fragmentos de extensión de encabezado o establecer bits de bandera de orden inferior) como cambios no compatibles hacia atrás (establecer bits de bandera de orden superior para señalar dichos cambios y añadir datos de soporte al área de extensión si es necesario).
Cada tupla comienza con un recuento entero de 16 bits del número de campos en la tupla. (Actualmente, todas las tuplas de una tabla tendrán el mismo recuento, pero eso podría no ser siempre cierto). Luego, repetido para cada campo de la tupla, hay una palabra de longitud de 32 bits seguida de esa cantidad de bytes de datos de campo. (La palabra de longitud no se incluye a sí misma, y puede ser cero). Como caso especial, -1 indica un valor de campo NULL. No siguen bytes de valor en el caso NULL.
No hay relleno de alineación (alignment padding) ni ningún otro dato adicional entre los campos.
Actualmente, se asume que todos los valores de datos en un archivo en formato binario están en formato binario (código de formato uno). Se prevé que una futura extensión pueda añadir un campo de encabezado que permita especificar códigos de formato por columna.
Para determinar el formato binario adecuado para los datos reales de la tupla, debes consultar el código fuente de
PostgreSQL, en particular las funciones *send y *recv para el tipo
de datos de cada columna (normalmente estas funciones se encuentran en el directorio src/backend/utils/adt/ de la
distribución del código fuente).
Si los OID se incluyen en el archivo, el campo OID sigue inmediatamente a la palabra de recuento de campos. Es un campo normal excepto que no se incluye en el recuento de campos. Ten en cuenta que las columnas de sistema OID no son compatibles en las versiones actuales de PostgreSQL.
El pie de página del archivo consiste en una palabra entera de 16 bits que contiene -1. Esto se distingue fácilmente de la palabra de recuento de campos de una tupla.
Un lector debe informar de un error si una palabra de recuento de campos no es -1 ni el número esperado de columnas. Esto proporciona una comprobación adicional contra la pérdida de sincronización con los datos.
El siguiente ejemplo copia una tabla al cliente utilizando la barra vertical (|) como delimitador de campos:
COPY country TO STDOUT (DELIMITER '|');
Para copiar datos de un archivo en la tabla country:
COPY country FROM '/usr1/proj/bray/sql/country_data';
Para copiar en un archivo únicamente los países cuyos nombres comiencen con 'A':
COPY (SELECT * FROM country WHERE country_name LIKE 'A%') TO '/usr1/proj/bray/sql/a_list_countries.copy';
Para copiar en un archivo comprimido, puedes canalizar la salida a través de un programa de compresión externo:
COPY country TO PROGRAM 'gzip > /usr1/proj/bray/sql/country_data.gz';
Aquí hay una muestra de datos adecuados para copiar en una tabla desde STDIN:
AF AFGHANISTAN AL ALBANIA DZ ALGERIA ZM ZAMBIA ZW ZIMBABWE
Ten en cuenta que el espacio en blanco en cada línea es en realidad un carácter de tabulación.
El siguiente código muestra los mismos datos, exportados en formato binario. Los datos se muestran después de filtrarlos a través de la
utilidad de Unix od -c. La tabla tiene tres columnas; la primera tiene el tipo char(2), la segunda tiene el
tipo text, y la tercera tiene el tipo integer. Todas las filas tienen un valor nulo en la tercera columna.
0000000 P G C O P Y \n 377 \r \n \0 \0 \0 \0 \0 \0 0000020 \0 \0 \0 \0 003 \0 \0 \0 002 A F \0 \0 \0 013 A 0000040 F G H A N I S T A N 377 377 377 377 \0 003 0000060 \0 \0 \0 002 A L \0 \0 \0 007 A L B A N I 0000100 A 377 377 377 377 \0 003 \0 \0 \0 002 D Z \0 \0 \0 0000120 007 A L G E R I A 377 377 377 377 \0 003 \0 \0 0000140 \0 002 Z M \0 \0 \0 006 Z A M B I A 377 377 0000160 377 377 \0 003 \0 \0 \0 002 Z W \0 \0 \0 \b Z I 0000200 M B A B W E 377 377 377 377 377 377
No existe una instrucción COPY en el estándar SQL.
La siguiente sintaxis se utilizaba antes de la versión 9.0 de PostgreSQL y todavía es compatible:
COPYtable_name[ (column_name[, ...] ) ] FROM { 'filename' | STDIN } [ [ WITH ] [ BINARY ] [ DELIMITER [ AS ] 'delimiter_character' ] [ NULL [ AS ] 'null_string' ] [ CSV [ HEADER ] [ QUOTE [ AS ] 'quote_character' ] [ ESCAPE [ AS ] 'escape_character' ] [ FORCE NOT NULLcolumn_name[, ...] ] ] ] COPY {table_name[ (column_name[, ...] ) ] | (query) } TO { 'filename' | STDOUT } [ [ WITH ] [ BINARY ] [ DELIMITER [ AS ] 'delimiter_character' ] [ NULL [ AS ] 'null_string' ] [ CSV [ HEADER ] [ QUOTE [ AS ] 'quote_character' ] [ ESCAPE [ AS ] 'escape_character' ] [ FORCE QUOTE {column_name[, ...] | * } ] ] ]
Ten en cuenta que en esta sintaxis, BINARY y CSV se tratan como palabras clave independientes,
no como argumentos de una opción FORMAT.
La siguiente sintaxis se utilizaba antes de la versión 7.3 de PostgreSQL y todavía es compatible:
COPY [ BINARY ]table_nameFROM { 'filename' | STDIN } [ [USING] DELIMITERS 'delimiter_character' ] [ WITH NULL AS 'null_string' ] COPY [ BINARY ]table_nameTO { 'filename' | STDOUT } [ [USING] DELIMITERS 'delimiter_character' ] [ WITH NULL AS 'null_string' ]