Skip to content

FakeNavigationManager sets "Uri" property too early #1647

Description

@ayyron-dev

Describe the bug

I would love to try submitting a PR if the maintainers agree this should be changed.

In FakeNavigationManager.NavigateToCore() the Uri is being set regardless of whether or not handlers prevented navigation.

Example:
Testing this component:

@using Microsoft.AspNetCore.Components.Routing
@inject NavigationManager nav
@implements IDisposable

<h3>Navigation</h3>
<button id="clickable" @onclick=@(() => nav.NavigateTo("/some-path"))></button>

@code {
    IDisposable? _navRegistration;

    protected override void OnInitialized()
    {
        nav.NavigateTo("/original-path");
        _navRegistration = nav.RegisterLocationChangingHandler(LocationChangingHandler);
    }

    private async ValueTask LocationChangingHandler(LocationChangingContext arg)
    {
        arg.PreventNavigation();
    }

    private void UnregisterLocationChangingHandler()
    {
        _navRegistration?.Dispose();
        _navRegistration = null;
    }

    void IDisposable.Dispose()
    {
        UnregisterLocationChangingHandler();
    }
}

With this test:

@inherits TestContext

@code {

	[Fact]
	public void PreventNavigation()
	{
		// Arrange
		var cut = Render(@<Navigation />);
		var navigationManager = Services.GetRequiredService<NavigationManager>();

		// Assert we're at the starting Uri
		Assert.Equal(new Uri(new(navigationManager.BaseUri), "/original-path").AbsoluteUri, navigationManager.Uri);

		// Act -> click the button to navigate
		var button = cut.Find("#clickable");
		button.Click();

		// Assert the path remains the original path as navigation was prevented
		Assert.Equal(new Uri(new(navigationManager.BaseUri), "/original-path").AbsoluteUri, navigationManager.Uri);
	}
}

Results in this output:

[xUnit.net 00:00:01.26]     BUnitExamples.Tests.NavigationTests.PreventNavigation [FAIL]
[xUnit.net 00:00:01.27]       Assert.Equal() Failure: Strings differ
[xUnit.net 00:00:01.27]                                   ↓ (pos 17)
[xUnit.net 00:00:01.27]       Expected: "http://localhost/original-path"
[xUnit.net 00:00:01.27]       Actual:   "http://localhost/some-path"
[xUnit.net 00:00:01.27]                                   ↑ (pos 17)
[xUnit.net 00:00:01.27]       Stack Trace:
[xUnit.net 00:00:01.27]         C:\Users\XXXXXX\source\repos\BUnitExamples\BUnitExamples.Tests\NavigationTests.razor(20,0): at BUnitExamples.Tests.NavigationTests.PreventNavigation()
[xUnit.net 00:00:01.27]            at System.RuntimeMethodHandle.InvokeMethod(Object target, Void** arguments, Signature sig, Boolean isConstructor)
[xUnit.net 00:00:01.27]            at System.Reflection.MethodInvoker.Invoke(Object obj, IntPtr* args, BindingFlags invokeAttr)
[xUnit.net 00:00:01.27]   Finished:    BUnitExamples.Tests

Expected behavior:
I would have expected the test to pass. But both line #83 and line #95 are setting the Uri property before it checks if navigation should be prevented. The History Stack is correct, but I would have expected the FakeNavigationManager to behave more like the WebAssemblyNavigationManager

Version info:

  • bUnit version: 1.34.0
  • .NET Runtime and Blazor version: net7.0 (Mcrosoft.NETCore.App 7.0.20)
  • OS type and version: Windows 11 Version 23H2

Additional context:

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions