问题
I have an existing Web application that was developed in ASP.NET 4.0. I want to add MVC functionality to the app, so I've integrated MVC into the app as per Scott Hanselman's article Integrating ASP.NET MVC 3 into existing upgraded ASP.NET 4 Web Forms applications. Because MVC routing is greedy, I added the following code to my Global.asa so that an empty URL will go to my Default.aspx:
routes.MapPageRoute("WebFormsDefault", "", "~/Default.aspx");
The problem now is that ActionLinks and RouteLinks don't form correctly. If I try to create an action link using:
@Html.ActionLink("Item List Page", "List", "Item")
the following URL is created:
"/SiteName/?action=List&controller=Item
I've found several posts from others with this same problem, but none of them have any answer. Is this just a bug? Is integrating MVC into a WebForms app just a bad idea in general? Or is there a way to fix this so that my Default.aspx page will be displayed when a user first enters the site and ActionLinks and RouteLinks will work correctly?
回答1:
Coming to this a bit late, but I figure better late than never. I was having this exact same issue and I solved it by grouping my MapPageRoute code and my MapRoute code and then always calling the MapRoute code first. Example:
Originally my routing looked like this -
routes.MapPageRoute("401", "401/", "~/Views/Error/401.aspx");
routes.MapPageRoute("404", "404/", "~/Views/Error/404.aspx");
routes.MapPageRoute("500", "500/", "~/Views/Error/500.aspx");
routes.MapRoute(
"Default",
"{controller}/{action}/{id}",
new { controller = "Home", action = "Index", id = "" }
);
etc etc
This was causing all of my form actions to direct to a url formatted as so: /mysite/401?action=x&controller=y
Clearly that was not useful. By making sure that I always setup all of my MVC routes first, the problem resolved itself. I ended up making two seperate methods, one for configuring MVC routes and one for configuring Webform routes as so:
RouteConfig.RegisterMvcRoutes(RouteTable.Routes); // contains only MapRoute
RouteConfig.RegisterWFRoutes(RouteTable.Routes); // contains only MapPageRoute
(these calls go into the Global.asax file as usual and replace RouteConfig.RegisterRoutes)
回答2:
I would not advise mixing webforms with MVC, but I did manage to get this working by using this helpful posting: http://bartwullems.blogspot.com/2011/04/combining-aspnet-webforms-and-aspnet.html
I also had to be rather careful about the ordering of the routes so that my most generic route went after the aspx page I wanted to be served up as a default.
Here is my complete RouteConfig:
public static void RegisterRoutes(RouteCollection routes)
{
routes.IgnoreRoute({resource}.axd/{*pathInfo}");
routes.MapRoute(
name: "SignUp",
url: "SignUp",
defaults: new { controller = "Profile", action = "SignUp", shortUrl = UrlParameter.Optional });
routes.MapRoute(
name: "Admin",
url: "Admin",
defaults: new { controller = "Admin", action = "Index", shortUrl = UrlParameter.Optional });
//used to get aspx page to render
routes.MapPageRoute("WebForms", "", "~/WebForms/Default.aspx", false, null, new RouteValueDictionary(new { controller = new IncomingRequestConstraint() }));
//this generic route must go last
routes.MapRoute(
"Default",
"{controller}/{action}/{id}",
new { controller = "Home", action = "Index", id = "" }
);
}
public class IncomingRequestConstraint : IRouteConstraint
{
public bool Match(HttpContextBase httpContext, Route route, string parameterName, RouteValueDictionary values, RouteDirection routeDirection)
{
return routeDirection == RouteDirection.IncomingRequest;
}
}
来源:https://stackoverflow.com/questions/13959514/mappageroute-breaks-actionlinks-in-integrated-mvc-webforms-app