これは私が作成しようとしているデータベースの単純化されたバージョンです:
create table Worker (
ID int,
constraint PKW
primary key (ID)
)
create table Business (
ID int,
W int,
constraint PKB
primary key (ID),
constraint FKBW
foreign key (W) references Worker (ID)
on delete set null on update cascade
)
create table Note (
ID int,
B int,
W int,
constraint PKN
primary key (ID),
constraint FKNB
foreign key (B) references Business (ID)
on delete cascade on update cascade,
constraint FKNW
foreign key (W) references Worker (ID)
on delete set null on update cascade
)
基本的に、各ビジネスには労働者が割り当てられており、どの労働者もあらゆるビジネスに関するメモを作成できます。これらの関係を反映する3つの外部キー制約がありますが、これによりエラーが発生します。
テーブル 'Note'にFOREIGN KEY制約 'FKNW'を導入すると、サイクルまたは複数のカスケードパスが発生する可能性があります。 ON DELETE NO ACTIONまたはON UPDATE NO ACTIONを指定するか、他のFOREIGN KEY制約を変更してください。
このセットアップには関係サイクルはありません。 FKBW on delete cascade
を使用すると、Noteへの削除パスが2つ作成されることがわかりますが、現在の設定ではそうではありません。 FKBWとFBNWの両方からon update cascade
を削除しても、エラーが解決しません。 set null
がどのように問題を引き起こすのかわかりません。
どんな明快さもいただければ幸いです!
問題はON UPDATE CASCADE
sのようです。ON DELETE
sで問題ありません。 ON UPDATE
sを削除してもエラーになりません。
で受け入れられた回答によると、「外部キー制約により、サイクルまたは複数のカスケードパスが発生する可能性があります。」スタックオーバーフロー では、SQL Serverはカスケードパスの「詳細」検査を行わず、浅いパスのみを検査します。テーブルA
のテーブルB
にカスケード制約がある場合、それはA
とB
の間のカスケードグラフにすでにエッジを誘導しています。対象の列の。
したがって、ここではWorker
からNote
への直接パスとWorker
からBusiness
を経由してNote
へのパスがあります。 Note
はグラフに2回表示されます。
ここでは、特定の列で競合は発生しませんが、Microsoftサポート記事 としてすでに十分です。複数のカスケードパスを引き起こす可能性のあるFOREIGN KEY制約を作成すると、エラーメッセージ1785が発生します。 " 状態:
このエラーメッセージが表示されるのは、SQL Serverでは、DELETEまたはUPDATEステートメントのいずれかによって開始されたすべてのカスケード参照アクションのリストにテーブルを複数回表示できないためです。たとえば、カスケード参照アクションのツリーは、カスケード参照アクションツリーの特定のテーブルへのパスを1つだけ持つ必要があります。
トリガーはこれを回避することをお勧めします。ただし、主キー以外の方法でinserted
疑似テーブルの行とdeleted
疑似テーブルの行をマップする方法がわからないため、トリガーに関する大きな問題が発生します。しかし、それが更新で変更された場合、一致する可能性はなく、変更された値のペアを検出する方法はありません。
したがって、主キーを更新せずにON UPDATE NO ACTION
を使用する以外に方法はないと思います。そして、オプションとして持つのはいいことですが、通常、とにかく主キーを更新する必要はありません。