Fresh Blazor Webassembly Template CLI v5.0.100 produces "Unauthorized"

Viewed 385

Sorry for the newbe question.
I really need to understand what is the workaround on this new template.

Reproduce the error:
Visual Studio, Brand new Blazor App, named "Demo3"

.NET 5.0, Blazor WebAssembly App, Template "CLI v5.0.100"
ASP.NET Core Hosted, https
Authentication, Single Domain, Read directory data

Run Create

I have done this hundreds of times on previous templates. But this "new" template, imidiately produces an error I cannot figure out.

Details:
Log in as normal
Click "Fetch data" (the weather forcast)
And I get this error message.

Keywords: 401 and Unauthorized.
I guess the Unauthorized, is the important information.

info: System.Net.Http.HttpClient.Demo3.ServerAPI.ClientHandler[100]
      Sending HTTP request GET https://localhost:44345/WeatherForecast
WeatherForecast:1 Failed to load resource: the server responded with a status of 401 ()
blazor.webassembly.js:1 info: System.Net.Http.HttpClient.Demo3.ServerAPI.ClientHandler[101]
      Received HTTP response after 1272.7899ms - Unauthorized
blazor.webassembly.js:1 info: System.Net.Http.HttpClient.Demo3.ServerAPI.LogicalHandler[101]
      End processing HTTP request after 1340.08ms - Unauthorized
blazor.webassembly.js:1 crit: Microsoft.AspNetCore.Components.WebAssembly.Rendering.WebAssemblyRenderer[100]
      Unhandled exception rendering component: Response status code does not indicate success: 401 (Unauthorized).
System.Net.Http.HttpRequestException: Response status code does not indicate success: 401 (Unauthorized).
  at System.Net.Http.HttpResponseMessage.EnsureSuccessStatusCode () <0x337bf70 + 0x00052> in <filename unknown>:0 
  at System.Net.Http.Json.HttpClientJsonExtensions.GetFromJsonAsyncCore[T] (System.Threading.Tasks.Task`1[TResult] taskResponse, System.Text.Json.JsonSerializerOptions options, System.Threading.CancellationToken cancellationToken) <0x32c6740 + 0x000f4> in <filename unknown>:0 
  at Demo3.Client.Pages.FetchData.OnInitializedAsync () [0x0003c] in D:\repos\nameofrepo\src\Demo3\Demo3\Client\Pages\FetchData.razor:48 
  at Microsoft.AspNetCore.Components.ComponentBase.RunInitAndSetParametersAsync () <0x2c764b0 + 0x0013a> in <filename unknown>:0 
  at Microsoft.AspNetCore.Components.RenderTree.Renderer.GetErrorHandledTask (System.Threading.Tasks.Task taskToHandle) <0x2f401a8 + 0x000b6> in <filename unknown>:0 

As the error indicates, there is a authorization error.

My question is:
Has someone found a "offical MS link" to this error?
Or, can someone explain what is wrong.

Follow-up
Just to clearify, I do not change or add any code. The test run is done directly after the template is finished. I have, of course, tried to debug the error and look at the settings in AzureAD, but no luck.

Second follow-up
Investigated a hint, the AADSTS7000218 detail in the comment.

So I set up an project. Here are the details:
I changed to Kestrel.
I changed to Azure App settings to SPA, with the same redirect address.

Gave myself owner permissions to both apps.
Added the server to api permissions on the client app. "api://BlazorApp1_Server/user_impersonation"

Tested: Same errors. The details, and I still notice the audience detail.

Microsoft.AspNetCore.Components.WebAssembly.Rendering.WebAssemblyRenderer[100]
      Unhandled exception rendering component: Response status code does not indicate success: 401 (Unauthorized).
System.Net.Http.HttpRequestException: Response status code does not indicate success: 401 (Unauthorized).

And in the response headers:

www-authenticate: Bearer error="invalid_token", error_description="The audience 'api://blazorapp1_server' is invalid"

But nothing about AADSTS7000218 or missing client secret.

Still not giving up on this... I'll be back...

3 Answers

I managed to solve this error in my project by adding the "Audience" value into the server's appsettings.json file

  "AzureAd": {
    "Instance": "https://login.microsoftonline.com/",
    "Domain": "<domain>",
    "TenantId": "<guid>",
    "ClientId": "api://<apiname>",
    "CallbackPath": "/signin-oidc",
    "Audience": "api://blazorapp1_server"
  },

It looks like the audience validation is case-sensitive and fails if the ClientId contains uppercase letters and the audience value passed in the bearer token is in all lowercase. Adding the audience value in all lower case solved it for me.

Thank you so much! I had the same issue, and your post was the key to resolve it. One thing to add: The value for Audience is the apiname in lowercase:

"Audience": "api://<apiname in lowercase>"

I also tried to only change the ClientID to lowercase but that did not work.

In addition to adding "Audience" in appsettings.json for the server, I had to adjust the app registration for the server as follows: Select only ID tokens for server.

The platform for the server must be Web.

I also had to adjust the app registration for the client.

The platform for the client must be SPA and both token types must be deselected: Deselect token type for client.

I want to chime in and say I was really struggling with this today and Sascha Stops' answer was right on the money. Thanks a lot.

One thing I'd like to point out that with .NET 5 being released and with the latest update to Visual Studio 2019, there is now a Blazor WebAssembly template for Work or School Accounts (i.e. Azure AD authentication). I created my app with this template and assumed it would set everything up correctly. It does not.

The client app registration has the redirect URIs set up as Web instead of SPA. This was the first issue I encountered and had to change it manually after doing some research. The second problem was this audience setting being discussed here. I hope Microsoft cleans up these bugs in the template soon because I'm sure there will be a lot of confused developers out there.

Related