如何成功编写 MVC 路由定义
本文关键字:MVC 路由 定义 何成功 成功 | 更新日期: 2023-09-27 18:35:17
有人可以帮我找到问题所在,并且仍然向我解释控制器如何知道它应该使用哪个路由定义(因为在很多情况下,URI 可以适合不止一个路由定义)?
这是我的问题...
控制器方法:
[HttpGet]
public ActionResult PreencherFormulario(int idPacientePesquisa, int idFormularioPesquisa)
路由(所有路由在 Global.asax 上定义):
protected void Application_Start()
{
RouteTable.Routes.MapRoute(
"Busca",
"{controller}/{action}/{SearchString}/{SearchSubString}/{id}"
);
RouteTable.Routes.MapRoute(
"Participacao",
"{controller}/{action}/{id}"
);
RouteTable.Routes.MapRoute(
"ParticipacaoPesquisa",
"{controller}/{action}/{idPesquisa}/{nrProntuario}",
null,
new { idPesquisa = @"'d+" }
);
//!!! This should be the one used...
RouteTable.Routes.MapRoute(
name: "PreencherForm",
url: "{controller}/{action}/{idPacientePesquisa}/{idFormularioPesquisa}",
defaults: new { idPacientePesquisa = 1, idFormularioPesquisa = 1 },
constraints: new { idPacientePesquisa = @"'d+", idFormularioPesquisa = @"'d+" }
);
RouteTable.Routes.MapRoute(
"AdicionarRegraCID",
"{controller}/{action}/{a}/{b}/{c}",
new { controller = "Pesquisas", action = "AdicionarRegraCID", MetodoResultado = "", MetodoCancelar = "" }
);
网址:
http://localhost:61404/RealizacaoPesquisa/PreencherFormulario/1/1
错误:
The parameters dictionary contains a null entry for parameter 'idPacientePesquisa' of non-nullable type 'System.Int32' for method 'System.Web.Mvc.ActionResult PreencherFormulario(Int32, Int32)' in 'Prometheus.Controllers.RealizacaoPesquisaController'. An optional parameter must be a reference type, a nullable type, or be declared as an optional parameter.
Nome do parâmetro: parameters
您的问题在于以下路由,该路由默认为 null,并且该路由位于您怀疑的路由之前,并且路由 url 的格式与下一个路由的格式相同。此路由被考虑,并且在路由时失败,因为您的操作参数是不可为 null 的 int。
RouteTable.Routes.MapRoute(
"ParticipacaoPesquisa",
"{controller}/{action}/{idPesquisa}/{nrProntuario}",
null, /*<--- This is the culprit*/
new { idPesquisa = @"'d+" }
);
请记住,路线的顺序很重要,您也应该将默认路线保留在底部。将上面的路线移动到有问题的路线下方。您需要重新安排路线。事情是这样的:
您点击网址:http://localhost:61404/RealizacaoPesquisa/PreencherFormulario/1/1
它查看路由表并找到第一个匹配项,即
"{controller}/{action}/{idPesquisa}/{nrProntuario}",
因此,然后它会尝试使用参数调用您的操作 idPesquisa
这是此路由中映射的内容。
但是您的操作需要其他内容作为参数名称,并且它们也是不可空的,因此如果失败。
首先,您要编写从更具体到更通用的路由。它使用它匹配的第一个。
所以你的问题是你的路由与这条路线匹配,你正在将idPacientPesqusa设置为空。
RouteTable.Routes.MapRoute(
"ParticipacaoPesquisa",
"{controller}/{action}/{idPesquisa}/{nrProntuario}",
null, <-- here!!
new { idPesquisa = @"'d+" }
);
您似乎正在尝试为每个控制器/操作设置路由,以便您可以执行以下操作
RouteTable.Routes.MapRoute(
name: "PreencherForm",
url:"RealizacaoPesquisa/PreencherFormulario/{idPacientePesquisa}/{idFormularioPesquisa}",
defaults: new { controller = "RealizacaoPesquisa", action = "PreencherFormulario", idPacientePesquisa = 1, idFormularioPesquisa = 1 },
constraints: new { idPacientePesquisa = @"'d+", idFormularioPesquisa = @"'d+" }
);