Postgres 9 \COPY FROM Command - Reserved Keyword - postgresql

I am having an issue trying to run \copy command where my column name is desc
I've tried the following:
psql -U user -p 1234 -h hostname -c "\copy schema.table (desc) from /my/file.txt WITH DELIMITER '|' HEADER CSV " db
psql -U user -p 1234 -h hostname -c "\copy schema.table ('desc') from /my/file.txt WITH DELIMITER '|' HEADER CSV " db
psql -U user -p 1234 -h hostname -c "\copy schema.table ("desc") from /my/file.txt WITH DELIMITER '|' HEADER CSV db
I get the same error everytime:
ERROR: syntax error at or near "desc"
I can't seem to get around it. Is there something that I am missing?

just escape double quotes, like here:
vao#vao-X102BA:~$ psql -c "copy s1(\"desc\") from stdin;"
Enter data to be copied followed by a newline.
End with a backslash and a period on a line by itself.
>> b
>> \.
COPY 1
vao#vao-X102BA:~$ psql
psql (9.6.3)
Type "help" for help.
vao=# select * from s1;
i | desc
---+------
| a
| b
(2 rows)

Related

[Windows 10]Problem escaping dollar sign contained in tablename for /copy command in psql

I am trying to setup a shell script to insert data from .csv files into postgreSQL. As a first test I just tried rto do it in terminal command, and I am running into an issue because my table has a '$' in its name and I was not able to come up with the proper way to escape it so far.
My command look like this :
psql -d trm -h localhost -p 5432 -U postgres -c "\COPY ts_dev.tbl$trm_secndry_readings from 'FILEPATH' with delimiter ',' ;"
I have made several test, with this command, if tablename='test1' the command works, but if tablename='prefix&test1' then the command fails as terminal is trying to parse what is after '$' as a variable name
So for example :
psql -d trm -h localhost -p 5432 -U postgres -c "\COPY schtest.prefix$name from 'FILEPATH' with delimiter ',' ;"
ERROR: relation "schtest.prefix" does not exist
I'm using Windows powershell.
In both POSIX-compatible shells such as bash and in PowerShell, $ is a metacharacter, which - in unquoted use or inside "..." - requires escaping in order to be interpreted verbatim (in order to be passed through to a command as-is).
However, the escape character differs between these two shells:
For POSIX-compatible shells it is \:
psql -d trm -h localhost -p 5432 -U postgres -c "\COPY ts_dev.tbl\$trm_secndry_readings from 'FILEPATH' with delimiter ',' ;"
For PowerShell it is ` (the so-called backtick; see about_Special_Characters):
psql -d trm -h localhost -p 5432 -U postgres -c "\COPY ts_dev.tbl`$trm_secndry_readings from 'FILEPATH' with delimiter ',' ;"
you can add escaped double quotes around the table name
psql -d trm -h localhost -p 5432 -U postgres -c "\COPY
\"ts_dev.tbl$trm_secndry_readings\" from 'FILEPATH' with delimiter ',' ;"

Psql output csv file formatting

Trying to make batch file that will get query from script file and put results into csv.
Batch file code:
psql -h host -d test -U test -p 5432 -a -q -f C:\Users\test\Documents\my_query.sql TO STDOUT WITH CSV HEADER DELIMITER ';' > C:\Users\test\Documents\res.csv
In result file I'm getting result like this:
select *
from public.test
limit 3
id | name | count_01
----------+------------+---------------+
11021555 | a | 1 |
39534568 | b | 2 |
11695210 | c | 3 |
(3 rows)
How to get only script results without rows count and symbols like '|' or '+' and using ';' delimetres as in the usual csv file?
Working script:
psql -h host -d test -U test -p 5432 -q --quiet --no-align --field-separator=';' --file=C:\Users\test\Documents\my_query.sql --output=C:\Users\test\Documents\res.csv
From PostgreSQL v12 on, you can use the CSV output format of psql:
psql --quiet --csv --file=my_query.sql --output=res.csv
--quiet suppresses the psql welcome message.
Should work with
psql -h host -d dbname -U user -p port -a -q -f my_query.sql -o res.csv --record-separator=',' --csv

Split a big postgres table into multiple csv

