Удалить строки из двух таблиц
-
20-08-2019 - |
Вопрос
У меня есть две таблицы.Между этими таблицами есть два отношения.
Table 1
* ID_XPTO (PK)
* Detail
Table 2
* ID_XPTO (FK) (PK)
* ID_XPTO2 (FK) (PK)
Эти два отношения существуют.
Table 1 -< Table2
Table 1 -< Table2
Мой вопрос в том, что мне нужно удалить некоторую строку в таблице 1.Я сейчас делаю,
declare @table Table (xptoTable2 int)
insert into @table
select ID_XPTO2
from Table2
where ID_XPTO = @ID_XPTO
delete from Table2
where ID_XPTO = @ID_XPTO
delete from Table
where ID_XPTO in (select xptoTable2from @table)
Я знаю, что могу использовать ON DELETE SET NULL в таблице2.Таким образом я мог бы найти все строки с нулевым значением в ID_XPTO2 и удалить их, но администратор базы данных не хочет их использовать.
Есть ли лучшее решение для этого процесса?
Решение
У вас есть следующие варианты:
Удалите в двух утверждениях, как вы делаете сейчас.Сначала удалите из Таблицы 2.
Удалить из двух таблиц одним оператором, если ваша база данных поддерживает многотаблицу.
DELETE
синтаксис (например,MySQL).Это не стандартный SQL, но он удобен.Используйте каскадные ограничения ссылочной целостности (я так понимаю, ваш администратор базы данных отменил эту опцию).
Напишите триггер
BEFORE DELETE
в Таблице 1, чтобы удалить или установить NULL любую ссылку в Таблице 2.Посоветуйтесь со своим администратором базы данных, не является ли это более приемлемым, чем ограничения каскадного RI.
Наконец, я бы посоветовал поговорить с вашим администратором базы данных и задать тот же вопрос, который вы задали здесь.Узнайте, какое решение он/она предпочел бы, чтобы вы использовали.Ребята из StackOverflow могут ответить на технические вопросы, но похоже, что вы имеете дело с вопрос ИТ-политики.
Другие советы
Использовать ON DELETE CASCADE
.Это автоматически удалить ссылки на строки.
Почему бы вам не использовать ON DELETE CASCASE
?
DROP TABLE t_f
DROP TABLE t_m
CREATE TABLE t_m (id INT NOT NULL IDENTITY PRIMARY KEY , value VARCHAR(50))
CREATE TABLE t_f (id INT NOT NULL IDENTITY PRIMARY KEY, m INT, CONSTRAINT fk_m FOREIGN KEY (m) REFERENCES t_m(id) ON DELETE CASCADE)
INSERT INTO t_m (value) VALUES ('test')
INSERT INTO t_f (m) VALUES (1)
DELETE FROM t_m
SELECT * FROM t_m
SELECT * FROM t_f
id value
------------ ------
0 rows selected
id m
------------ ------
0 rows selected
Два известных мне метода:
Вы можете использовать ON DELETE CASCADE
Напишите свой SQL для очистки после себя, т.е.:
DECLARE @DetailCriteria ... SET @DetailCriteria = '....' BEGIN TRAN -- First clear the Table2 of any child records DELETE FROM Table2 WHERE ID_XPTO IN (SELECT ID_XPTO FROM Table1 WHERE Detail = @DetailCriteria) OR ID_XPTO2 IN (SELECT ID_XPTO FROM Table1 WHERE Detail = @DetailCriteria) -- Next clear Table2 (which will delete fine because you've followed the referential chain) DELETE FROM Table1 WHERE Detail = @DetailCriteria -- commit if you're happy (should check @@ERROR first) COMMIT