dotnet / aspnetcore

ASP.NET Core is a cross-platform .NET framework for building modern cloud-based web applications on Windows, Mac, or Linux.
https://asp.net
MIT License
35.44k stars 10.02k forks source link

Blazor WASM - Azure AD B2C - .NET 5 prerelease v5.0.0-rc.1.20451.17 Login Errors #26195

Closed BruceHunter closed 4 years ago

BruceHunter commented 4 years ago

I have setup a Azure B2C tenant. Note: prior to upgrading from .NET Core 3.1 to .NET 5 my project authentication was working fine.

The error I am getting is the following after accessing the login page, entering my credentials, and redirected back to my application (blazor wasm):

Gets here and stays

image

error abc.b2clogin.com/abc.onmicrosoft.com/b2c_1_signin/oauth2/v2.0/token:1 Failed to load resource: the server responded with a status of 400 (Bad Request)

Extra Information: index.html image

RedirectToLogin.razor image

App.razor image

MyProject.csproj image

AppSetting.json - I changed the dns and client id values. Note: I did not setup a signup user flow, just signin.

{
  "AzureAdB2C": {
    "Authority": "https://abc.b2clogin.com/abc.onmicrosoft.com/B2C_1_signin",
    "ClientId": "111-111-111-111",
    "ValidateAuthority": false
  }
}

To check if it's my project, I did the following.

dotnet new blazorwasm -au IndividualB2C --aad-b2c-instance "https://abc.b2clogin.com/sshnet.onmicrosoft.com/" --client-id "111-111-111-111" --domain "abc.onmicrosoft.com" -o appname -ssp "B2C_1_signin"

Everything looks exactly the same, except for the appsetting.json inserts the domain value in the uri.

{ "AzureAdB2C": { "Authority": "https://abc.b2clogin.com/abc.onmicrosoft.com/B2C_1_signin", "ClientId": "111-111-111-111", "ValidateAuthority": false } }

If I run the app with it configured with the domain value, this is the error I get.

image

Access to fetch at 'https://abc.b2clogin.com/sshnet.onmicrosoft.com/b2c_1_signin/v2.0/.well-known/openid-configuration' from origin 'https://localhost:5001' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource. If an opaque response serves your needs, set the request's mode to 'no-cors' to fetch the resource with CORS disabled.
abc.b2clogin.com/abc.onmicrosoft.com/b2c_1_signin/v2.0/.well-known/openid-configuration:1 Failed to load resource: net::ERR_FAILED

If I change the AppSettings.json to how I have it with my application and remove 'domain' like so..

{
  "AzureAdB2C": {
    "Authority": "https://abc.b2clogin.com/abc.onmicrosoft.com/B2C_1_signin",
    "ClientId": "111-111-111-111",
    "ValidateAuthority": false
  }
}

Then I now get redirected to the login page and I can login

image

But I then get the same exact error as my application.

image

image

Note: My Azure B2C Application configuration hasn't changed and was working with the .NET Core 3.1 applications just fine.

Hopefully, this is not a bug and I'm just not aware of something and can get pointed towards a fix.

Zhiyuan-Amos commented 4 years ago

I'm facing a similar problem as well.

I followed the Blazor WASM Standalone with AAD B2C tutorial (also tried Hosted with AAD B2C), and upon successful login, I get redirected to https://localhost:5001/authentication/login-callback as expected.

However, I am stuck on this page. On further inspection, I noticed the following

Printed on Console

AuthenticationService.js:32 POST https://{AAD B2C INSTANCE}/{TENANT DOMAIN}/b2c_1_signin/oauth2/v2.0/token 400 (Bad Request)

Network: The request to the above url returns the following response

error: "invalid_request"
error_description: "AADB2C90079: Clients must send a client_secret when redeeming a confidential grant.
↵Correlation ID: 160af7fb-4a31-4436-9fc6-f92aa4e99f56
↵Timestamp: 2020-09-23 10:59:07Z

It seems that the login is successful as Azure Portal does show that the user has performed a successful sign in request. However, the Blazor WASM app doesn't recognise that I've logged in.

I've tried with .NET Core 3.1 as well and it works fine.

BruceHunter commented 4 years ago

@Zhiyuan-Amos I see that same 'client_secret' error if I look deeper.

I've tried all kinds of things by changing the authority value. With and without {Tenant domain}. One min I get cors error and the other I can login and get 400 as we are seeing here.

With

