PostgreSQL
 sql >> база данни >  >> RDS >> PostgreSQL

Как да актуализирам избрани редове със стойности от CSV файл в Postgres?

COPY файла във временна професионална таблица и актуализирайте действителната таблица от там. Като:

CREATE TEMP TABLE tmp_x (id int, apple text, banana text); -- but see below

COPY tmp_x FROM '/absolute/path/to/file' (FORMAT csv);

UPDATE tbl
SET    banana = tmp_x.banana
FROM   tmp_x
WHERE  tbl.id = tmp_x.id;

DROP TABLE tmp_x; -- else it is dropped at end of session automatically

Ако импортираната таблица съвпада точно с таблицата, която трябва да се актуализира, това може да е удобно:

CREATE TEMP TABLE tmp_x AS SELECT * FROM tbl LIMIT 0;

Създава празна временна таблица, съответстваща на структурата на съществуващата таблица, без ограничения.

Привилегии

До Postgres 10, SQL COPY изисква привилегии на суперпотребител за това.
В Postgres 11 или по-нова версия има и някои предварително дефинирани роли (по-рано „роли по подразбиране“), които позволяват това. Ръководството:

COPY именуването на файл или команда е разрешено само на суперпотребители на база данни или потребители, на които е предоставена една от ролите pg_read_server_files ,pg_write_server_files или pg_execute_server_program [...]

psql метакоманда \copy работи за всяка db роля. Ръководството:

Извършва фронтенд (клиентско) копие. Това е операция, която изпълнява anSQL COPY команда, но вместо сървърът да чете или записва посочения файл, psql чете или записва файла и насочва данните между сървъра и локалната файлова система. Това означава, че достъпността до файловете и привилегиите са тези на локалния потребител, а не на сървъра и не се изискват привилегии на суперпотребител на SQL.

Обхватът на временните таблици е ограничен до една сесия на една роля, така че горното трябва да се изпълни в същата psql сесия:

CREATE TEMP TABLE ...;
\copy tmp_x FROM '/absolute/path/to/file' (FORMAT csv);
UPDATE ...;

Ако скриптирате това в bash команда, не забравяйте да го обвиете в единична psql повикване. Като:

echo 'CREATE TEMP TABLE tmp_x ...; \copy tmp_x FROM ...; UPDATE ...;' | psql

Обикновено се нуждаете от метакомандата \\ за превключване между psql мета команди и SQL команди в psql, но \copy е изключение от това правило. Отново ръководството:

специални правила за синтактичен анализ се прилагат за \copy мета-команда. За разлика от повечето други мета-команди, цялата останала част от реда винаги се приема като аргументи на \copy и в аргументите не се извършват нито интерполация на променлива, нито разширяване на обратни кавички.

Големи маси

Ако таблицата за импортиране е голяма, може да си струва да увеличите temp_buffers временно за сесията (първото нещо в сесията):

SET temp_buffers = '500MB';  -- example value

Добавете индекс към временната таблица:

CREATE INDEX tmp_x_id_idx ON tmp_x(id);

И стартирайте ANALYZE ръчно, тъй като временните таблици не са обхванати от автоматично вакуумиране/автоматичен анализ.

ANALYZE tmp_x;

Свързани отговори:

  • Най-добрият начин да изтриете милиони редове по идентификатор
  • Как мога да вмъкна общи данни във временна таблица от различни схеми?
  • Как да изтрия дублиращи се записи?


  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Как да изброите всички бази данни с помощта на PostgreSQL

  2. Архитектура и настройка на паметта в PostgreSQL бази данни

  3. Достъп до външни XML файлове като променливи в PSQL скрипт (източник от bash скрипт)

  4. Как да създадете Postgres таблица с уникален комбиниран първичен ключ?

  5. Разлика между индекса GiST и GIN