(7/30) Learn Blazor Together: Lifecycle (Lifetime)

(7/30) Learn Blazor Together: Lifecycle (Lifetime)

Services you create yourself must be registered in Startup.cs (Blazor Server) or Program.cs (Blazor WebAssemlby), but some basic services don't need to be created by yourself.

Last updated 12/13/2021 9:38 PM
StrayaWorker
4 min read
Category
Blazor
Topic
Learn Blazor Together Series
Tags
.NET C# ASP.NET Core Blazor

As mentioned earlier, all services you create must be registered in Program.cs, but some basic services don't require manual setup.

Currently, Blazor provides three built-in services:

  1. HttpClient: Handles HTTP requests, with a Scoped lifetime (Note: Only available in Blazor WebAssembly; for Blazor Server, you must register it yourself).
  2. IJSRuntime: Provides the JavaScript runtime component for JS functionality. For Blazor WebAssembly, the lifetime is Singleton; for Blazor Server, it is Scoped.
  3. NavigationManager: Handles route navigation and state. For Blazor WebAssembly, the lifetime is Singleton; for Blazor Server, it is Scoped.

Lifetime refers to the duration a component exists. Besides Singleton and Scoped, there is also Transient.

  1. Singleton: Only one instance exists from application start to shutdown, shared by all components.
  2. Transient: A new instance is created every time the component is used.
  3. Scoped: This is special because Blazor Server and Blazor WebAssembly behave differently. In Blazor Server, Scoped means a new instance is created per HTTP request, but components communicating via SignalR do not create new instances. Microsoft documentation states, "Blazor WebAssembly does not currently have the concept of DI; Scoped is equivalent to Singleton."

However, I was also confused after reading the above explanation, until I watched a video using GUIDs to demonstrate. Let's try it out.

First, create an interface IGuidService with a single string property UId. Then create a class GuidService and initialize the UId property as a GUID string in the constructor. Next, register it in Program.cs using AddTransient.

Then create a Guid.razor component with three lines: define a route, inject the service, and display the GUID string. Since this example is simple and doesn't use ComponentBase, add @using BlazorServer.Services to _Import.razor. Finally, for easy navigation, define a set of NavLink in NavMenu.razor pointing to the newly created Guid.razor.

After starting, whether switching between the Post and Guid pages or reloading the page, you will see a new set of GUID generated each time. This is the characteristic of Transient: a new instance is created on every switch.

Next, change the registration to Singleton. Even after reloading the page, you see the same GUID. This is the characteristic of Singleton: only one instance exists from application start to shutdown.

Finally, change the registration to Scoped. Switch to the Post page and back – still the same GUID. But when you reload the page, a new set appears. This is the characteristic of Scoped: each HTTP request creates a new instance, but components do not create new instances among themselves.

The above example uses Blazor Server. If using Blazor WebAssembly, Singleton behaves differently from Blazor Server because Blazor WebAssembly has no server side. Every time the page is reloaded, the application downloads to the browser as a completely new HTTP request. Therefore, both Singleton and Scoped create a new instance whenever the page is reloaded.

Note: For brevity, I omitted some content from the video. Interested readers can explore further.

References:

Note: The code in this article is refactored using .NET 6 + Visual Studio 2022. You can click the original link to compare with the refactored code. Thanks for reading and supporting the original author.

Keep Exploring

Related Reading

More Articles
Same category / Same tag 12/25/2021

(29/30)Learn Blazor Together: Blazor Unit Testing

The most boring part of developing a system is probably fixing bugs, especially errors like trying to access a null object (`Object reference not set to an instance of an object.`), which is the most common problem most people encounter when they first step into programming. To break free from the tedious bug-fixing process, this article introduces `unit testing`.

Continue Reading
Same category / Same tag 12/25/2021

(28/30) Learning Blazor Together: Policy-based Authorization

It was mentioned earlier that `ASP.NET Core Identity` uses `Claim`-based authentication. In fact, `ASP.NET Core Identity` has different types of authorization methods, the simplest being `Login Authorization`, `Role Authorization`, and `Claim Authorization`. However, all of the above are implemented in one way: Policy-based Authorization.

Continue Reading