{
  "AzureAdB2C": {
    "Authority": "https://{AAD B2C INSTANCE}/{TENANT DOMAIN}/B2C_1_signin",
    "ClientId": "111-111-111-111",
    "ValidateAuthority": false
  }
}

Without

{
  "AzureAdB2C": {
    "Authority": "https://{AAD B2C INSTANCE}/B2C_1_signin",
    "ClientId": "111-111-111-111",
    "ValidateAuthority": false
  }

}

The entire reason I want to upgrade to .NET 5 is for the redirect feature. Who wants a popup when logging in? Not me!

Program.cs

builder.Services.AddMsalAuthentication(options =>
{
    builder.Configuration.Bind("AzureAdB2C", options.ProviderOptions.Authentication);

    //turn off popup window!
    options.ProviderOptions.LoginMode = "redirect";

    //sign out, the user should be brought back to the home page
    options.AuthenticationPaths.LogOutSucceededPath = "";
});
BruceHunter commented 4 years ago

I am getting word from a Microsoft employee, which I am in contact with via email; when you upgrade, that you should be using Azure B2C application auth plane application registration "spa" and not "web". Switching over causes other issues, such as not even getting to the login page. with this error. (This is not in the documentation)

image

MSFT Employee Quote : PKCE is picked up via the underlying MSALjs component (which is pushed into blazor wasm by js interop). The 2.x version of msaljs uses pkce, which is what dictates the requirement for pkce - msal 2x doesn't do implicit flow at all.

BruceHunter commented 4 years ago

@Zhiyuan-Amos Update from MSFT Employee (Email conversation):

Quote:

OK I see what's going on - short version is about 5 teams are all coalescing at once - b2c supports pkce, but msal 2x does not yet support it for b2c, but msaljs 2 is what's in rc5.

I'll check in with a few folks to get the current story on timelines - in the interim, it looks like popup with netcore 3.1 is the best bet until this gets sorted.

BruceHunter commented 4 years ago

@Zhiyuan-Amos @bratsche I have a confirmed workaround/hack

1) You need to choose 'spa' when registering the blazor wasm with .NET 5 RC1 image

2) Expose API image

3) Add a scope scope_name: user_impersonation display name: user_impersonation description: fix

4) Take that Application ID URI + scope and add this line to program.cs

builder.Services.AddMsalAuthentication(options =>
{
    builder.Configuration.Bind("AzureAdB2C", options.ProviderOptions.Authentication);

    //hack for now! msft bug
    options.ProviderOptions.DefaultAccessTokenScopes = new[] { "https://{your ID URI}/user_impersonation" };
    //hack for now! msft bug
});

As a bonus if you don't want the popup and redirect back to home page do this.

builder.Services.AddMsalAuthentication(options =>
{
    builder.Configuration.Bind("AzureAdB2C", options.ProviderOptions.Authentication);

    //hack for now! msft bug
    options.ProviderOptions.DefaultAccessTokenScopes = new[] { "https://{your ID URI}/user_impersonation" };
    //hack for now! msft bug

    // no popup window
    options.ProviderOptions.LoginMode = "redirect";

    //sign out, the user should be brought back to the home page
    options.AuthenticationPaths.LogOutSucceededPath = "";

});
BruceHunter commented 4 years ago

Above is a workaround, but MSFT still needs to apply a fix when they release RC2

captainsafia commented 4 years ago

Thanks for reporting this issue folks! It looks like you've run into a dupe of #25961

Also, @guardrex, we should document the need to change the configuration from Web to SPA when upgrading from 3.2 to 5.

guardrex commented 4 years ago

Coming soon for the Blazor WASM security topics on https://github.com/dotnet/AspNetCore.Docs/issues/19503. Working on the doc updates should start this week or next and should take less than a week (or a little more if I hit any major snags).

Just a general note in passing to all of the community subscribers here: We don't usually document major framework updates until at least RC1 because the change sets are too time-consuming to keep up with preview-to-preview. Now that we've entered RC1, pre-release docs can be worked up. I'm just waiting on a couple of open PRs to merge before starting the work. The work shouldn't (in theory) take long, so I anticipate docs within a few weeks. You can keep an :eye: on https://github.com/dotnet/AspNetCore.Docs/issues/19503 for an attached PR and then track on the PR when it appears.

captainsafia commented 4 years ago

@guardrex Thanks!

I'll be taking a look at fixing the scopes issue as outlined in #25961 as part of RC2. I'll close this issue in favor of the other that we are using for tracking.