Сильно типизированное действие T4MVC Action/ActionLink
Я довольно долго использовал T4MVC (FYI: v2.6.62), и я медленно двигался над нашим кодом для этого способа работы (меньше полагаться на магические строки).
Но мне пришлось остановиться, потому что по какой-то причине T4MVC не может переводить объекты в URL-адреса и, похоже, может работать только с примитивными типами (int/string/etc).
Вот пример:
Распад маршрута:
/MyController/MyAction/{Number}/{SomeText}
Класс:
namespace MyNamespace
{
public class MyClass
{
public int Number { get; set; }
public string SomeText { get; set; }
}
}
Контроллер:
public class MyController
{
public virtual ActionResult MyAction(MyClass myClass)
{
return View();
}
}
Вид:
<%= Html.Action(
T4MVC.MyController.Actions.MyAction(
new MyClass()
{
Number = 1,
SomeText = "ABC"
}
) %>
Конечным результатом является следующее:
/MyController/MyAction?myClass=MyNamespace.MyClass
а не
/MyController/MyAction/1/ABC
У кого-нибудь еще есть эта проблема? Доступны ли URL-адреса T4MVC?
Вопрос также задан на форуме ASP.NET.
Ответы
Ответ 1
Обновление (10/11/2012): недавно добавленная поддержка разворачивания модели (см. раздел 3.1 в doc), надеюсь, охватывают многие из этих случаев.
Оригинальный ответ:
Копирование моего ответа из темы форума:
Хммм, я не думаю, что это все-таки появилось. Может быть, в большинстве случаев у людей есть методы Action, которые берут объект, значения объекта берутся из опубликованных данных формы, а не передаются по URL-адресу? В таком сценарии вопрос не возникает.
Я думаю, что теория T4MVC может быть изменена для поддержки этого. Просто нужно было бы продвигать все свойства верхнего уровня объекта в виде значений маршрута, а не пытаться использовать сам объект (очевидно, текущее поведение является фиктивным и является результатом простого вызова ToString() вслепую).
Есть ли у кого-то другие проблемы и считают целесообразным?
Ответ 2
Если я правильно понял проблему, следующий синтаксис должен позволить вам обойти проблему.
<%= Html.ActionLink("test", MVC.MyController.MyAction().AddRouteValues(new MyClass() { Number = 5, SomeText = "Hello" })) %>
Я думаю, что ответ, чтобы сделать синтаксис более привлекательным, состоял бы в том, чтобы обернуть каждый параметр типа non value в RouteValueDictionary в каждом сгенерированном методе результата действия
Изменить: (Ответ на комментарий как недостаточно символов)
Ah ok Мне удалось воссоздать простой пример выше, используя этот метод, чтобы дать: /MyController/MyAction/5/Hello
как url.
Я не совсем уверен, как вложенные сложные типы будут на практике. Вы можете использовать некоторую рекурсию, чтобы погрузиться в объект верхнего уровня и отразить значения для их добавления, но затем вы откроете новый набор проблем, например, как справиться с именем дочернего объекта, которое идентично родительскому Имя свойства.
Похоже, это может быть сложной проблемой для решения, таким образом, что это будет работать для всех.
Возможно, какой-то тип адаптера был бы наиболее полезен для преобразования сложного объекта в значения маршрута. В простейшем случае это может быть объявление метода расширения ToRouteDictionary, который действует на ваш сложный тип и преобразует его, используя ваши знания о том, как он должен работать. Просто задумываясь вслух, поскольку я, очевидно, не знаю ваших случаев использования