Search code examples
c#.netazure-ad-b2cazure-ad-msal

Azure B2C Token audience refer to own client id


As the title say i am currently acquiring a token in my .net 6 console app, but the audience is reffering to itself when it should be referring to another application. I am using a custom policy for login and signup, that i am also using on my 3 SPA sites where it is working as expected. Here is the code in the console application:

string clientId = "<clientID>";
string authority = "https://<custom_login_dns>/tfp/<TenantId>/B2C_1A_SIGNUP_SIGNIN";
string redirecturi = "http://localhost:3000";
string[] scopes = new string[] {
    "openid", "profile", "offline_access",
    "https://<resourcename>/<apiname>/tasks.read",
    "https://<resourcename>/<apiname>/tasks.write"
};
var app = PublicClientApplicationBuilder.
            Create(clientId).
            WithAuthority(authority).
            WithRedirectUri(redirecturi).
            Build();

var accounts = await app.GetAccountsAsync();
AuthenticationResult result;
try
{
    result = await app.AcquireTokenSilent(scopes, accounts.FirstOrDefault()).ExecuteAsync();
}
catch (MsalUiRequiredException)
{
    result = await app.AcquireTokenInteractive(scopes).ExecuteAsync();
}

And the api permissions in app registration

enter image description here

Thank you in advance.


Solution

  • I have one application named B2C API app where I exposed API scopes as below:

    enter image description here

    Now, I registered one Azure AD B2C application named ClientB2C and added API permissions in it:

    enter image description here

    When I ran your code in my environment, it asked me to sign in interactively with below screen:

    enter image description here

    After completing the authentication, I got access token successfully in response like this:

    using Microsoft.Identity.Client;
    
    string clientId = "e05c1257-585e-4fd2-ae70-xxxxxxxxx";
    string authority = "https://srib2caadtenant.b2clogin.com/tfp/360d9b86-d102-41e4-871f-xxxxxxxxx/B2C_1A_SIGNUP_SIGNIN";
    string redirecturi = "http://localhost:3000";
    string[] scopes = new string[] {
        "openid", "profile", "offline_access",
        "https://srib2caadtenant.onmicrosoft.com/b2cApi/tasks.read",
        "https://srib2caadtenant.onmicrosoft.com/b2cApi/tasks.write"
    };
    var app = PublicClientApplicationBuilder.
                Create(clientId).
                WithAuthority(authority).
                WithRedirectUri(redirecturi).
                Build();
    
    var accounts = await app.GetAccountsAsync();
    AuthenticationResult result;
    try
    {
        result = await app.AcquireTokenSilent(scopes, accounts.FirstOrDefault()).ExecuteAsync();
        Console.WriteLine("Access token: {0}", result.AccessToken);
    }
    catch (MsalUiRequiredException)
    {
        result = await app.AcquireTokenInteractive(scopes).ExecuteAsync();
        Console.WriteLine("Access token: {0}", result.AccessToken);
    }
    

    Response:

    enter image description here

    When I decoded the above token in jwt.ms website, I got aud and scp claims with right values:

    enter image description here

    To confirm that, I checked API application(client) ID in Portal where it has same value as below:

    enter image description here

    In your case, check if you are using API application itself to acquire token. To reproduce your use case, I added permissions in API application itself like below:

    enter image description here

    Now, I generated access token by passing API application ID in clientId parameter like below:

    enter image description here

    When I decoded the token, I too got audience referred to own client id where azp and aud claims are same as below:

    enter image description here