Предварительная версия ASP.NET MVC 4 – остановка Url.RouteUrl() и т. д.используя существующие параметры
-
09-06-2019 - |
Вопрос
У меня есть такое действие:
public class News : System.Web.Mvc.Controller
{
public ActionResult Archive(int year)
{
/ *** /
}
}
С таким маршрутом:
routes.MapRoute(
"News-Archive",
"News.mvc/Archive/{year}",
new { controller = "News", action = "Archive" }
);
URL-адрес, по которому я нахожусь:
News.mvc/Archive/2008
У меня есть форма на этой странице:
<form>
<select name="year">
<option value="2007">2007</option>
</select>
</form>
Отправка формы должна осуществляться по адресу News.mvc/Archive/2007, если в форме выбрано «2007».
Для этого необходимо, чтобы атрибут действия формы был «News.mvc/Archive».
Однако, если я объявлю такую форму:
<form method="get" action="<%=Url.RouteUrl("News-Archive")%>">
он отображается как:
<form method="get" action="/News.mvc/Archive/2008">
Может кто-нибудь, пожалуйста, дайте мне знать, что мне не хватает?
Решение
Я думаю, у вас есть пара проблем.
Во-первых, в вашем маршруте нет значения по умолчанию для года, поэтому URL-адрес «/News.mvc/Archive» фактически недействителен для целей маршрутизации.
Во-вторых, вы ожидаете, что значения формы будут отображаться как параметры маршрута, но HTML работает не так.Если вы используете простую форму с выбором и отправкой, в конце ваших URL-адресов будет стоять «?year=2007».Именно так формы GET-метода предназначены для работы в HTML.
Итак, вам нужно прийти к какому-то выводу о том, что важно.
- Если вы хотите, чтобы пользователь мог выбрать что-то из раскрывающегося списка и это изменило URL-адрес отправки, то вам придется использовать Javascript для достижения этой цели (путем перехвата отправки формы и формулирования правильного URL-адреса).
- Если вас устраивает /News.mvc/Archive?year=2007 в качестве URL-адреса, вам следует полностью удалить указатель {year} из маршрута.Вы по-прежнему можете оставить для своего действия параметр «intyear», поскольку значения формы также будут заполнять параметры метода действия.
Другие советы
Думаю, я понял, почему: маршрут включает в себя {year}, поэтому сгенерированные маршруты всегда будут тоже..
Если кто-нибудь может это подтвердить?
Решение
Хорошо, вот решение (спасибо Брэду, что привел меня туда).
1) Требовать значение по умолчанию в маршруте:
routes.MapRoute(
"News-Archive",
"News.mvc/Archive/{year}",
new { controller = "News", action = "Archive", year = 0 }
);
2) Добавьте перенаправление для анализа параметров GET, как если бы они были сегментами URL.
public ActionResult Archive(int year)
{
if (!String.IsNullOrEmpty(Request["year"]))
{
return RedirectToAction("Archive", new { year = Request["year"] });
}
}
3) Убедитесь, что у вас есть код перенаправления для параметров запроса. до любой код для перенаправления записей года «по умолчанию».то есть
public ActionResult Archive(int year)
{
if (!String.IsNullOrEmpty(Request["year"]))
{
return RedirectToAction("Archive", new { year = Request["year"] });
}
if (year == 0)
{
/* ... */
}
/* ... */
}
3) Явно укажите значение года по умолчанию в вызове Url.RouteUrl():
Url.RouteUrl("News-Archive", new { year = 0 })