I am using following psql query to connect to a remote host and split a big table into multiple csv files.
psql -h xx -p xx -U xx -d xx -c "\COPY (select * from table) TO program 'split --lines 1000' (format csv)
I am not getting what mistake I am making here.
Have you tried using STDOUT?
$ psql -d db -c "COPY (SELECT * FROM t) TO STDOUT CSV " | split -1000

Psql output to file with column alias starting with number

I am running psql from command line and sending output to a file. It is a simple select statement on a view, but I am getting a syntax error when I have a column alias that starts with a number.
I ran the query in PgAdmin and it works (which makes me believe that this is some sort of issue with psql). I also tried adding a '_' to the beginning of the alias and that allows it to go through.
works: 'abc as "_1abc"'
doesn't work: 'abc as "1abc"'
psql -u <username> -h <host> -p <port> -d <DB> -o <outputfile> -A -c
"SELECT abc as "1abc" From example.view
This is the error I get:
ERROR: syntax error at or near "1"
It is a problem with nested double quotes. You need to escape the inner ones.
psql -u <username> -h <host> -p <port> -d <DB> -o <outputfile> -A -c "SELECT abc as \"1abc\" From example.view"

How do you print the result of a PostgreSQL query in CSV or TSV format from the command line?

I'd like to execute a query from the shell (not in the interactive psql client) and have it print the CSV or TSV representation of the output to STDOUT. How do you do that with psql or one of the PostgreSQL command-line tools?
If you are using PostgreSQL 8.2 or newer, use this for CSV:
psql -c "COPY (<select query>) TO STDOUT WITH CSV"
and this of TSV, with proper NULLs:
psql -c "COPY (<select query>) TO STDOUT WITH NULL AS ''"
The CSV form will properly quote any fields that contain the double-quote character. See the PostgreSQL documentation of your specific version for more details and options for COPY.
Starting from Bohemian's answer, I found these flags useful:
psql my_database -U myuser -A -F , -X -t -f /path/to/query.sql -o /path/to/output.csv
Unaligned output mode: -A
Use comma as field delimiter: -F ,
Do not read psqlrc: -X
Tuples only (no header/footer): -t
File containing SQL query: -f
Output file: -o
EDITED: Using -F
Use commas via -F and use "unaligned table output mode" -A:
psql my_database -U myuser -A -F , -c "select * from mytable"
To specify a tsv use the delimiter '\t'
psql my_database -U myuser -F'\t' --no-align -f mysqlfile.sql -o outputfile.tsv
To specify a csv use the delimiter ','
psql my_database -U myuser -F',' --no-align -f mysqlfile.sql -o outputfile.csv
The simplest way (using psql) seems to be by using --csv flag:
psql --csv -c "SELECT * FROM sometable"
Also possible is the copy command which allows you to specify header, delimiters and quoting options
psql my_database -U my_user -c "copy (select a.id,b.id from my_table_a as a inner join my_table_b as b on b.id = a.id) to STDOUT"
You can specify the field separator with the -F command line parameter to psql
Export AS TSV WITH HEADER
You can include the HEADER as follows:
\COPY (SELECT * FROM tca) TO '/.../metab/tca.tsv' WITH DELIMITER E'\t' CSV HEADER;
\COPY (SELECT * FROM tca) TO '/...a/metab/tca.tsv' WITH NULL AS '' DELIMITER E'\t' CSV HEADER;
E.g. (PSQL):
[metabolism]# \COPY (SELECT * FROM tca) TO '/mnt/Vancouver/programming/data/metabolism/tca.tsv' WITH NULL AS '' DELIMITER E'\t' CSV HEADER;
COPY 22
BASH:
[victoria#victoria tsv]$ pwd
/mnt/Vancouver/programming/data/metabolism/tsv
[victoria#victoria tsv]$ head -n3 tca.tsv
uuid src tgt rel rel_type
878b87de-0ca8-49a8-9f77-a24353e251d2 oxalosuccinic acid oxoglutaric acid 1.1.1.42 2
7fd9cf88-495b-491b-956e-294f19097923 isocitric acid oxoglutaric acid 1.1.1.41 2
[victoria#victoria csv]$