Overview
Blazor WASM apps call web APIs using a preconfigured HttpClient
service which is focused on HttpClient
service configurations manually for requests to other web APIs.
- Documentation: https://learn.microsoft.com/en-us/aspnet/core/blazor/call-web-api?view=aspnetcore-7.0&pivots=webassembly
Sending PATCH Requests
If sending HTTP PATCH requests, there are additional considerations beyond those listed in these notes.
See:
https://learn.microsoft.com/en-us/aspnet/core/blazor/call-web-api?view=aspnetcore-7.0&pivots=webassembly#patch-as-json-patchasjsonasync
Using the Preconfigured HttpClient
Add the HttpClient service to the DI container:
Program.cs
builder.Services.AddScoped(sp => new HttpClient { // The client's base address is set to the originating server's address: BaseAddress = new Uri(builder.HostEnvironment.BaseAddress) });
Inject required services:
SomeComponent.razor
@using System.Net.Http <!-- For HttpClientJsonExtensions: --> @using System.Net.Http.Json @inject HttpClient Http
Send requests from the component in the
OnInitializedAsync()
method after the component has finished initializing:SomeComponent.razor
@code { private TodoItem[]? todoItems; protected override async Task OnInitializedAsync() => todoItems = await Http.GetFromJsonAsync<TodoItem[]>("api/TodoItems"); }
Using the IHttpClientFactory
Instead of injecting a preconfigured HttpClient
, IHttpClientFactory
can be used instead, similar to
how it is used in other .NET apps.
Both named and typed clients are supported.
Named Client Example
Program.cs
:
builder.Services.AddHttpClient("NAMED_CLIENT_NAME", client =>
client.BaseAddress = new Uri(builder.HostEnvironment.BaseAddress));
SomeComponent.razor
@inject IHttpClientFactory ClientFactory
<!-- ... -->
@code {
// ...
protected override async Task OnInitializedAsync()
{
var client = ClientFactory.CreateClient("NAMED_CLIENT_NAME");
result = await client.GetFromJsonAsync<SomeModel[]>("SomeModel");
}
}
Typed Client Example
- Add
Microsoft.Extensions.Http
to the app:dotnet add package Microsoft.Extensions.Http
- Create the typed client:
SomeHttpClient.cs
public class SomeHttpClient { private readonly HttpClient http; private SomeModel[]? results; public SomeHttpClient(HttpClient http) { this.http = http; } public async Task<SomeModel[]> GetResultsAsync() { results = await http.GetFromJsonAsync<SomeModel[]>("/api/endpoint"); return results ?? Array.Empty<SomeModel>(); } }
- Use the typed client:
SomeComponent.razor
@inject SomeHttpClient Http <!-- ... -->
@code { private SomeModel[]? results; protected override async Task OnInitializedAsync() { results = await Http.GetResultsAsync(); } }
Fetch API Request Options
Blazor WASM’s implementation of HttpClient
uses Fetch API. Fetch API can be configured with request-specific options via HttpRequestMessage
extension methods:
Extension Method | Use to… |
---|---|
SetBrowserRequestCache | |
SetBrowserRequestCredentials | …include credentials in a cross-origin request |
SetBrowserRequestIntegrity | |
SetBrowserRequestMode | |
SetBrowserResponseStreamingEnabled | …enable support for response streaming |
Additional options can be set via the generic SetBrowserRequestOption extension method.
Cross-Origin Resource Sharing (CORS)
Browser security restricts a web page from making requests to a different domain than the one that served the web page. This is called the same-origin policy.
Adjust the names and ports of WithOrigins
as needed for the app:Program.cs
// ...
app.UseCors(policy => policy
.WithOrigins("http://localhost:5000", "https://localhost:5001")
.AllowAnyMethod()
.WithHeaders(HeaderNames.ContentType);
// ...
See also: https://learn.microsoft.com/en-us/aspnet/core/security/cors?view=aspnetcore-7.0
Testing a Web API
Blazor framework’s reference source has HttpClient
test assets:
https://github.com/dotnet/aspnetcore/tree/main/src/Components/test/testassets/BasicTestApp/HttpClientTest