私は複雑なモデルを作成し、フォームデータをデータベースに追加/更新する方法を見つけるためにしばらくの間苦労しています。私はModelClass1のための足場のCRUDコントローラを作成し、1つの編集クラスを使用して、すべての3つのエンティティを更新しようとしているMVC5 /エンティティ|複雑なモデルの更新/作成
namespace Models
{
public class ModelClass1
{
public int Id { get; set; }
public string Prop1 { get; set; }
public string Prop2 { get; set; }
public ICollection<ModelClass2> ModelClass2 { get; set; }
}
public class ModelClass2
{
public int Id { get; set; }
public string Prop3 { get; set; }
public string Prop4 { get; set; }
public ICollection<ModelClass3> ModelClass3 { get; set; }
}
public class ModelClass3
{
public int Id { get; set; }
public string Prop5 { get; set; }
public string Prop6 { get; set; }
}
}
:
は基本的に私のモデルは、以下のいずれかのように見えます。
私の編集(取得/ポスト)クラス:
// GET
public ActionResult Edit(int? id)
{
if (id == null)
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
ModelClass1 ModelClass1 = db.ModelClass1
.Include(i => i.ModelClass2.Select(c => c.ModelClass3))
.Where(x => x.Id == id)
.Single();
if (config == null)
{
return HttpNotFound();
}
return View(ModelClass1);
}
// POST
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit(ModelClass1 ModelClass1)
{
if (ModelState.IsValid)
{
db.Entry(ModelClass1).State = EntityState.Modified;
db.SaveChanges();
return RedirectToAction("Index");
}
return View(ModelClass1);
}
私はEdi.cshtmlは次のようになりますので、編集ビュー内のフォームを移入するエディタテンプレートを使用することを選択した:
@model ModelClass1
@using (Html.BeginForm())
{
@Html.AntiForgeryToken()
<div class="form-horizontal">
@Html.ValidationSummary(true, "", new { @class = "text-danger" })
@Html.HiddenFor(model => model.Id)
<div class="form-group">
@Html.LabelFor(model => model.Prop1, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.EditorFor(model => model.Prop1, new { htmlAttributes = new { @class = "form-control" } })
@Html.ValidationMessageFor(model => model.Prop1, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
@Html.LabelFor(model => model.Prop2, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.EditorFor(model => model.Prop2, new { htmlAttributes = new { @class = "form-control" } })
@Html.ValidationMessageFor(model => model.Prop2, "", new { @class = "text-danger" })
</div>
</div>
@Html.EditorFor(model => model.ModelClass2, new { htmlAttributes = new { @class = "form-control" } })
@Html.EditorFor(model => model.ModelClass2.FirstOrDefault().ModelClass3, new { htmlAttributes = new { @class = "form-control" } })
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Save" class="btn btn-default" />
</div>
</div>
}
以下のような私の3つのモデルクラスのそれぞれについて、
そして、作成したテンプレート:
@model ModelClass2
<div class="form-group">
@Html.LabelFor(model => model.Prop3, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.EditorFor(model => model.Prop3, new { htmlAttributes = new { @class = "form-control" } })
@Html.ValidationMessageFor(model => model.Prop3, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
@Html.LabelFor(model => model.Prop4, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.EditorFor(model => model.Prop4, new { htmlAttributes = new { @class = "form-control" } })
@Html.ValidationMessageFor(model => model.Prop4, "", new { @class = "text-danger" })
</div>
</div>
データがBであります「ModelClass3」のために失敗したタイプのエンティティをアタッチ
:私はフォーム内のデータを変更し、HTTPPost Editメソッドを呼び出し、それを投稿したときに、正しく、私は、私は以下のエラーを受け取る編集コントローラを呼び出すことが、よ示さeing同じタイプの別のエンティティはすでに同じ主キー値を持っています。これは、「Attach」メソッドを使用するか、またはグラフ内のエンティティのいずれかが競合するキー値を持つ場合、エンティティの状態を「Unchanged」または「Modified」に設定すると発生します。これは、一部のエンティティが新しく、データベース生成キー値をまだ受け取っていないことが原因です。この場合、 'Add'メソッドまたは 'Added'エンティティ状態を使用してグラフを追跡し、非新規エンティティの状態を 'Unchanged'または 'Modified'に適切に設定します。
コントローラ/ビューからModelClass3を完全に削除してもエラーは発生しませんが、変更されたデータはデータベースに保存されません。
私のアプローチは最高のものではないと確信していますので、私はアイデアがなくなり、どんな助けにも大いに感謝します。
おかげで、私は考え出しだから、修正に状態を設定する前に、それを添付しなければなりません私は完全に私のアプリケーションを再構築し、automapperを使用して開始する必要があります。私はより構造的なdesingを発見した:https://www.pluralsight.com/guides/microsoft-net/asp-net-mvc-creating-solutions-with-separate -projects-for-entities-data-access-and-website-functionality – Alex