ユーザーがデータベース内で一意である必要がある値を入力できるようにする場合は、変更を保存する前に、この入力を検証する必要があります。
if (context.Customers.Any(c => c.SomeUniqueProperty == userInput))
// return to user with a message to change the input value
else
context.SaveChanges();
これは、データベースに一意の制約がある値の場合だけでなく、データベースで主キーが自動生成されない場合に既存のターゲットレコードまたは主キー値を参照する必要がある外部キー値を入力する場合にも当てはまります。コンテキストはデータベーステーブル全体のコンテンツを認識せず、現在コンテキストに接続されているエンティティについてのみ認識しているため、EFは後者の状況でも役立ちません。EFは、同じ主キーを持つ2つのオブジェクトをアタッチすることを禁止しますが、同じ一意のキー制約を持つ2つのオブジェクトを許可することは事実です。ただし、これは、データベースに変更を保存するときに主キー制約違反から完全に保護するわけではありません。
Any
チェックと別のユーザーが同じ値のレコードを入力したというまれなケースではSaveChanges
、発生した例外を処理できないと見なし、「予期されたエラーが発生しました。もう一度やり直してください...」とユーザーに伝えます。ユーザーが再試行すると、Any
チェックが再度行われ、上記のコードから入力値を変更するためのより有用なメッセージが表示されます。
このような一意キー制約または主キー制約違反に対して返される例外は一般的なDbUpdateException
ものであり、内部例外のSqlException
1つは、そのプロパティの1つとしてSQLServerエラーコードを含むになります。その他の詳細は、「UNIQUEKEY制約の違反IX_SomeUniqueProperty_Index...」などの例外メッセージでのみ確認できます。ユーザーがこの情報を理解し、それに応じて反応できることを期待する場合は、それを表示できます。それ以外の場合は、管理者または開発者がバグやその他の問題の可能性を確認するために、このメッセージをログに記録することができます。