Відповіді:
Ви хочете отриманий файл на сервері чи на клієнті?
Якщо ви хочете щось легко використати або автоматизувати, ви можете використовувати вбудовану команду COPY Postgresql . напр
Copy (Select * From foo) To '/tmp/test.csv' With CSV DELIMITER ',' HEADER;
Цей підхід працює повністю на віддаленому сервері - він не може записувати на ваш локальний ПК. Його також потрібно запускати як "суперпользователь" Postgres (зазвичай його називають "root"), оскільки Postgres не може зупинити його робити неприємні дії з локальною файловою системою цієї машини.
Це на самому ділі не означає , що ви повинні бути підключені як привілейований користувач (автоматизації , що буде представляти загрозу безпеці іншого роду), тому що ви можете використовувати в SECURITY DEFINERможливістьCREATE FUNCTION зробити функцію , яка працює , як якщо б ви були суперкористувача .
Найважливіша частина полягає в тому, що ваша функція полягає в тому, щоб виконувати додаткові перевірки, а не просто обходити безпеку - щоб ви могли написати функцію, яка експортує точні потрібні вам дані, або ви можете написати щось, що може приймати різні варіанти, якщо вони зустріти суворий білий список. Вам потрібно перевірити дві речі:
GRANTs в базі даних, але функція зараз працює як суперпользователь, тому таблиці, які зазвичай не знаходяться ", будуть повністю доступними. Напевно, ви не хочете, щоб хтось посилався на вашу функцію та додавав рядки в кінці таблиці ваших користувачів ...Я написав публікацію в блозі, яка розширює цей підхід , включаючи деякі приклади функцій, які експортують (або імпортують) файли та таблиці, що відповідають суворим умовам.
Інший підхід - це обробка файлів на стороні клієнта , тобто у вашій програмі чи сценарії. Серверу Postgres не потрібно знати, у який файл ви копіюєте, він просто виплює дані, і клієнт десь розміщує їх.
Основним синтаксисом для цього є COPY TO STDOUTкоманда, а графічні інструменти, такі як pgAdmin, перетягнуть її в хороший діалог.
psqlКлієнт командного рядка має спеціальний «мета-команду» під назвою \copy, який приймає всі ті ж параметри , як «реальні» COPY, але запускається всередині клієнта:
\copy (Select * From foo) To '/tmp/test.csv' With CSV
Зауважте, що немає завершення ;, оскільки метакоманди завершуються новим рядком, на відміну від команд SQL.
З документів :
Не плутати COPY з інструкцією psql \ copy. \ копіює виклики COPY OF STDIN або COPY TO STDOUT, а потім отримує / зберігає дані у файлі, доступному клієнту psql. Таким чином, доступність файлів та права доступу залежать від клієнта, а не від сервера, коли використовується \ copy.
Ваша мова програмування додатків може також мати підтримку для виштовхування або отримання даних, але зазвичай не можна використовувати COPY FROM STDIN/ TO STDOUTв стандартному операторі SQL, оскільки немає способу підключення потоку вводу / виводу. Обробник PostgreSQL PHP ( не PDO) включає в себе дуже основні pg_copy_fromта pg_copy_toфункції, які копіюють в / з масиву PHP, що може бути неефективним для великих наборів даних.
\copyтеж працює - там шляхи відносно клієнта, і крапка з комою не потрібна / дозволена. Дивіться мою редакцію.
\copyпотрібно бути однолінійним. Таким чином, ви не отримаєте красу форматування sql так, як вам потрібно, а просто помістіть навколо нього копію / функцію.
\copyце спеціальна мета-команда в psqlклієнтському командному рядку . Він не працюватиме в інших клієнтах, таких як pgAdmin; вони, можливо, матимуть власні інструменти, такі як графічні майстри, для виконання цієї роботи.
Є кілька рішень:
psqlкомандаpsql -d dbname -t -A -F"," -c "select * from users" > output.csv
Це має велику перевагу в тому, що ви можете користуватися ним через SSH, наприклад, ssh postgres@host command- це дозволяє вам отримати
copyкоманда postgresCOPY (SELECT * from users) To '/tmp/output.csv' With CSV;
>psql dbname
psql>\f ','
psql>\a
psql>\o '/tmp/output.csv'
psql>SELECT * from users;
psql>\q
Усі вони можуть бути використані в сценаріях, але я віддаю перевагу №1.
У терміналі (при підключенні до db) встановіть висновок у файл cvs
1) Встановіть сепаратор поля на ',':
\f ','
2) Встановити вихідний формат нерівномірно:
\a
3) Показати лише кортежі:
\t
4) Встановити вихід:
\o '/tmp/yourOutputFile.csv'
5) Виконайте свій запит:
:select * from YOUR_TABLE
6) Вихід:
\o
Потім ви зможете знайти свій файл csv у цьому місці:
cd /tmp
Скопіюйте його за допомогою scpкоманди або відредагуйте за допомогою nano:
nano /tmp/yourOutputFile.csv
COPYабо \copyпідходять правильно (перетворюють у стандартний формат CSV); це робить?
Якщо вас цікавлять усі стовпці певної таблиці разом із заголовками, ви можете використовувати
COPY table TO '/some_destdir/mycsv.csv' WITH CSV HEADER;
Це крихітно трохи простіше, ніж
COPY (SELECT * FROM table) TO '/some_destdir/mycsv.csv' WITH CSV HEADER;
які, наскільки мені відомо, рівнозначні.
Ця інформація насправді недостатньо представлена. Оскільки це вже другий раз, коли мені потрібно було це зробити, я поставлю це тут, щоб нагадати про себе, якщо нічого іншого.
Дійсно, найкращий спосіб зробити це (вивести CSV з постгресів) - використовувати COPY ... TO STDOUTкоманду. Хоча ви не хочете робити це так, як показано у відповідях тут. Правильний спосіб використання команди:
COPY (select id, name from groups) TO STDOUT WITH CSV HEADER
Це чудово для використання над ssh:
$ ssh psqlserver.example.com 'psql -d mydb "COPY (select id, name from groups) TO STDOUT WITH CSV HEADER"' > groups.csv
Він відмінно підходить для використання всередині докера над ssh:
$ ssh pgserver.example.com 'docker exec -tu postgres postgres psql -d mydb -c "COPY groups TO STDOUT WITH CSV HEADER"' > groups.csv
Це навіть чудово на локальній машині:
$ psql -d mydb -c 'COPY groups TO STDOUT WITH CSV HEADER' > groups.csv
Або всередині докера на локальній машині ?:
docker exec -tu postgres postgres psql -d mydb -c 'COPY groups TO STDOUT WITH CSV HEADER' > groups.csv
Або на кластері кубернетів, у докері, над HTTPS ??:
kubectl exec -t postgres-2592991581-ws2td 'psql -d mydb -c "COPY groups TO STDOUT WITH CSV HEADER"' > groups.csv
Так універсально, багато коми!
Так, я зробив, ось мої замітки:
Використання /copyефективно виконує операції з файлами в будь-якій системі, на якій працює psqlкоманда, як користувач, який її виконує 1 . Якщо ви підключитесь до віддаленого сервера, просто скопіювати файли даних у систему, що виконується psqlна / з віддаленого сервера.
COPYвиконує операції з файлами на сервері, оскільки обліковий запис користувача процесу резервного копіювання (за замовчуванням postgres), шляхи та дозволи файлів перевіряються та застосовуються відповідно. Якщо використовується, TO STDOUTтоді перевірки дозволів на файл обходять.
Обидва ці варіанти вимагають подальшого переміщення файлів, якщо psqlвін не виконується в системі, де ви хочете, щоб результат CSV в кінцевому рахунку знаходився. Це, швидше за все, з мого досвіду, коли ви в основному працюєте з віддаленими серверами.
Складніше налаштувати щось на зразок тунелю TCP / IP через ssh для віддаленої системи для простого виводу CSV, але для інших форматів виводу (бінарних) може бути краще, /copyніж через тунельне з'єднання, виконуючи локальне psql. Аналогічно, для великого імпорту переміщення вихідного файлу на сервер та використання COPY, мабуть, найбільш ефективний варіант.
За допомогою параметрів psql ви можете відформатувати вихід, як CSV, але є й такі недоліки, як пам’яті, щоб вимкнути пейджер і не отримувати заголовки:
$ psql -P pager=off -d mydb -t -A -F',' -c 'select * from groups;'
2,Technician,Test 2,,,t,,0,,
3,Truck,1,2017-10-02,,t,,0,,
4,Truck,2,2017-10-02,,t,,0,,
Ні, я просто хочу вивести CSV зі свого сервера без компіляції та / або встановлення інструменту.
psql може це зробити для вас:
edd@ron:~$ psql -d beancounter -t -A -F"," \
-c "select date, symbol, day_close " \
"from stockprices where symbol like 'I%' " \
"and date >= '2009-10-02'"
2009-10-02,IBM,119.02
2009-10-02,IEF,92.77
2009-10-02,IEV,37.05
2009-10-02,IJH,66.18
2009-10-02,IJR,50.33
2009-10-02,ILF,42.24
2009-10-02,INTC,18.97
2009-10-02,IP,21.39
edd@ron:~$
Зверніться man psqlза допомогою до параметрів, які використовуються тут.
Нова версія - psql 12 - підтримуватиме --csv.
--csv
Перемикається на вихідний режим CSV (значення, розділені комами). Це еквівалентно \ pset формату csv .
csv_fieldsep
Вказує роздільник поля, який буде використовуватися у вихідному форматі CSV. Якщо символ роздільника відображається у значенні поля, це поле виводиться в подвійних лапки, дотримуючись стандартних правил CSV. За замовчуванням - кома.
Використання:
psql -c "SELECT * FROM pg_catalog.pg_tables" --csv postgres
psql -c "SELECT * FROM pg_catalog.pg_tables" --csv -P csv_fieldsep='^' postgres
psql -c "SELECT * FROM pg_catalog.pg_tables" --csv postgres > output.csv
У pgAdmin III є можливість експорту у файл із вікна запиту. У головному меню це Query -> Execute to file або є кнопка, яка робить те саме (це зелений трикутник із синьою дискетою на відміну від звичайного зеленого трикутника, який просто виконує запит). Якщо ви не запускаєте запит у вікні запиту, я б зробив те, що запропонував IMSoP, і скористався командою копіювання.
Я написав невеликий інструмент під назвою, psql2csvякий інкапсулює COPY query TO STDOUTвізерунок, в результаті чого з'являється правильний CSV. Його інтерфейс схожий на psql.
psql2csv [OPTIONS] < QUERY
psql2csv [OPTIONS] QUERY
Запит вважається вмістом STDIN, якщо він присутній, або останнім аргументом. Усі інші аргументи передаються в psql, крім цих:
-h, --help show help, then exit
--encoding=ENCODING use a different encoding than UTF8 (Excel likes LATIN1)
--no-header do not output a header
Якщо у вас є більш тривалий запит, і ви хочете використовувати psql, тоді поставте свій запит у файл і скористайтеся такою командою:
psql -d my_db_name -t -A -F";" -f input-file.sql -o output-file.csv
-F","замість того, -F";"щоб генерувати файл CSV, який би відкрився правильно у MS Excel
Я дуже рекомендую DataGrip , IDE бази даних від JetBrains. Ви можете експортувати SQL-запит у файл CSV та легко налаштувати ssh-тунелювання. Коли документація посилається на "набір результатів", вони означають результат, повернений запитом SQL в консолі.
Я не пов'язаний з DataGrip, я просто люблю продукт!
JackDB , клієнт бази даних у вашому веб-браузері, робить це дуже просто. Особливо, якщо ти на Хероку.
Він дозволяє підключатися до віддалених баз даних і запускати на них SQL запити.
Джерело
(джерело: jackdb.com )
Після підключення БД ви можете запустити запит та експортувати в CSV або TXT (див. Праворуч внизу).

