Вставки нескольких значений в PostgreSQL

возможно ли выполнить многозначную апсерт в PostgreSQL? Я знаю, что существуют вставки с несколькими значениями, как и ключевые слова «ON CONFLICT» для выполнения обновления, если ключ нарушен... но возможно ли объединить их? Как-то так...

INSERT INTO table1(col1, col2) VALUES (1, 'foo'), (2,'bar'), (3,'baz')
ON CONFLICT ON CONSTRAINT theConstraint DO
UPDATE SET (col2) = ('foo'), ('bar'), ('baz')

Я гуглил crud из этого и не мог найти ничего об этом.

У меня есть приложение, использующее pg-promise, и я выполняю пакетную обработку. Он работает, но ужасно медленно (например, 50 строк каждые 5 секунд или около того...). Я подумал, что если бы я мог покончить с пакетной обработкой и вместо этого правильно построить этот многозначный запрос upsert, это могло бы повысить производительность.

Редактировать: Ну... Я только что попробовал это сам, и нет, это не работает. Если я не делаю это неправильно. Итак, теперь я думаю, что мой вопрос изменился на то, какой хороший способ реализовать что-то подобное?


person dvsoukup    schedule 17.11.2016    source источник
comment
Возможный дубликат многострочных обновлений PostgreSQL в Node.js   -  person vitaly-t    schedule 17.11.2016
comment
Спасибо, @vitaly-t. Я собираюсь использовать некоторые из этих шаблонов в сочетании с построением запросов в ответе ниже. Я пропустил важную ИСКЛЮЧЕННУЮ часть upsert. Спасибо за этого человека с библиотекой pg-promise... широко использовал его, и это просто фантастика!!!   -  person dvsoukup    schedule 17.11.2016
comment
Это, возможно, ближе к вашему вопросу: Многострочная вставка с pg-promise.   -  person vitaly-t    schedule 18.11.2016


Ответы (2)


Многозначный upsert определенно возможен, и значительная часть почему вставка... при конфликте... была реализована.

CREATE TABLE table1(col1 int, col2 text, constraint theconstraint unique(col1));

INSERT INTO table1 VALUES (1, 'parrot'), (4, 'turkey');

INSERT INTO table1 VALUES (1, 'foo'), (2,'bar'), (3,'baz')
ON CONFLICT ON CONSTRAINT theconstraint
DO UPDATE SET col2 = EXCLUDED.col2;

приводит к

regress=> SELECT * FROM table1 ORDER BY col1;
 col1 | col2 
------+------
    1 | foo
    2 | bar
    3 | baz
    4 | turkey
(4 rows)

Если документы были неясными, отправьте соответствующий отзыв в список рассылки pgsql-general. Или, что еще лучше, предложите патч к документации.

person Craig Ringer    schedule 17.11.2016
comment
Круто, спасибо большое!! По своей глупости я не рассмотрел специальное выражение EXCLUDED. Нашел это в вики postgres... хотя немного скрыт в документации ON CONFLICT: -- Многострочная вставка или обновление со ссылкой на отклоненные кортежи с использованием специального выражения EXCLUDED.*: - person dvsoukup; 17.11.2016

1. Перед вставкой

введите здесь описание изображения

2.Команда

введите здесь описание изображения

3.После вставки

введите здесь описание изображения

person liyuhui    schedule 15.09.2017