postgresql — Как выполнить ‘Upsert’ программно, используя php в postgres

Upsert это отличная новинка в PG (мы недавно обновили базу данных для ее использования), и теперь мы пытаемся написать адаптер upsert на PHP, чтобы его использование было простым.

Вот что мы должны сделать, если хотим оторваться:

INSERT INTO {$this->_name} AS t ({$insertCols}) VALUES ({$insertVals})
ON CONFLICT {$onConflict} DO UPDATE
SET {$updateVals}
WHERE {$updateWhere}

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

ModelTable()->getInstance()->getAdapter->upsert($data, $onConflict, $where);
//e.g.
ModelTable()->getInstance()->getAdapter->upsert(['name=>'Denis', 'age'=>36], '(name)', "name = 'Denis'");

В этом случае использование более удобно, но проблема в том, что нам нужно знать имя (имена) столбца ограничения или само имя ограничения, чтобы поместить его в переменную $ onConflict. переменная '(name)' в примере выше.

Если кто-то добавит другое ограничение к этой таблице или переименует старое, весь код php, который работает с этой таблицей, должен быть обновлен, чтобы добавить новые ограничения.

Идеальный адаптер должен выглядеть как обычный адаптер обновления:

ModelTable()->getInstance()->getAdapter->upsert(['name=>'Denis', 'age'=>36], "name = 'Denis'");

Так что, если строка с name = Denis существует, будет обновлено, если не существует, его следует создать.

Таким образом, вопрос — как создать рекламодатель в php, который будет работать таким образом? Мы знаем имя столбца, по которому должна быть обновлена ​​строка, поэтому должна быть возможность построить ON CONFLICT ... DO UPDATE предложение. Я хочу сделать обновление на любой конфликт, так же, как это было бы с

try {
...insert
} catch (Exception $e) {
...update
}

который мы используем сейчас.

Спасибо.

1

Решение

То, как вы хотите реализовать upsert как ловить \Exception означает «Если вставка не работает по какой-либо причине, я пытаюсь обновить затем.» Признайте, что это реальное отсутствие контроля над доменом. Вы можете захотеть, чтобы строки обновлялись при конфликте с первичным ключом, но отклонялись, когда они конфликтовали с уникальным полем в той же таблице, например.

Причины конфликта принадлежат модели, это бизнес-правила, явно реализованные в виде ограничений. Только уровень модели знает, почему он отклонит вставку и обновит строку. Так что это не может быть общая команда upsert, которую вы можете вызывать во всех таблицах независимо от определения домена.

Это означает, что это ModelTable экземпляр, который знает, почему запись будет конфликтовать с существующими данными так же, как он знает структуру таблицы (как я предполагаю из вашего примера).

0

Другие решения

Других решений пока нет …

По вопросам рекламы ammmcru@yandex.ru
Adblock
detector