Default Index Method behaviour in ASP.NET MVC - asp.net-mvc-2

I have the following ActionMethod in UserController
public ActionResult Index(string id, string name, int? org)
When I navigate to > http://example.com/User , the above action method is invoked. Thats good.
However when I navigate to > http://example.com/User/1 , it can't find the resource. Shouldn't it navigate to the above action method with id = 1 and the rest as null ?
Routing in Global.asax:
context.MapRoute(
"Default",
"/{controller}/{action}/{id}",
new { action = "Index", id = UrlParameter.Optional }
);

You will have to add those other parameters into your routing as well for them to ever get populated.
routes.MapRoute(
"Default", // Route name
"{controller}/{action}/{id}/{name}/{org}", // URL with parameters
new { controller = "Home", action = "Index", id = UrlParameter.Optional, name = UrlParameter.Optional, org = UrlParameter.Optional } // Parameter defaults
);
You can then navigate to http://yourdomain/User/Index/1
As name and org are optional you can also pass these in when you want
http://yourdomain/User/Index/1/fred
http://yourdomain/User/Index/1/fred/44

You should navigate to http://mysite.com/User/Index/1 instead of http://mysite.com/User/1

Related

How to handle ASP MVC Url Parameter containing forward slash

I am working on a ASP.Net MVC project. I have a particular controller action that accepts a date value in the form yyyy/mm/dd. So the URL becomes
http://localhost/MyProject/PublicReview/GetReviews/2012/10/29.
where GetReviews is an action and 2012/10/29 the parameter.
My RouteConfig is as follows:
public static void RegisterRoutes(RouteCollection routes)
{
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
routes.MapRoute(name: "Default",url: "{controller}/{action}/{id}",defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional });
}
How should I change the routevalues ? What should be the order of MapRoute values?
I've not tested this, but I'm guessing this will work in your scenario:
routes.MapRoute(
"Reviews", "PublicReview/GetReviews/{year}/{month}/{day}"
{ controller = "PublicReview", action = "GetReviews" };
Note that this will need your GetReviews method to have three properties of "year", "month" and "day". You'll then have to parse them into a DateTime.
Taken from http://www.asp.net/mvc/tutorials/controllers-and-routing/creating-custom-routes-cs which uses "-" for date separators.

Request.QueryString in MVC

In my HomeController I'm trying to get information using Request.QueryString
string aa = Request.QueryString["aa"];
string bb = Request.QueryString["bb"];
So In the address bar I am expecting something like:
< something >?aa=12345&bb=67890
I created a new route:
routes.MapRoute(
"Receive",
"Receive",
new { controller = "Home", action = "Index" }
);
And I'm trying to use it in this way:
http://localhost:54321/Receive?aa=12345&bb=67890
But I'm getting the following error:
The resource cannot be found.
Description: HTTP 404. The resource you are looking for (or one of its dependencies) could have been removed, had its name changed, or is temporarily unavailable. Please review the following URL and make sure that it is spelled correctly.
Requested URL: /Receive
I think your routing is goofed which is why you are getting a 404. Please look at some tutorials, specifically here: asp.net/mvc/tutorials/asp-net-mvc-routing-overview-cs
Also, like #YuriyFaktorovich says, you really shouldn't be using Request.QueryString, but rather passing those as parameters to your action method
Example in VB:
Function Retrieve(ByVal aa as String, ByVal bb as String) as ActionResult
You can access the Query String values in 2 ways...
grab the values in the controller initialization
use the values in your action
specifying the route with those variables
1 - grab the values in the controller initialization
protected override void Initialize(RequestContext requestContext) {
// you can access and assign here what you need and it will be fired
// for every time he controller is initialized / call
string aa = requestContext.HttpContext.Request.QueryString["aa"],
bb = requestContext.HttpContext.Request.QueryString["bb"];
base.Initialize(requestContext);
}
2 - use the values in your action
public void ActionResult Index(string aa, string bb) {
// use the variables aa and bb,
// they are the routing values for the keys aa and bb
}
3 - specifying the route with those variables
routes.MapRoute(
"Receive",
"Receive/{aa}/{bb}",
new {
controller = "Home",
action = "Index",
aa = UrlParameter.Optional,
bb = UrlParameter.Optional }
);
Use "Receive/" for the url in the route, and don't use Request.Querystring.
You can modify your action to be
public ActionResult Index(string aa, string bb) {...}
The ASP.Net MVC framework will hydrate those items for you.
Your HTTP 404 error is because your new route is very likely in the wrong place. Make sure your new route is before the default route:
routes.MapRoute(
"Receive",
"Receive",
new { controller = "Home", action = "Index" }
);
routes.MapRoute(
"Default", // Route name
"{controller}/{action}/{id}", // URL with parameters
new { controller = "Home", action = "Index", id = UrlParameter.Optional } // Parameter defaults
);

Having trouble with a simple MVC route

Having some trouble with some routes. I don't fully understand the MVC routing system so bear with me.
I've got two controllers, Products and Home (with more to come!).
I want to have the views within the Home controller accessible without having to type Home in the url. Essentially I want to turn www.example.com/home/about into www.example.com/about, however I still want to preserve the www.example.com/products.
Here's what I have so far.
routes.MapRoute( "Home", "{action}", new { controller = "Home" } );
routes.MapRoute(
"Default",
"{controller}/{action}/{id}",
new { controller = "home", action = "index", id = UrlParameter.Optional }
);
Now depending on which one is first I can get either one or the other to work, but not both.
I think what you might be looking for is something that that the author of the code below has termed a Root Controller. I have used this myself on a couple sites, and it really makes for nice URLS, while not requiring you to create more controllers that you'd like to, or end up with duplicate URLs.
This route is in Global.asax:
// Root Controller Based on: ASP.NET MVC root url’s with generic routing Posted by William on Sep 19, 2009
// http://www.wduffy.co.uk/blog/aspnet-mvc-root-urls-with-generic-routing/
routes.MapRoute(
"Root",
"{action}/{id}",
new { controller = "Root", action = "Index", id = UrlParameter.Optional },
new { IsRootAction = new IsRootActionConstraint() } // Route Constraint
);
With this defined elsewhere:
public class IsRootActionConstraint : IRouteConstraint
{
private Dictionary<string, Type> _controllers;
public IsRootActionConstraint()
{
_controllers = Assembly
.GetCallingAssembly()
.GetTypes()
.Where(type => type.IsSubclassOf(typeof(Controller)))
.ToDictionary(key => key.Name.Replace("Controller", ""));
}
#region IRouteConstraint Members
public bool Match(HttpContextBase httpContext, Route route, string parameterName, RouteValueDictionary values, RouteDirection routeDirection)
{
string action=values["action"] as string;
// Check for controller names
return !_controllers.Keys.Contains(action);
}
#endregion
}
The RootActionContraint alows you to still have other routes, and prevents the RootController actions from hiding any controllers.
You also need to create a controller called Root. This is not a complete implementation. Read the original article here
Have you tried:
routes.MapRoute(
"Home_About",
"About",
new { controller = "Home", action = "About" } );
routes.MapRoute(
"Default",
"{controller}/{action}/{id}",
new { controller = "home", action = "index", id = UrlParameter.Optional }
);
Products should still be handled by the Default route, while the first one can handle your About route.

MapRoute (Asp.Net MVC 2.0 .NET 4.0)

is there any possibility to create a maproute which would use always one method and it won't be necessary to put it in address?
I mean I've got controller with one method (Index) and it displays items depend on methods argument.
public ActionResult Index(string TabName)
{
var tab = (from t in BlogDB.Tabs
where t.TabName == TabName
select t).SingleOrDefault();
ViewData.Model =(Tab)tab;
return View();
}
and what I want is that I can display items putting address "www.example.com/Tabs/TabName" without "/Index/" between Tabs and TabName. I've tried:
routes.MapRoute(
"Tabs1",
"Tabs/{TabName}",
new { controller = "Tabs", action = "Index", TabName = UrlParameter.Optional }
);
But it doesn't work.
do you still have the default route? and if yes is it defined before this one?
Your problem is that asp.net mvc is trying to find the Tabs controller and the Tabname action.
Put this route before the default {controller}/{action} route

actionlink not resolving urls related to route

I have the following route ( it's the first in my global.asax )
routes.MapRoute(
"AdminCompany", // Route name
"{controller}.aspx/{action}/{companyId}/{id}", // URL with parameters
new { controller = "Home", action = "Index", companyId = "", id = "" } // Parameter defaults
);
if i navigation to
"Order/DisplayAdmin/2/79000180" it resolves correctly
However if i do the following
Html.ActionLink("View", "DisplayAdmin", new {companyId = Model.CompanyId, id = order.OrderNumber }, new { #class = "button add" })
it displays
/Order.aspx/DisplayAdmin/39068760?companyId=0
which also works, but isn't so pretty :)
Here is my Controller Method
public ActionResult DisplayAdmin(int companyId, [DefaultValue(0)]int id, [DefaultValue(0)] int orderItemStatusId)
{
var viewModel = DisplayAdminViewModel(companyId, id, _statusResponses);
return View(viewModel);
}
Am i calling ActionLink the wrong way? how do i get the nice Urls?
only thing I can think of that is happening is that its falling back to the Default route, I did a copy paste of both your route and the html.ActionLink and it works perfectly for me displaying it like "/Order.aspx/DisplayAdmin/39068760/45456", i did replicate the same fault like you get if the naming isn't the same in the route and action link.
Use the overload of ActionLink that has a RouteValueDictionary argument.
It appears that you are currently using the overload with the "object" argument and it's going to a workable, but not as clean, url.