PostgreSQL で外部キー制約を使用したカスケード親削除を実装するにはどうすればよいですか?

Linda Hamilton
リリース: 2024-10-31 22:34:29
オリジナル
972 人が閲覧しました

How to Implement Cascading Parent Deletion with Foreign Key Constraints in PostgreSQL?

外部キー制約を使用した親のカスケード削除

リレーショナル データベース システムでは、子の行を削除すると、多くの場合、親の削除が必要になります。他の子によって参照されなくなりました。このタスクは、PostgreSQL バージョン 9.1 以降で、データ変更 CTE (共通テーブル式) を使用して実行できます。

データ変更 CTE アプローチ

<code class="sql">WITH del_child AS (
    DELETE FROM child
    WHERE  child_id = 1
    RETURNING parent_id, child_id
    )
DELETE FROM parent p
USING  del_child x
WHERE  p.parent_id = x.parent_id
AND    NOT EXISTS (
   SELECT FROM child c
   WHERE  c.parent_id = x.parent_id
   AND    c.child_id <> x.child_id   -- !
   );</code>
ログイン後にコピー

これCTE はまず、指定された子行を削除します。次に、親 ID と削除された子 ID を返します。 2 番目の DELETE ステートメントは、この情報を使用して、他に子が残っていない場合に親行を削除します。条件 c.child_id <> x.child_id は、削除される子以外の子のみが考慮されることを保証します。

競合状態の排除

同時トランザクションが予期しない結果を引き起こす可能性がある潜在的な競合状態を防ぐため、削除プロセスの前に親行をロックできます。これは、CTE で FOR NO KEY UPDATE 句を使用して親行をロックすることによって実現されます。

<code class="sql">WITH lock_parent AS (
   SELECT p.parent_id, c.child_id
   FROM   child  c
   JOIN   parent p ON p.parent_id = c.parent_id
   WHERE  c.child_id = 12              -- provide child_id here once
   FOR    NO KEY UPDATE                -- locks parent row.
   )
 , del_child AS (
   DELETE FROM child c
   USING  lock_parent l
   WHERE  c.child_id = l.child_id
   )
DELETE FROM parent p
USING  lock_parent l
WHERE  p.parent_id = l.parent_id
AND    NOT EXISTS (
   SELECT FROM child c
   WHERE  c.parent_id = l.parent_id
   AND    c.child_id <> l.child_id   -- !
   );</code>
ログイン後にコピー

このアプローチでは、危険な DELETE 操作の実行が 1 つのトランザクションに制限され、同時実行の可能性が効果的に排除されます。干渉。

以上がPostgreSQL で外部キー制約を使用したカスケード親削除を実装するにはどうすればよいですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ソース:php.cn
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
著者別の最新記事
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート