aspnetcore: Cannot add additional claims to Blazor WebAssembly 3.2.0 Preview 4 application

I created a Asp.Net Core hosted Blazor webassembly 3.2.0 Preview 3 application with the authentication option of In-App accounts. I then added a few additional attributes to the ApplicationUser class, and migrated these changes to the database, and registered a few users, which was successful. I then implemented a custom claims factory like so:

public class MyCustomUserClaimsPrincipalFactory : UserClaimsPrincipalFactory<ApplicationUser>
{
    public MyCustomUserClaimsPrincipalFactory(
        UserManager<ApplicationUser> userManager,
        IOptions<IdentityOptions> optionsAccessor)
            : base(userManager, optionsAccessor)
    {
    }
    protected override async Task<ClaimsIdentity> GenerateClaimsAsync(ApplicationUser user)
    {
        var identity = await base.GenerateClaimsAsync(user);
        identity.AddClaim(new Claim(ClaimTypes.GivenName, user.FirstName ?? string.Empty));
        .....

        return identity;
    }
}

and registered the claims factory in the server application like so:

services.AddDefaultIdentity<ApplicationUser>(options => options.SignIn.RequireConfirmedAccount = true)
            .AddEntityFrameworkStores<ApplicationDbContext>()
            .AddClaimsPrincipalFactory<MyCustomUserClaimsPrincipalFactory>();

However, when I list the claims in a client web app component, I do not see any of the additional claims I added in the custom claims factory. The code I am using to list the claims is:

<AuthorizeView>
   <Authorized>
    <ul>
        @foreach (var claim in context.User.Claims)
        {
            <li><span>@claim.Type</span><span>@claim.Value</span></li>
        }
    </ul>
   </Authorized>
</AuthorizeView>

I verified that the claims factory code is being called. How can I get the additional claims in the client web app? Note: I have even tried using ClaimsTransformer (as suggested here) but I still do not see the additional claims

About this issue

  • Original URL
  • State: closed
  • Created 4 years ago
  • Comments: 21 (18 by maintainers)

Most upvoted comments

And in that issue @rubeesh is asking the same question: “How can i add extra information like employee id, name to claims

But enough already, I’m not feeling particular wonderful with your short answers “we’ve docs for this”, and “not relevant” is just plain arrogant in my humble opinion. I’m #nobody, but still a person.

@JeepNL I’m sorry if I came out as arrogant, I was trying to help you out while I was in the middle of other things and was just trying to give you a fast answer. Based on the issue title pointing to preview4 and one of the linked SO questions referring to preview 3 I interpreted that the questions where made in the context of the initial version we released, which we improved in later previews.

I hope you understand that I’m not trying to dispatch you, I only wanted to give you an answer as fast as possible and that I was doing so while handling other work. I’m a human too and it’s been a long day for me too, so again I apologize if my answers came back as rude, it was not my intention.

I’ll look at this in more detail in the following days and will try to provide a more complete/concrete answer.

Hope that helps.

@JeepNL Look at the Troubleshoot section of the doc … I put some (IMO) very helpful advice there to deal with that.

Yes! … I lived thru sheer hell with lingering cookies during testing. My new approach with an automated inprivate/incognito browser that clears cookies for every change (new browser opens every run) is a PURE JOY to work with. 🏖️

I was also trying to add custom claims (“DisplayName”) for the Blazor WASM (Hosted) project. I had already got Identity and AzureAD working following this guide: https://docs.microsoft.com/en-us/aspnet/core/security/blazor/webassembly/hosted-with-identity-server?view=aspnetcore-3.1&tabs=visual-studio

I had also found another article about adding custom claims for asp.net core by creating a custom IUserClaimsPrincipalFactory and registering it. i.e.

public class ApplicationClaimsPrincipalFactory :UserClaimsPrincipalFactory<ApplicationUser, ApplicationRole>
{
    public ApplicationClaimsPrincipalFactory(UserManager<ApplicationUser> userManager, RoleManager<ApplicationRole> roleManager, IOptions<IdentityOptions> optionsAccessor)
    : base(userManager, roleManager, optionsAccessor)
    {
    }


    protected override async Task<ClaimsIdentity> GenerateClaimsAsync(ApplicationUser user)
    {
        var identity = await base.GenerateClaimsAsync(user);
        identity.AddClaim(new Claim("DisplayName", $"{user.FirstName} {user.LastName}"));
        return identity;
    }
}


//.... register it. If using a custom SignInManager do it before that
services.AddDefaultIdentity<ApplicationUser>(options => options.SignIn.RequireConfirmedAccount = true)
    .AddRoles<ApplicationRole>()
    .AddEntityFrameworkStores<ApplicationDbContext>()
    .AddClaimsPrincipalFactory<ApplicationClaimsPrincipalFactory>()
    .AddSignInManager<ApplicationSiginInManager>();

This claim is available server side but not in the client. I tried many things without success but then I remembered the guide linked above tells your to create and register a IProfileService. So I thought I would see what would happen if I modified that.

public Task GetProfileDataAsync(ProfileDataRequestContext context)
{
   //...

    context.IssuedClaims.AddRange(context.Subject.FindAll("DisplayName"));

    return Task.CompletedTask;
}

Doing this worked. The claim was now available in the client. Not sure if this is the correct way to do it.