Postgresql
如何在不使用 ON DELETE CASCADE 的情況下從具有不同外鍵的多個表中刪除數據?
我有以下 SELECT 語句:
SELECT * FROM "Users" u INNER JOIN "Calendars" c ON (u."UserId" = c."UserId") INNER JOIN "Actions" a ON (c."CalendarId" = a."Calendar_CalendarId") WHERE u."AuthenticationStatus" = 0 AND u."CreationDate" < now()::date - 7;
這會從三個表“使用者”、“日曆”和“操作”中正確選擇我想要的所有行。它通過將“Users”表的“UserId”與“Calendars”表的外鍵“UserId”以及“Calendars”表的“CalendarId”與“行動”表。
我想將其轉換為 DELETE 語句。我嘗試的是:
DElETE FROM "Users" u USING "Actions" a, "Calendars" c WHERE u."UserId" = c."UserId" AND c."CalendarId" = a."Calendar_CalendarId" AND u."AuthenticationStatus" = 0 AND u."CreationDate" < now()::date - 7;
但這說:
表“Calendars”上的更新或刪除違反了表“Actions”上的外鍵約束“FK_public.Actions_public.Calendars_Calendar_CalendarId”
詳細資訊:鍵 (CalendarId)=(2) 仍從表“Actions”中引用。
有誰知道我如何將此查詢轉換為 DELETE 語句?
您錯誤地解釋了 delete 語句的語義。使用
using
子句時,並不意味著記錄也會從這些表中刪除。相反,這些表純粹用於連接以確定需要從中刪除哪些行Users
。你基本上有三個選擇:
before delete on Users
刪除觸發器中的子行。on delete cascade
約束。- 以正確的順序對涉及的各種表執行多個刪除語句。
在某些情況下,我的偏好實際上是用於
on delete cascade
約束,但我不會在任何地方使用它們:只是為了能夠一次性刪除給定父級的所有子級的情況。我可能會將它用於“發票”和“發票行”。當您採用這種方法時,您需要確保只有真正需要能夠從父表中刪除的使用者才具有該權限——沒有使用者或應用程序以表所有者身份登錄!