JasonX
JasonX

Reputation: 543

Routing using ASPNET Core 2.0 RazorPages

I've done quite some ASP.NET API programming over the years, but am very new to .NET Core and RazorPages. I cannot seem to get routing working properly.

For example, I have an Index page. The OnGet works fine, as expected, it returns the Razor defined page. Now I add another method, let's call it Test to the Index page codebehind, like so:

[Route("Test")]
public void Test()
{
    Console.WriteLine("Test");
}

Now for the life of me, I cannot access this route, neither by localhost/Index/Test or localhost/Test or any other convoluted route I can think of. Is this by design? Both localhost and localhost/index return the default get method.

This is causing me quite a bit of trouble where I am trying to display a product's details using the owner and product Id in a pretty URL, like so:

products/{ownerid}/{productid}

As mentioned above, I cannot map to this custom pretty URL. If I understand correctly, the functions mapping to the {ownerid}/{productid} route should be in the index page codebehind in order to be found, or am I mistaken?

Thank you for your help.

Upvotes: 5

Views: 6904

Answers (4)

Ben Adams
Ben Adams

Reputation: 3431

Add it to the page directive for at the top of the .cshtml page:

@page "{ownerid}/{productid}"

If they are ints then also add that constraint

@page "{ownerid:int}/{productid:int?}"

Upvotes: 3

causita
causita

Reputation: 1708

Have you look at page handlers?

You can use something like:

<form method="GET">
    <input asp-page-handler="Test"> 
</form>

public IActionResult OnGetTest()
{
}

Upvotes: 0

Borisni
Borisni

Reputation: 91

You can do it with multiple handlers: in your codebehind:

public class FooModel : PageModel
{
    public void OnGet()
    {
        Trace.TraceInformation("Returns the page");
    }

    public IActionResult OnGetTest()
    {
        return new OkObjectResult( "Test" );
    }
}

You could call Test function with request: GET foo?handler=test.
Also, you can configure a page route to call it with GET foo/test. You can do it in foo.cshtml file with @page directive:

@page "{handler?}"
@model FooModel
@{
    ViewData["Title"] = "Foo";
}
<h2>Foo</h2>

Or you can add route in Startup.cs:

public void ConfigureServices(IServiceCollection services)
    {
        services
        .AddMvc()
        .AddRazorPagesOptions( options =>
        {
            options.Conventions.AddPageRoute( "/foo", "foo/{handler?}" );
        } );
    }

Same way you can add a route with parmeters:

options.Conventions.AddPageRoute( "/foo", "products/{ownerId}/{productId}" );

and in codebehind:

public void OnGet( string productId, string ownerId)
    {
        Trace.TraceInformation("IDs: {0}, {1}", productId, ownerId );
    }

Upvotes: 9

Svek
Svek

Reputation: 12848

I think what you are looking for is this:

Products.cshtml

@pages "{ownerId}" // note this part! very important!
@using Microsoft.AspNetCore.Mvc.RazorPages
@model ProductsModel

@functions {
    public class ProductsModel : PageModel
    {
        public void OnGet(string ownerId) // pass the string
        {
            // your code here
        }
    }
}

<div>...</div>

This would then map to http://localhost/products/{ownerid}

I hope this gets you going in the right direction with dealing with routes in RazorPages.

Upvotes: 0

Related Questions