Потратив два удивительных часа на форматирование некоторых скрытых полей, чтобы правильно связать их с параметрами метода действия - во второй раз, когда я испытывал это на прошлой неделе, - мне теперь очень любопытно, почему архитекторы MVC выбрал конкретное соглашение о связывании, которое они сделали для списков (и словарей) объектов.
Вот мое болезненно собранное понимание формата, ожидаемого механизмом привязки по умолчанию. В моем примере я хочу привязать к списку, где тип CustomClass предоставляет открытое свойство с именем PropertyName:
<input type="hidden" name="prefix[idx].PropertyName" value="PropertyName[idx] Value" />
Префикс - это ViewDataDictionary.TemplateInfo.HtmlPrefix, если он был определен.
Я считаю, что начинать ссылку на что-либо с информации об индексировании (то есть, части [idx]) очень нелогично. Меня также беспокоит, что нигде в этой конструкции я не делаю ссылку на имя параметра метода действия, к которому привязываюсь. Это, кажется, находится в прямом противоречии с тем, что происходит, скажем, с примитивным свойством модели:
<input type="hidden" name="Text" value="something" />
public ActionResult SomeActionMethod( string Text )...
Я понимаю, что могу свернуть свою собственную модель в MVC. Это не похоже на прибыльное использование моего времени, хотя проводить часы, пытаясь найти правильный формат для скрытых полей, тоже не выгодно :), так что, возможно, я попробую это. Я также знаю, что могу позволить MVC выполнять всю тяжелую работу, создав шаблон типа с помощью @ Html.HiddenFor (), а затем вывести экземпляры CustomClass через простое частичное представление с CustomClass в качестве модели и однострочный @Html. DisplayForModel (). Но это похоже на долгий путь вокруг сарая тоже. Кроме того, существуют ограничения на использование помощников @ Html.Hidden (например, они «старательно» совершают набег на кэш после обратной передачи для заполнения значений, поэтому написание @ Html.Hidden («fieldname», value) не гарантирует, что значение закончится) до вывода - вы можете вместо этого получить старое значение в кэше, что сегодня было еще одним часовым раздражением).
Но мне просто любопытно, почему этот формат был выбран. Почему не что-то более C / C ++ / C # / VB вроде:
<input name="prefix.ParameterName.PropertyName[idx]" />
Edit:
Хороший вопрос о том, куда я поместил параметр индекса в моем примере. Вы правы, свойство не проиндексировано, содержащий класс:
Однако это не меняет основную ситуацию. Почему синтаксис не похож на:
<input name="prefix.ParameterName[0].PropertyName" />
Стандартный синтаксис игнорирует имя параметра с коллекциями пользовательских типов и «угадывает» пользовательский тип по именам свойств. Это странно ... поэтому за этим должна стоять история или выбор:).