Routing In Blazor

Introduction

 
A Route is a URL pattern and Routing is a pattern matching process that monitors the requests and determines what to do with each request.
 
Blazor server app uses ASP.net Core Endpoint Routing. Using MapBlazorHub extension method of endpoint routing, ASP.net Core is start to accept the incoming connection for Blazor component. The Blazor client app provides the client-side Routing. The router is configured in Blazor client app in App.cshtml file.
 
Blazor Client app 
  1. <Router AppAssembly="@typeof(Program).Assembly"/>  
Blazor Server app 
  1. public void Configure(IApplicationBuilder app, IWebHostEnvironment env)  
  2. {  
  3. ....  
  4. ....  
  5. ....  
  6.   
  7.     app.UseRouting();  
  8.   
  9.     app.UseEndpoints(endpoints =>  
  10.     {  
  11.         endpoints.MapBlazorHub();  
  12.         endpoints.MapFallbackToPage("/_Host");  
  13.     });  
  14. }  
The Blazor Server app allows to set fallback route. It operates with low priority in routing matching. The fallback route is only considered when other routes are not matched. The fallback route is usually defined in _Host.cshtml component.
 
@page directive
 
Using @page directive, you can define the routing in Blazor component. The @page directives are internally converted into RouteAttribute when template is compiled.
  1. @page "/route1"  
In Blazor, Component can have multiple routes. If we require that component can render from multiple route values, we need to define all routes with multiple @page directives.
  1. @page "/multiple"  
  2. @page "/multiple1"  
If you have defined class only component, you can use RouteAttribute.
  1. using Microsoft.AspNetCore.Components;  
  2.   
  3. namespace BlazorServerApp.Pages  
  4. {  
  5.     [Route("/classonly")]  
  6.     public class ClassOnlyComponent: ComponentBase  
  7.     {  
  8.        ...  
  9.     }  
  10. }  
Route Template
 
The Router mechanism allows to define the routing for each component. The route template is defined in App.razor file. Here, we can define default layout page and default route data.
  1. <Router AppAssembly="@typeof(Program).Assembly">  
  2.     <Found Context="routeData">  
  3.         <RouteView RouteData="@routeData" DefaultLayout="@typeof(MainLayout)" />  
  4.     </Found>  
  5.     <NotFound>  
  6.         <LayoutView Layout="@typeof(MainLayout)">  
  7.             <p>Sorry, there's nothing at this address.</p>  
  8.         </LayoutView>  
  9.     </NotFound>  
  10. </Router>  
In above code, three components are defined under Router component: Found, NotFound and RouteView. The RouteView component receive the route data and default layout. Blazor routing mechanism render the Found component, if any route matched else render NotFound component. The NotFound component allows us to provide custom message when route or content not found.
 
Handle Parameter in Route Template
 
Route may have parameters. The parameters can be defined using curly braces within the routing template in both @page directive or RouteAttribute. The route parameters are automatically bound with component parameters by matching the name. This matching is case insensitive.
  1. <h3>Route Constraints Example</h3>  
  2. @page "/routepara/{Name}"  
  3.   
  4. <h4>Name : @Name </h4>  
  5.   
  6. @code {  
  7.     [Parameter]  
  8.     public string Name { get; set; }  
  9. }  
Current version of Blazor does not supports the optional parameter , so you must pass parameter in above example.
 
Route constraints
 
The Blazor routing also allows Route constraints. It enforces type matching between route parameter and route data. Current version of Blazor supports few route constraints but might supports many more route constraints in the future.
  1. <h3>Route Constraints Example</h3>  
  2. @page "/routecons/{Id:guid}"  
  3.   
  4. <h4>Id : @Id </h4>  
  5.   
  6. @code {  
  7.     [Parameter]  
  8.     public Guid Id { get; set; }  
  9. }  
Following route constraints are supported by Blazor
 
Constraint Invariant culture matching Example 
 int  Yes     {id:int}
 long   Yes  {id:long}
 float  Yes  {mrp:float}
 double  Yes  {mrp:double}
 decimal  Yes  {mrp:decimal}
 guid  No  {id:guid}
 bool  No  {enabled:bool}
 datetime  Yes  {birthdate:datetime}
 
NavLink Component
 
Blazor provides NavLink component that generates HTML hyperlink element and it handles the toggle of active CSS class based on NavLink component href match with the current URL.
 
There are two options for assign to Match attribute of NavLink component
  • NavLinkMatch.All: Active when it matches the entire current URL
  • NavLinkMatch.Prefix: It is a default option. It active when it matches any prefix of the current URL
The NavLink component renders as the anchor tag. You can also include the target attribute.
 
Programmatically navigate one component to another component
 
Blazor is also allowed to navigate from one component to another component programmatically using Microsoft.AspNetCore.Components.NavigationManager. The NavigationManager service provides the following events and properties.
 
Event / Method Description
 NavigateTo  It navigates to specified URI. It takes parameter "forceload", if its parameter is set to true, client-side routing is bypassed and the browser is forced to load a new page 
 ToAbsoluteUri   It converts relative URI to absolute URI
 ToBaseRelativePath  Returns relative URI with base URI prefix
 NotifyLocationChanged  This event is fired when browser location has changed
 EnsureInitialized  This method allows derived class to lazy self-initialized
 Initialize  This method set base URI and current URI before they are used
 NavigateToCore  Navigate to specified URI. This is an abstract method hence it must implement in a derived class
 
Properties Description
 BaseUri  Get and set the current base URI. It allows representing as an absolute URI end with a slash
 Uri   Get and set the current URI. It allows representing as an absolute URI
 
To navigate URI using NavigationManager service, you must inject the service using @inject directive in component. Using the NavigateTo method, you can navigate from one component to another component.
  1. @page "/navexample"  
  2. @inject NavigationManager UriHelper  
  3. <h3>Navigation Example</h3>  
  4. Navigate to other component <a href="" @onclick="NavigatetoNextComponent">Click here</a>  
  5.   
  6. @code {  
  7.     void NavigatetoNextComponent()  
  8.     {  
  9.         UriHelper.NavigateTo("newcomponent");  
  10.     }  
  11. }  
You can also capture query string or query parameter value when redirect to another component. Using QueryHelpers class, we can access query string and query parameter of the component. The QueryHelpers.ParseQuery method extract the value from the query string. This method returns the dictionary of type Dictionary<string, StringValues> that contains all query parameter of the route.
  1. <h3>New Component with Parameter</h3>  
  2. @page "/newcomponentwithpara"  
  3. @inject NavigationManager UriHelper  
  4. @using Microsoft.AspNetCore.WebUtilities;  
  5.   
  6. <p> Parameter value : @Name</p>  
  7.   
  8. @code {  
  9.     public string Name { get; set; }  
  10.     protected override void OnInitialized()  
  11.     {  
  12.         var uri = UriHelper.ToAbsoluteUri(UriHelper.Uri);  
  13.         Name = QueryHelpers.ParseQuery(uri.Query).TryGetValue("name", out var type) ? type.First() : "";  
  14.     }  
  15. }  

Summary

 
Blazor provides rich routing. Blazor server app uses ASP.net Core Endpoint Routing. It provides almost all features including route parameters, route constraints. It also provides a built-in component like NavLink that helps to generate menu items. It provides built-in services that help us to navigate from one component to another component. However, there are some limitations like route parameter does not support optional parameter and it supports a limited number of route constraints.