0

I am attempting to create a very flexible routing system that allows users to configure their own publishable url paths to their own content pages, sort of like a CMS. To achieve this, I created a generic controller and route that accepts 3 parameters in this form:

https://localhost:8080/{route1}/{route2}/{route3}

This is my controller:

public class XController : Controller
{
    [HttpGet("{route1?}/{route2?}/{route3?}")]
    public async Task<IActionResult> Index([FromRoute] string? route1, [FromRoute] string? route2, [FromRoute] string? route3)
    {
        if (User == null || User.Identity == null || !User.Identity.IsAuthenticated)
            return Unauthorized();
        //do some stuff here
        return View("/views/X/Index.cshtml", model);
    }
}

And this works great. However, I still want to use some "predefined" routes for special functions, such as logging in, account management, payments, etc. So my thinking is to have some predefined routes for these special controllers, and then everything else goes to the generic controller defined above. Unfortunately, EVERYTHING, even my "predefined" routes are going to the generic controller. I have routing defined like this:

app.MapControllerRoute(
    name: "default",
    defaults: new { controller = "Home", action = "Index" },
    pattern: "{controller=Home}/{action=Index}/{id?}");
app.MapControllerRoute(
    name: "account",
    defaults: new { controller = "Account", action = "Index" },
    pattern: "{controller=Account}/{action=Index}/{id?}");
app.MapControllerRoute(
    name: "x",
    defaults: new { controller = "X", action = "Index" },
    pattern: "{route1?}/{route2?}/{route3?}");

So, for example, if I navigate to https://localhost:8080/account/login, the generic controller defined above is still handling the request, instead of my "Account" controller. I would like requests to my "predefined" routes to be handled by their respective named controllers, and everything else to be handled by the generic controller.

Am I trying to achieve something that is not doable, or is there a better way of doing this? Or, am I perhaps missing something simple? How can I have a handful of predefined routes to named controllers, and then every other route that does not match those controllers be handled by the generic (controller-less) controller?

7
  • It's quite odd, especially you have defined route for Home, Account controller. By right based on sequence, it should match those "default", "account" rule first. I would say you can try to remove the "x" rule first to ensure the existing Account routes are navigated correctly. Commented Jul 18 at 1:08
  • Anyhow, I feel both "default" and "account" rules are redundant as those values in defaults and pattern are predefined if it is not provided in the route. For example, when you browse "/", it will navigate to "Home/Index". For "account", you specify a route rule unless you have specified a pattern such as pattern: "Account/{action=Index}/{id?}" Commented Jul 18 at 1:15
  • Thinking this is what you try to achieve: Map wildcard in .NET Core WebApplication Commented Jul 18 at 1:21
  • 1
    Yes it is odd. I also have tried doing just attribute routing (the 3 entries in Program.cs have been removed), and I decorated my two controllers with [HttpGet("{route1?}/{route2?}/{route3?}")] and [HttpGet("account/login")]. Now both controllers get hit when I navigate to account/login. Commented Jul 18 at 3:04
  • I see, I think that you shouldn't specify that route: {route1}/{route2}/{route3} in your XController. But what you should look for the map wildcard (that I shared in the previous comment) or a fallback route app.MapFallback() to redirect to the XController Index action. Then, within the action, you can extract the route parameter. But the downside is it could be shown "/X/Index/{original route}" URL in the browser. Commented Jul 18 at 3:37

0

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.