Примітка. Я жодним чином не пов'язаний з JackDB. Зараз я користуюся їхніми безкоштовними послугами і думаю, що це чудовий продукт.
На запит @ skeller88 я надсилаю свій коментар як відповідь, щоб люди не втрачали кожної відповіді ...
Проблема з DataGrip полягає в тому, що він утримує ваш гаманець. Це не безкоштовно. Спробуйте спільне видання DBeaver на dbeaver.io. Це багатоплатформенний засіб баз даних FOSS для програмістів SQL, DBA та аналітиків, який підтримує всі популярні бази даних: MySQL, PostgreSQL, SQLite, Oracle, DB2, SQL Server, Sybase, MS Access, Teradata, Firebird, Hive, Presto тощо.
DBeaver Community Edition робить тривіальним підключення до бази даних, видавати запити для отримання даних, а потім завантажувати набір результатів, щоб зберегти їх у CSV, JSON, SQL або інших поширених форматах даних. Це життєздатний конкурент FOSS TOAD для Postgres, TOAD для SQL Server або Toad for Oracle.
Я не маю приналежності до DBeaver. Мені подобається ціна та функціональність, але я б хотів, щоб вони більше відкривали додаток DBeaver / Eclipse і полегшували додавання віджетів аналітики до DBeaver / Eclipse, а не вимагати від користувачів плати за щорічну підписку для створення графіків та діаграм безпосередньо в межах додаток. Мої навички кодування Java іржавіють, і мені не хочеться витрачати тижні, щоб вивчити, як створювати віджети Eclipse, лише щоб виявити, що DBeaver відключив можливість додавання сторонніх віджетів до DBeaver Community Edition.
Чи мають користувачі DBeaver розуміння кроків для створення віджетів аналітики для додавання до спільноти DBeaver Community?
import json
cursor = conn.cursor()
qry = """ SELECT details FROM test_csvfile """
cursor.execute(qry)
rows = cursor.fetchall()
value = json.dumps(rows)
with open("/home/asha/Desktop/Income_output.json","w+") as f:
f.write(value)
print 'Saved to File Successfully'