MVC2 TextBox для значения не обновляется после отправки? - PullRequest
12 голосов
/ 28 мая 2010

Это действительно странное поведение, и я настроил демонстрационный код, чтобы попытаться выяснить, что происходит.

В основном есть два действия и один вид. Первое действие отправляет пустую модель в представление, действие section получает модель, изменяет ее содержимое и отправляет обратно в то же представление.

Странность, с точки зрения модели, в ней, похоже, есть обновленные значения, но когда я делаю Html.TextBoxFor (x => x.PropertyNameHere), она отображает текстовое поле с неизмененным значением в нем. 1005 *

lol ... Я заранее извиняюсь за туалетный юмор, но это не дает скучать. ;)

Кто-нибудь знает, что здесь происходит? Почему вывод TextBoxFor помещает старое значение в атрибут value?

Вот код для копирования:

/ Views / Demo / index.aspx

<%@ Page Language="C#" Inherits="System.Web.Mvc.ViewPage<TestWeb.DemoModel>" %>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title>Demo</title>
</head>
<body>
    <div>
      <%using (Html.BeginForm("DemoSubmit", "Admin", FormMethod.Post)) { %>
        Foo: <%=Html.TextBoxFor(x => x.Foo)%> <%:Model.Foo %><br />
        Bar: <%=Html.TextBoxFor(x => x.Bar) %> <%:Model.Bar %><br />
        PoopSmith: <%=Html.TextBoxFor(x => x.PoopSmith) %> <%:Model.PoopSmith %><br />
        <button type="submit">Submit</button>
      <%} %>
    </div>
</body>
</html>

DemoModel.cs

namespace TestWeb {
    public class DemoModel {
        public string Foo { get; set; }
        public int Bar { get; set; }
        public string PoopSmith { get; set; }
    }
}

DemoController.cs

public class AdminController : Controller {

        public ActionResult Index() {
            var m = new DemoModel();
            return View(m);
        }

        public ActionResult DemoSubmit(DemoModel demo) {
            demo.Foo += "!!!";
            demo.Bar++;
            demo.PoopSmith += " has pooped.";
            return View("Index", demo);
        }
}

А вот странный вывод:

Bizarre http://i47.tinypic.com/308cwvb.png

Ответы [ 5 ]

14 голосов
/ 28 мая 2010

Помощник по умолчанию Html попытаться заново отобразить данные, которые им отправлены. Сначала они используют значение из опубликованных данных, а если нет опубликованных данных, они берут данные из модели.

Это не то, что вам нужно, очевидно, но все же наиболее распространенное использование: вы отображаете некоторые данные в полях формы после получения запроса get. Вы публикуете сообщение об обновлении. Если у вас есть ошибки, вы хотите снова отобразить форму с введенными вами значениями.

Я видел, как некоторые люди обошли это (я думаю, написав в ModelState), но я всегда выбирал не использовать помощников по умолчанию, если они не помогают мне. Это особенно актуально для скрытых полей: большинство людей смущаются, когда устанавливают значение для скрытого поля, но действительно используемое значение взято из публикации. По крайней мере, каждый день возникает вопрос об этом на SO: -)

Забудьте «Большинство людей» и замените его на «Все».

ASP.NET MVC: значение скрытого поля не отображается при использовании HtmlHelper.Hidden

http://blog.johnwest.com/post/ASPNET-MVC-Hidden-Form-Field-Bug.aspx

http://blogs.msdn.com/b/simonince/archive/2010/05/05/asp-net-mvc-s-html-helpers-render-the-wrong-value.aspx?utm_medium=Twitter&utm_source=Shared

UPDATE О, я нашел еще один с сегодняшнего дня (Вы не одиноки):

Как обновить значение текстового поля

6 голосов
/ 03 сентября 2010

Do ModelState.Clear (); в вашем контроллере, чтобы предотвратить это. Для этого проверьте MSDN .

3 голосов
/ 31 марта 2011

Я бы избегал ModelState.Clear () или ModelState.Remove (), если в этом нет необходимости. Как правило, если вы видите это поведение, то это потому, что а) вы не следуете шаблону Post-Redirect-Get и должны быть, или б) если это не подходит, вы должны рассмотреть возможность не использовать метод TextBox HtmlHelper, поскольку разработан, чтобы помочь с проверкой и т. д. при следовании шаблону PRG.

Я уверен, что есть исключения (например, пользовательский интерфейс в стиле мастера может закончиться примерно так), но я бы принял это как подход по умолчанию.

1 голос
/ 31 марта 2011

Решение состоит в том, чтобы использовать либо ModelState.Remove («[Имя свойства режима]»), прежде чем ему будет присвоено новое значение с помощью контроллера.Или на странице просмотра измените Html.TextBoxFor () на Html.TextBox () для конкретного свойства модели.

0 голосов
/ 31 марта 2011

У меня возникла та же проблема с VS 2010, и я обнаружил, что весь день врезался в стену. Подумав всю ночь, думаю, я нашел причину. Причина в настойчивости. Он только запоминает любое значение, введенное в браузере. Тем не менее, я думаю, что это нарушает обязательный принцип. Если мне разрешено передавать параметр модели в представление, представление должно привязать этот параметр, принимая все, что я передаю в текущем состоянии модели.

...