Skip to content

SupplyParameterFromQuery triggers OnParametersSet after Navigation using AuthorizeRouteView #48241

@jofford

Description

@jofford

Is there an existing issue for this?

  • I have searched the existing issues

Describe the bug

When navigating away from a Blazor page that has a Parameter with SupplyParameterFromQuery, the OnParametersSet event will trigger unexpectedly on the page you're leaving from after OnNavigateAsync has been called. It only appears to happen when using the Microsoft.AspNetCore.Components.Authorization component "AuthorizeRouteView" in App.razor.

My basic authorization setup:

public sealed class MyRequirement : IAuthorizationRequirement { }

public class AuthHandler : AuthorizationHandler<MyRequirement>
{
    protected override Task HandleRequirementAsync(AuthorizationHandlerContext context, MyRequirement requirement)
    {
        context.Succeed(requirement);
        return Task.CompletedTask;
    }
}

public class AuthProvider : AuthenticationStateProvider
{
    public override Task<AuthenticationState> GetAuthenticationStateAsync()
    {
        ClaimsIdentity identity = new();
        ClaimsPrincipal principal = new(identity);

        return Task.FromResult(new AuthenticationState(principal));
    }
}

Program.cs:

var builder = WebAssemblyHostBuilder.CreateDefault(args);
builder.RootComponents.Add<App>("#app");
builder.RootComponents.Add<HeadOutlet>("head::after");

builder.Services.AddAuthorizationCore(options =>
{
    AuthorizationPolicyBuilder builder = new();
    builder.Requirements.Add(new MyRequirement());
    options.DefaultPolicy = builder.Build();
});

builder.Services.AddScoped<AuthenticationStateProvider, AuthProvider>();
builder.Services.AddScoped<IAuthorizationHandler, AuthHandler>();
builder.Services.AddScoped<MyService>();

await builder.Build().RunAsync();

App.razor:

<CascadingAuthenticationState>
    <Router AppAssembly="@typeof(App).Assembly" OnNavigateAsync="OnNavigate">
        <Found Context="routeData">
            <FocusOnNavigate RouteData="@routeData" Selector="h1" />
            <AuthorizeRouteView RouteData="routeData" DefaultLayout="@typeof(MainLayout)">
                <NotAuthorized>Not authorized.</NotAuthorized>
                <Authorizing>Authorizing..</Authorizing>
            </AuthorizeRouteView>
        </Found>
        <NotFound>
            <PageTitle>Not found</PageTitle>
            <LayoutView Layout="@typeof(MainLayout)">
                <p role="alert">Sorry, there's nothing at this address.</p>
            </LayoutView>
        </NotFound>
    </Router>
</CascadingAuthenticationState>

@code {
    private void OnNavigate()
    {
        Console.WriteLine("OnNavigateAsync");
    }
}

TestPage.razor:

@page "/test"

<a href="/">Leave this page</a>
<p>Value = @Value</p>

@code {
    [Parameter, SupplyParameterFromQuery(Name = "v")] public string Value { get; set; }

    protected override void OnParametersSet()
    {
        Console.WriteLine("MyPage: OnParametersSet");
    }
}

You will see in the console that navigation occurs then OnParametersSet is called from the previous page.

Expected Behavior

OnParametersSet should not be called from the page you're navigating away from.

Steps To Reproduce

See attached code and example. Visit the /test page then click the link to navigate away.

sample app.zip

Exceptions (if any)

No response

.NET Version

7.0.203

Anything else?

No response

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions