WPDB Вставить или, если существует, Обновить

21

Я не очень знаком с WPDB или SQL в целом, но у меня есть настраиваемая таблица для моего проекта, и я пытаюсь присвоить ей некоторые метаданные. То, что я «хотел бы», - это если строка существует, обновите ее, а если не вставьте. Я прочитал «Вставить и обновить» в Кодексе WPDB, но ни один из них не попал в ситуацию «или» или «. Я думал, что смогу работать с обновлением, поэтому мой код выглядит так:

$wpdb->update(
    $wpdb->prepare(
        $wpdb->prefix.'item_info',
        array(
            'post_id'       => $post_id,
            'item_stock'    => $item_stock
        ),
        array('post_id' => $post_id)
    )
);

Есть ли в WordPress что-то вроде «если существует обновление, вставка ELSE», или мне нужно запустить собственный SQL для этого, или мне сначала нужно запросить базу данных, чтобы узнать, существует ли идентификатор в моей таблице, ТОГДА решите, нужно ли обновлять это или вставить это?

Howdy_McGee
источник

Ответы:

23

Во-первых, вы используете prepareнеправильно. Похоже, у вас есть $wpdb->updateаргументы, обернутые $wpdb->prepareтаким образом. Это не сработает. По сути, вы передаете updateодин аргумент - вывод prepare. Попробуйте что-нибудь простое, например, следующее, и вы поймете, почему это не сработает:

$post_id = 123;
$item_stock = 567;
var_dump(
  $wpdb->prepare(
    $wpdb->prefix.'item_info',
    array(
        'post_id'       => $post_id,
        'item_stock'    => $item_stock
    ),
    array('post_id' => $post_id)
  )
);

И $wpdb->update()бежит prepareза тобой .

Во-вторых, если бы это был я, я пропускаю функцию-помощник и напишу правильный ON DUPLICATE KEY UPDATEзапрос:

$sql = "INSERT INTO {$wpdb->prefix}item_info (post_id,item_stock) VALUES (%d,%s) ON DUPLICATE KEY UPDATE item_stock = %s";
// var_dump($sql); // debug
$sql = $wpdb->prepare($sql,$post_id,$item_stock,$item_stock);
// var_dump($sql); // debug
$wpdb->query($sql);

Это предполагает, что post_idэто UNIQUEиндекс илиPRIMARY KEY . Если ваша структура таблицы такая, как я думаю, пусть база данных справится с этим.

s_ha_dum
источник
Это было безумно полезно ... Спасибо за ваше время s_ha_dum!
Джейк
Prepare возвращает false для меня - никаких других ошибок БД. Если запрос выполняется вручную в phpmyadmin, он работает как положено. Также проверил, что переменные такие, какими они должны быть. Есть идеи?
trainoasis
1
Что если post_id не ПЕРВИЧНЫЙ КЛЮЧ?
Майк Корменди
18

Вы пробовали $wpdb->replace. Согласно WP Codex:

Замените строку в таблице, если она существует, или вставьте новую строку в таблицу, если строка еще не существовала.

Я пробовал себя в некоторых плагинах, и он работает, пытаясь избежать ошибок дублирования уникальных идентификаторов и т. Д.

Больше информации в кодексе

е-Креспо
источник
Это сработало для меня, в то время как пользовательский запрос не
помог
Это правильный ответ на вопрос.
Тайлер Джонс
6
Стоит отметить, что $wpdb->replaceэто разрушительная перезапись всей записи, тогда как $wpdb->updateобновляются только определенные поля, включенные в $dataмассив
MatthewLee
0

Вы должны проверить, существует ли строка в первую очередь.

Скорее всего, вы захотите получить идентификатор или первичный ключ для строки, которую вы пытаетесь обновить, тогда, $wpdb->updateесли это произойдет или $wpdb->insertнет

felipelavinz
источник
14
Пример того, как проверить, существует ли идентификатор или первичный ключ, действительно сделал бы этот ответ полезным. Это почти как повторение вопроса.
Джейк