これはこのサイトの最初の質問です。私はMVCとEntity FrameworkをASP.Net Webアプリケーションで教えています。私は一連の関連するエンティティを持っており、context.saveChanges()を呼び出すと、削除された関連するデータ項目は削除されません。Entity Frameworkを使用してデータベースから関連オブジェクトを削除する
マイエンティティ 私は、0個以上のエイリアスを持つアイテムエンティティを持っています。これはデータベースの最初のプロジェクトであり、これらのコード行のほとんどは自動生成されています。
public Class Item
{
public int Id{get;set};
public string Name {get;set;}
public virtual ICollection<AliasClass> AssociatedAliases {get;set;}
}
public Class AliasClass
{
public int Id {get;set;}
public int ItemId {get;set;}
public string AliasName {get;set;}
public virtual Item RelatedItem {get;set;}
}
これで、自動生成されたものが完成しました。私のポストバックアクションは、ポストバックviewmodelを受け入れます。私はリポジトリパターンを実装しています。私のItem Repoには更新機能があります。
[HttpPost]
public ActionResult Edit (Models.EditViewPostBack MyPostBackModel)
{
If (!ModelState.isValid){
... rebuild and copy // this part works. Skipping over it
}
// this may be a key line of my issue
MyPostBackModel.Item.Alias = MyPostBackModel.myAliases;
ItemRepo.Update(MyPostBackModel.Item);
return RedirectToAction("Index","Home");
}
ここはModels.EditViewPostBackです。新しい関連付けのリストは配列として返されます。新しいアソシエーションのIDは0です。更新時には、実際のIDが割り当てられます。
public class EditViewPostBack{
Item myItem {get; set;}
AliasClass[] myAliases {get;set;}
}
最後に、プロジェクトの肉と私の本当の問題。これは、変更を更新するItemRepoのメソッドです。 entitystate Becuase
public void Update (Item myItem)
{
// myItem.AssociatedAliases contains only the wanted associations.
// It doesn't have the to-be deleted items.
// new items have an id of 0
// defined in class constructor.
context.Item.Attach(myItem);
context.Entry(Item).State = EntityState.Modified;
foreach(var name in myItem.AssociatedAliases){
// finds the modified local version of the item. doesn't connect
// to the database to location info.
if(name.id > 0)
{
var moded = context.AliasClass.find(name.Id);
context.Entry(moded).State = EntityState.Modified;
}
else
{
// it is brand new
context.Item.Add(name)
}
}
//
// Once the alias is not attached to it's item it has to go
// How to handle deletes goes here
//
context.SaveChanges();
}
は関連が残り、私はそれを削除したことがないように項目が表示されます削除済みとしてマークされていません。私はすでにいくつかのことを試みました。
context.Alias.linqFunction()を使用して元のアイテムをロードまたは検索すると、リスト全体がidの一致後にmyItemパラメータに再関連付けされます。
// invoking the following line causes Item.Alias to fully re-associate.
// I lose the list passed to the function
context.AliasClass.Where(x=>x.ItemId == myItem.Id)
私はアイテムを削除しないデータベースへの往復であるため、エイリアスは現在ロードできません。
私は、Idがまだ接続されているリストと一致する場合を除いて削除する必要があると思います。しかしremoveは削除する項目のインスタンスをとります。
関連付けられたエイリアス名をデータベースから削除するにはどうすればよいですか?
これは機能しません。 myItem.Aliasesをnullにするだけで項目への関連付けが消去されますが、データストアからは削除されません。削除されたアイテムを取得するには、アイテムに関連付けられていないエイリアスが必要です**。今、Aliasesテーブルに必須のItemIdがあります。しかし、どこにでもエイリアス/エイリアスを使用することについてのあなたの意見があります。混乱を避けるため、より良い名前を使用するように質問を更新します。 –
@Michael私は自分の答えを更新しました。 – Hadee
ありがとう、Hadee。私は前にこのようなことを試みましたが、問題に遭遇しました。提案されたソリューションは、常に2つの要求をデータベースに作成します。これは更新プロセスにとって非常に非効率的です。私が以前に持っていた問題は、itemidが現在のアイテムであるエイリアスをロードするとすぐにitemとaliasclassにitemとaliasの間の既存の関係が突然現れることでした。それで、私は、追加、削除、または更新が必要なものを見逃してしまいます。 –