3

これは、昨日尋ねられた質問のフォローアップです。

目的のリストを表示するビューモデルがあります。jqueryを使用して、画面に新しい目標行を追加できます(リストされている新しい目標のIDは0に設定されています)。[保存]ボタンをクリックして目的リストをコントローラーにポストバックすると、コントローラーは目的リストをループし、IDをデータベースと照合します。IDが見つからない場合は、新しい目的が作成され、これがDBコンテキストに追加され、変更が保存されます。次に、IDを取得し、ビュー(モデル)をビューに返します。

問題は、モデル内のIDがデータベースIDに更新されているにもかかわらず、モデルがビューに再度レンダリングされたときに、そのIDが0のままであるということです。したがって、もう一度[保存]をクリックすると、「新しい」が再度追加されます。以前に追加された目的」をデータベースに再度追加しました。

私のコントローラーを以下に示します。

    //
    // POST: /Objective/Edit/model
    [HttpPost]
    public ActionResult Edit(ObjectivesEdit model)
    {
        if (model.Objectives != null)
        {
             foreach (var item in model.Objectives)
            {
                // find the database row
                Objective objective = db.objectives.Find(item.ID);
                if (objective != null) // if database row is found...
                {
                    objective.objective = item.objective;
                    objective.score = item.score;
                    objective.possscore = item.possscore;
                    objective.comments = item.comments;
                    db.SaveChanges();
                }
                else // database row not found, so create a new objective
                {
                    Objective obj = new Objective();
                    obj.comments=item.comments;
                    obj.objective = item.objective;
                    obj.possscore = item.possscore;
                    obj.score = item.score;
                    db.objectives.Add(obj);
                    db.SaveChanges();
                    // now get the newly created ID 
                    item.ID = obj.ID;
                 }
             }
        }
        return View(model);
    }

私のIDはコントローラーに設定されています:

ここに画像の説明を入力してください

編集:ここにある別の例は、model.Objectives1.IDが更新されていることを示しています。

ここに画像の説明を入力してください

ただし、ビューがレンダリングすると、0に戻ります。

ここに画像の説明を入力してください

目標リストは次のように決定されます。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;

namespace MvcObjectives2.Models
    {
    public class ObjectivesEdit
    {
        public IEnumerable<Objective> Objectives { set; get; }
        public ObjectivesEdit()
        {
            if (Objectives == null)
                Objectives = new List<Objective>();
        }
    }
    }

ビューには次のものがあります。

@model MvcObjectives2.Models.ObjectivesEdit

@using (Html.BeginForm())
{
  @Html.EditorFor(x=>x.Objectives)
  <button type="submit" class="btn btn-primary"><i class="icon-ok icon-white"></i> Save</button>
 }

そして私のEditorTemplate(objective.cshtml)で:

@model  MvcObjectives2.Models.Objective          

<div class="objec">
<div>
@Html.TextBoxFor(x => x.objective})
</div>
<div>
@Html.TextBoxFor(x => x.score})
</div>
<div>
@Html.TextBoxFor(x => x.possscore})
</div>
<div>
@Html.TextBoxFor(x => x.comments})

@Html.HiddenFor(x => x.ID)  // This is the ID where it should now show the new ID from the database, but shows 0

</div>
</div>

問題はコントローラーのどこかにあると思いますが、ビューに追加された目的の新しいIDをレンダリングする方法についてアドバイスをいただければ幸いです。

4

2 に答える 2

3

検索を言い換えた後、これは仕様によるものであると言ういくつかの投稿に出くわしました。投稿されたフォームは、同じページが再び表示された場合、コントローラーに送信された内容を表示することを期待しています。

ただし、これを追加すると、ModelStateがフラッシュされ、コントローラーで更新されたモデルから更新された値が表示されます。

        ModelState.Clear();
        return View(model);

これが他の効果をもたらすかどうかはまだわかりませんが、今のところ、問題なく機能しているようです。

ありがとう、マーク

于 2012-07-20T10:57:46.643 に答える
1

Html.HiddenForは、以前に同様のシナリオで私を噛みました。問題は、このHTMLヘルパーを使用すると、再投稿時に非表示の値が更新されないことです。

フォームから何かを投稿してコントローラー内で変更した場合、それを使用してページを再レンダリングすると、アクションに最初に投稿された値が使用されます。

代わりに使用する

<input type="hidden" name="ID" id="ID" value="@Html.Encode(Model.ID)" />
于 2012-07-20T09:54:36.170 に答える