Skip to content

Add Claims to a user during login while using Identity #46558

@akhanalcs

Description

@akhanalcs

Is there an existing issue for this?

  • I have searched the existing issues

Is your feature request related to a problem? Please describe the problem.

I am honestly shocked that I have searched everywhere and tried everything but still not able to accomplish this basic behavior.
Am I missing something or is Identity missing a basic behavior?

Let me explain it:

My application is a Blazor Server project where I have added Identity following the steps mentioned here.

Now this is what I want to achieve:

  1. User enters their credentials.
  2. If the username is valid (in our Active Directory), I retrieve a field known as EmployeeId from the Active Directory.
  3. Authenticate the user using SignInManager.PasswordSignInAsync.
  4. Add EmployeeId that I retrieved in Step 2 as a claim to the ClaimsPrincipal. (So that I can use EmployeeId from Razor Components like this).

My OnPostAsync method in Login.cshtml.cs looks like this:

public class LoginModel : PageModel
{
	private readonly SignInManager<MMTUser> _signInManager;
	private readonly ILogger<LoginModel> _logger;

	public LoginModel(SignInManager<MMTUser> signInManager, ILogger<LoginModel> logger)
	{
		_signInManager = signInManager;
		_logger = logger;
	}

	// Other Properties, methods etc. here.

	public async Task<IActionResult> OnPostAsync(string returnUrl = null)
	{
		returnUrl ??= Url.Content("~/");

		if (ModelState.IsValid)
		{
			// Step 1: Check if this user exists in our AD
			// If YES: Grab the Employee Id and go to next step
			// If NO: Terminate the process
			var adLookupResult = ADHelper.ADLookup(Input.Username);
			if (adLookupResult == null || string.IsNullOrEmpty(adLookupResult.EmployeeId))
			{
				ModelState.AddModelError(string.Empty, "Invalid login attempt.");
				return Page();
			}

			// Step 2: SignIn the user
			var result = await _signInManager.PasswordSignInAsync(Input.Username, Input.Password, isPersistent: Input.RememberMe, lockoutOnFailure: false);

            // Step 3: How do I add adLookupResult.EmployeeId to the ClaimsPrincipal?

			if (result.Succeeded)
			{
				_logger.LogInformation("User logged in.");
				return LocalRedirect(returnUrl);
			}
			else
			{
				ModelState.AddModelError(string.Empty, "Invalid login attempt.");
				return Page();
			}
		}

		// If we got this far, something failed, redisplay form
		return Page();
	}
}

I tried to use ClaimsTransformer as documented here but since I cannot pass my adLookupResult.EmployeeId to TransformAsync method, I can't really use that approach.

I tried adding it using:
HttpContext.User.AddIdentity(new ClaimsIdentity(new List<Claim> { new Claim("NewClaim", "EmployeeIdFromStep2") }));
right after successful sign in, but that doesn't work.

Describe the solution you'd like

Either provide a way to pass claims value to the public Task<ClaimsPrincipal> TransformAsync(ClaimsPrincipal principal) method or provide a method to add claims during Login while using Identity.

Additional context

Full source code:
https://github.com/affableashish/blazor-server-auth/tree/feature/AddClaimsDuringLogin

Added Claims during Login (in Login.cshtml.cs file) and accessed those claims from Razor Component.

Unfortunately, it didn't work. I only get null as the claim value. 😔

Stackoverflow question:
https://stackoverflow.com/q/75377386/8644294

Metadata

Metadata

Assignees

No one assigned

    Labels

    area-identityIncludes: Identity and providers

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions