このエラーについて多くの質問がありますが、それでも私の問題を理解することはできません(多分私はこれに関する理論のいくつかをもっと必要とします)。
「同じキーを持つオブジェクトがobjectstatemanagerにすでに存在します」というエラーが発生し、実行しようとしていることは非常に単純です。電話のリストを含むクライアントの編集ビューがあります。ユーザーが[保存]ボタンを押すと、すべてをJsonでラップし、Ajaxでコントローラーに送信します。
コントローラーで、送信されたリストのどの電話を更新し、ニュースとして挿入し、削除する必要があるかを確認することになっています。
したがって、コードの重要な部分(および前述の例外をスローする部分)は次のとおりです。
if (ModelState.IsValid)
{
foreach (var tel in propModel.Proprietario.Telefones)
{
//Updates
TelefoneProprietario telToEdit = null;
if (tel.IDTelefoneProprietario.HasValue)
telToEdit = db.TelefonesProprietarios.Find(tel.IDTelefoneProprietario);
if (telToEdit != null)
{
db.Entry(tel).State = EntityState.Modified; << Exception HERE!!!
}
else
{
//Inserts
db.TelefonesProprietarios.Add(tel);
}
}
if (propModel.Proprietario.IDProprietario.HasValue)
{
var prop = db.Proprietarios.Find(propModel.Proprietario.IDProprietario);
prop.LoadLists();
foreach (var telDel in prop.Telefones)
{
//Deletes
if (propModel.Proprietario.Telefones.Find(t => t.IDTelefoneProprietario == telDel.IDTelefoneProprietario) == null)
{
db.TelefonesProprietarios.Remove(telDel);
}
}
}
db.Entry(propModel.Proprietario).State = EntityState.Modified;
db.SaveChanges();
return Json(new { Success = 1, IDProprietario = propModel.Proprietario.IDProprietario, ex = "" });
}
ヘルプや提案はありますか?
さらに最悪の場合、残りのコードをテストするために例外をスローする行を削除し、SaveChangesの前の最後の行で別の例外をスローします。
The relationship between the two objects cannot be defined because they are attached to different ObjectContext objects.
アップデート:
私は、上記のルーチンを次のような別の形式で書き直すという問題の一部をなんとか解決しました。
if (prop.IDProprietario.HasValue)
{
//Separete updates/inserts from deletes
List<int?> dbTels = db.TelefonesProprietarios
.Where(dt => dt.IDProprietario == prop.IDProprietario)
.Select(dt => dt.IDTelefoneProprietario)
.ToList();
List<int?> postedTels = prop.Telefones
.Select(pt => pt.IDTelefoneProprietario)
.ToList();
List<int?> deletedTels = dbTels
.Except(postedTels).ToList();
//Perform deletes
foreach (var delTelId in deletedTels)
{
if (delTelId.HasValue)
{
TelefoneProprietario delTel = db.TelefonesProprietarios
.Where(dt => dt.IDProprietario == prop.IDProprietario && dt.IDTelefoneProprietario == delTelId)
.Single();
db.Entry(delTel).State = EntityState.Deleted;
}
}
//Perform insert and updates
foreach (var tel in prop.Telefones)
{
if (tel.IDTelefoneProprietario.HasValue)
{
db.Entry(tel).State = EntityState.Modified;
}
else
{
db.Entry(tel).State = EntityState.Added;
tel.IDProprietario = (int)prop.IDProprietario;
}
}
db.Entry(prop).State = EntityState.Modified;
}
else
{
db.Proprietarios.Add(prop);
}
db.SaveChanges();
現在残っている問題は、Proprietarioインスタンスを削除することだけです(TelefoneProprietarioのリストがあり、TelefoneProprietarioにはそれを所有するProprietarioへの参照があるためです。このシナリオでは、「2つのオブジェクト間の関係は、に接続されているため定義できません。ここSOで広く議論されているように、さまざまなObjectContextオブジェクト」...解決策を見つけようとしているので、私に何かを指摘できれば...)