asp.net mvc - How to make one controller the default one when only action specified? -
i using standard mvc template mvc 2013.
there home controller actions about, contact, etc.
there account controller actions login, logout, etc.
the app deployed @ domain website. url http://website produce output of /home/index, without changing url in browser address box, ie browser shows not result of http redirect.
how make url http://website/x route /home/x if x not controller in application? otherwise should route /home/x/index.
the reason http://website/about, http://website/contact etc without home.
a naive solution define new route above default (catch-all) looks like:
routes.maproute( name: "shorturltohomeactions", url: "{action}", defaults: new { controller = "home" } ); the problem approach prevent accessing index (default action) of other controllers (requesting /other, when have othercontoller index action result in 404, requesting /other/index work).
a better solution create routeconstraint match our /{action} in case there no other controller same name:
public class noconflictingcontrollerexists : irouteconstraint { private static readonly dictionary<string, bool> _cache = new dictionary<string, bool>(stringcomparer.ordinalignorecase); public bool match(httpcontextbase httpcontext, route route, string parametername, routevaluedictionary values, routedirection routedirection) { var path = httpcontext.request.path; if (path == "/" || string.isnullorempty(path)) return false; if (_cache.containskey(path)) return _cache[path]; icontroller ctrl; try { var ctrlfactory = controllerbuilder.current.getcontrollerfactory(); ctrl = ctrlfactory.createcontroller(httpcontext.request.requestcontext, values["action"] string); } catch { _cache.add(path, true); return true; } var res = ctrl == null; _cache.add(path, res); return res; } } then applying constraint:
routes.maproute( name: "shorturltohomeactions", url: "{action}", defaults: new { controller = "home" }, constraints: new { noconflictingcontrollerexists = new noconflictingcontrollerexists() } ); see msdn
Comments
Post a Comment