Можно ли с помощью только одного запроса INSERT INTO добавить данные сразу в 2 таблицы?
Сразу скажу, что триггеры я ещё не изучал.
У меня тема JOIN.
По раздельности то добавить данные в 2 таблицы понятно как, что я и сделал. Но можно ли как-то провернуть это одним запросом с помощью JOIN? Вряд ли на данном этапе будет задание просто с двумя INSERT'ами.
Исходные таблицы тут https://dbfiddle.uk/CooZGvBH
СУБД MySQL
Ответы (2 шт):
Не бывает такого, насколько я знаю. Единственное что можно сделать - сделать два INSERT
-а через ;
.
INSERT INTO genres (name) VALUES ('Rap');
INSERT INTO artists (name, genre_id, is_group) VALUES ('Eminem', 6, False);
Решение в формате триггера.
Требуемый жанр передаётся в определённой пользователем переменной @genres
.
В случае пакетной вставки всем записям, у которых жанр не задан либо задан неправильно, будет присвоен жанр из переменной.
Обрабатываются варианты:
id
жанра указан, и такой существует (триггер ничего не делает)id
жанра указан, но такой не существует (обрабатывается, будто не указано)id
жанра не указан, переданное в переменной название существует (подставляется соотв. значение)id
жанра не указан, переданное в переменной название не существует (вставляется новая запись, подставляется её id)
CREATE TRIGGER tr_bi_artists
BEFORE INSERT ON artists
FOR EACH ROW
BEGIN
-- проверка, что genre_id задано, причём правильно
IF (SELECT name FROM genres WHERE id = NEW.genre_id) IS NULL THEN
-- проверка, что переданный в переменной @genre жанр отсутствует
-- если он существует - вставляем соотв. значение-ссылку
SET NEW.genre_id = (SELECT id FROM genres WHERE name = @genre);
-- если не существует - вставляем запись и заполняем поле ссылки
IF NEW.genre_id IS NULL THEN
INSERT INTO genres (name) VALUES (@genre);
SET NEW.genre_id = LAST_INSERT_ID();
END IF;
END IF;
END
fiddle (с дополнительными пояснениями)
Триггер не обрабатывает вариант, когда жанр не задан либо задан неправильно, и переменная @genre
не имеет значения (содержит NULL). В этом случае в genres вставится запись с name=NULL
. Однако по смыслу это поле должно быть определено как NOT NULL. Следует исправить структуру таблицы. Тогда описанный вариант приведёт к ошибке вставки, а не к вставке пустого значения. Если же "пустой" жанр легитимен и обозначает "не задано", замените простое сравнение на NULL-safe.
Если существуют дополнительные варианты - следует соотв. образом дополнить код.
PS. Значительную долю артистов относят обычно к более чем одному жанру. То есть должна быть связь много-ко-много и плюс связующая таблица. А там всё будет по-другому.