I need to create a custom route with MVC to build a custom search:
Default Home's Index's Action:
public virtual ActionResult Index()
{
return View();
}
And I would like to read a string like this:
public virtual ActionResult Index(string name)
{
// call a service with the string name
return View();
}
For an URL like:
www.company.com/name
The problem is that I have this two routes but it's not working:
routes.MapRoute(
name: "Name",
url: "{name}",
defaults: new { controller = "Home", action = "Index", name = UrlParameter.Optional }
);
routes.MapRoute(
name: "Default",
url: "{controller}/{action}/{id}",
defaults: new { controller = "Home", action = "Index", area = "", id = UrlParameter.Optional }
);
This way, any controller other then Home is redirected to Home, and if I switch the order, it can't find the Index Home Action.
You can use attribute routing for this. You can see the details about the package here. After installing the attribute routing package. Now a days it is installed by default for MVC5 application. Change your action method as below:
[GET("{name}")]
public virtual ActionResult Index(string name)
{
// call a service with the string name
return View();
}
Here's a catch for the code above:
The router will send the requests without the name also to this action method. To avoid that, you can change it as below:
[GET("{name}")]
public virtual ActionResult Index2(string name)
{
// call a service with the string name
return View("Index");
}
Related
This question already has answers here:
Asp.Net Routing - Display complete URL
(3 answers)
Closed 6 years ago.
When i redirect from a Controller using
RedirectToAction("Index", "Controller");
Or Generate a link with UrlHelper
#Url.Action("Index","Controller");
In both ways the "/Index" Part is striped down from my URL.
Although for SEO Purposes i want my url to be displayed always at the same manner.
www.domain.com/en/Controller/Index
but now i get
www.domain.com/en/Controller
How can i force these two methods above always display the "/Index" Part.
P.S I know this happens because "Index" is indicated as a Default action on my route, but either way i want it to be displayed.
Add new role in RouteConfig with before default route with Index action
routes.MapRoute(
name: "DefaultIndex",
url: "{controller}/Index/{id}",
defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
);
Check your configuration inside global.asax file. It can be like this.
public static void RegisterRoutes(RouteCollection routes)
{
routes.MapRoute(
"Default", // Route name
"{controller}/{action}/{id}", // URL with parameters
new { controller = "Controller", action = "Index", id = UrlParameter.Optional });
}
Maybe based on your mask you always going to default route. So just remove default mapping.
You can try do this:
public class HomeController : Controller
{
public ActionResult Index()
{
ViewBag.Message = "Modify this template to jump-start your ASP.NET MVC application.";
return RedirectToAction("About","Home");
}
public ActionResult About()
{
ViewBag.Message = "Your app description page.";
return View();
}
public ActionResult Contact()
{
ViewBag.Message = "Your contact page.";
return View();
}
}
I need to redirect on different action based on role. I have made following changes to RouteConfig.cs.
RouteConfig.cs
routes.MapRoute(
name: "borrower",
url: "borrower",
defaults: new { controller = "Home", action = "Borrower" });
routes.MapRoute(
name: "broker",
url: "broker",
defaults: new { controller = "Home", action = "Broker" });
routes.MapRoute(
name: "Default",
url: "{controller}/{action}/{id}",
defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional });
Here is my controller
HomeController.cs
public class HomeController : Controller
{
public ActionResult Index()
{
if (UserPrincipal.Current.Identity.IsAuthenticated)
{
if (UserPrincipal.Current.IsInRole("Broker"))
{
return RedirectToRoute("broker");
}
else if (UserPrincipal.Current.IsInRole("Borrower"))
{
return RedirectToRoute("borrower");
}
}
return View();
}
public ActionResult Broker()
{
return View();
}
public ActionResult Borrower()
{
return View();
}
}
Code flow is working properly till return RedirectToRoute("")but after this code flow never goes to related/appropriate action and empty view is returned.
NOTE: Both Broker and Borrower views are not empty they have static text.
In network tab you can see proper redirect is being performed and URL in browser is being set to route URL.
RedirectToRoute("Broker") result in 302 response and user is redirected to abc.com/broker as it should but abc.com/broker does not hit Broker action method in HomeController and empty view is returned. According to RouteConfig.cs it should hit Broker action method.
Please point out what I'm doing wrong here.
It turned out that I had a directory named "Borker" and "Borrower" at root of the web project. Due to this MVC routing module was being ignored and requests (abc.com/broker and abc.com/borrower) was moved to these directory. So I renamed these directories and everything worked as expected :)
A simple routing scenario is not working for me.
my route registration looks like this
context.MapRoute(
"Users_default",
"Users/{controller}/{action}/{id}",
new { action = "Index", id= UrlParameter.Optional });
and i am expecting it to honor the requests for
users/profile/
users/profile/1
users/profile/2
with the following controller
public class ProfileController : Controller
{
public ActionResult Index(int? id)
{
var user = id == null ? (UserModel)HttpContext.Session["CurrentUser"] : userManager.GetUserById((int)id);
return View(user);
}
}
it works for users/profile but not for users/profile/1
i've tried few different things but i know the answer must be simple, its just my lack of knowledge, what am i missing here.
i dont want index to appear. i want to use the same method for both users/profile/1 and users/profile/
Then don't put action into your URL.
context.MapRoute(
"Users_default",
"Users/{controller}/{id}",
new { action = "Index", id= UrlParameter.Optional });
The route you have defined will not allow index to be optional because it is followed by another parameter (in this case "id"). Only the last parameter can be optional on all but the default route.
This is because your route interprets as:
{controller: "profile", action: "1"}.
You need to point you details action url explicit, something like this:
users/profile/index/1
You can use Attribute routing
The code would look like
public class ProfileController : Controller
{
[Route("users/profile/{id}")]
public ActionResult Index(int? id)
{
var user = id == null ? (UserModel)HttpContext.Session["CurrentUser"] : userManager.GetUserById((int)id);
return View();
}
}
And you have to modify your RouteConfig
public class RouteConfig
{
public static void RegisterRoutes(RouteCollection routes)
{
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
// This will enable attribute routing in your project
routes.MapMvcAttributeRoutes();
routes.MapRoute(
name: "Default",
url: "{controller}/{action}/{id}",
defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
);
}
}
So now you can use users/profile for your default behaviour and users/profile/ for a specific profile.
I would like to have an Index action with an optional string parameter. I'm unable to make it work.
I need the following routes:
http://mysite/download
http://mysite/download/4.1.54.28
The first route will send a null model to the Index view, and the second one will send an string with the version number.
How can I define the route and the controller?
This is my route definition:
routes.MapRoute(
name: "Download",
url: "Download/{version}",
defaults: new { controller = "Download", action = "Index", version = UrlParameter.Optional }
);
routes.MapRoute(
name: "Default",
url: "{controller}/{action}/{id}",
defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
);
And this is the controller:
public ActionResult Index(string version)
{
return View(version);
}
Why does this not work? I'm not an expert in ASP MVC but this seems to be a very simple problem.
The error
When I go to http://mysite/downloads it works fine
When I go to http://mysite/downloads/4.5.6, the controller is correctly called, and the parameter is correctly passed. But then seems that the view is not found. This is the error I found:
string? will not work because string is not a value type.
You can set a default value to your parameter:
public ActionResult Index(string version="")
{
return View(version);
}
The issue is fixed passing the parameter to the view in the following way:
public ActionResult Index(string version)
{
return View((object)version);
}
Or
public ActionResult Index(string version)
{
return View("Index", version);
}
When you pass a string model to the view, if the model is a string parameter, it is interpreted as the view name due to the following overload method
View(String viewName)
Your Download route is conflicting with your Default route. Comment out the Download route and it will probably work.
BTW you can install RouteDebugger to figure out these kind of problems for yourself.
Your controller is looking for a view with the same name as the version attribute entered in the url (e.g. 4.1.54.28). Are you intentionally looking for a view with that name, in which case it should be in the Views/Download folder or your project. If however you simply want to pass it to the default view as a variable to be used on the page your best off sticking it in a model or you can just stick it in ViewBag if it's a one off.
Also you don't need to use:
Public ActionResult Index(string version)
You can use routedata instead e.g.
Public ActionResult Index()
{
string version = RouteData.Values["Version"].ToString();
ViewBag.version = version;
return View();
}
Hope this of some help
You are not set action name in url like {action}
you can try:
routes.MapRoute(
name: "Download",
url: "Download/{action}/{version}",
defaults: new { controller = "Download", action = "Index", version = UrlParameter.Optional }
);
I'm pretty sure it's because in the View you state it is an optional parameter, but your controller says that it is mandatory. Change the signature of your index method to expect a nullable param
public ActionResult Index(string? version)
{
return View(version);
}
Why not have two methods in your download controller:
public ActionResult Index()
{
return View();
}
[HttpGet, ActionName("Index")]
public ActionResult IndexWithVersion(string version)
{
return View(version);
}
I want to create a URLs shortener website. URLs that I offer are like example.com/XXX where
XXX is the value of the short URL.
I want to have website on example.com and URLs are example.com/xxx. I want to get xxx from URL and redirect users to equivalent URLs in database.
How can implement this?
Create a new route in your RouteConfig for example:
public class RouteConfig
{
public static void RegisterRoutes(RouteCollection routes)
{
routes.IgnoreRoute("{resource}.axd/{*pathInfo}");
routes.MapRoute("empty",
"{id}",
new {controller = "Home", action = "Index", id = UrlParameter.Optional}
);
routes.MapRoute(
name: "Default",
url: "{controller}/{action}/{id}",
defaults: new { controller = "Home", action = "Index", id = UrlParameter.Optional }
);
}
}
And the simply go to your database with the id passed in the index
public ActionResult Index(int id)
{
//Do Stuff with db
return View();
}
asp.net mvc documentation here.
One way you be doing the needed redirection in the default controller action. By default in asp.net mvc it is home/index.
So in the index action you should be having such code
public ActionResult Index(string id)
{
var url = Db.GetNeededUrl(id);
return Redirect(url);
}
So now if the user enters such an address site.com/NewYear you'll get redirected to the equivalent url that is in you database.