ASP.NET Core Identity - Quick Reference
SkillSecurityASP.NET Core Identity for authentication, roles, claims, and external providers. Covers Identity setup, customization, and token-based auth.
Available today. Use it from your connected AI after setup.
No other account needed.
Connect ahel once, and every AI you use reads what you have installed.
Then ask your AI: use the ASP.NET Core Identity - Quick Reference skill
What this skill tells your AI
The instructions your AI receives, as published by claude-dev-suite/claude-dev-suite in skills/backend-frameworks/aspnet-identity/SKILL.md and read by ahel’s review.
Deep Knowledge: Use
mcp__documentation__fetch_docswith technology:aspnet-corefor Identity documentation.
Setup
// Program.cs
builder.Services.AddIdentity<ApplicationUser, IdentityRole>(options =>
{
options.Password.RequireDigit = true;
options.Password.RequiredLength = 12;
options.Password.RequireNonAlphanumeric = true;
options.Lockout.DefaultLockoutTimeSpan = TimeSpan.FromMinutes(15);
options.Lockout.MaxFailedAccessAttempts = 5;
options.User.RequireUniqueEmail = true;
})
.AddEntityFrameworkStores<AppDbContext>()
.AddDefaultTokenProviders();
Custom User Entity
public class ApplicationUser : IdentityUser
{
public string FirstName { get; set; } = default!;
public string LastName { get; set; } = default!;
public DateTime CreatedAt { get; set; }
}
Registration & Login
public class AuthService
{
private readonly UserManager<ApplicationUser> _userManager;
private readonly SignInManager<ApplicationUser> _signInManager;
public async Task<IdentityResult> RegisterAsync(RegisterRequest request)
{
var user = new ApplicationUser
{
UserName = request.Email,
Email = request.Email,
FirstName = request.FirstName,
LastName = request.LastName,
};
return await _userManager.CreateAsync(user, request.Password);
}
public async Task<SignInResult> LoginAsync(LoginRequest request)
{
return await _signInManager.PasswordSignInAsync(
request.Email, request.Password, request.RememberMe, lockoutOnFailure: true);
}
}
Role-Based Authorization
// Seed roles
using var scope = app.Services.CreateScope();
var roleManager = scope.ServiceProvider.GetRequiredService<RoleManager<IdentityRole>>();
foreach (var role in new[] { "Admin", "User", "Manager" })
{
if (!await roleManager.RoleExistsAsync(role))
await roleManager.CreateAsync(new IdentityRole(role));
}
// Assign role
await _userManager.AddToRoleAsync(user, "Admin");
// Controller
[Authorize(Roles = "Admin")]
public IActionResult AdminPanel() => Ok();
// Policy-based
builder.Services.AddAuthorization(options =>
{
options.AddPolicy("RequireAdmin", policy => policy.RequireRole("Admin"));
options.AddPolicy("MinAge", policy =>
policy.RequireClaim("DateOfBirth")
.RequireAssertion(ctx =>
{
var dob = DateTime.Parse(ctx.User.FindFirst("DateOfBirth")!.Value);
return DateTime.Today.Year - dob.Year >= 18;
}));
});
External Login Providers
builder.Services.AddAuthentication()
.AddGoogle(options =>
{
options.ClientId = builder.Configuration["Auth:Google:ClientId"]!;
options.ClientSecret = builder.Configuration["Auth:Google:ClientSecret"]!;
})
.AddMicrosoftAccount(options =>
{
options.ClientId = builder.Configuration["Auth:Microsoft:ClientId"]!;
options.ClientSecret = builder.Configuration["Auth:Microsoft:ClientSecret"]!;
});
Anti-Patterns
| Anti-Pattern | Why It's Bad | Correct Approach |
|---|---|---|
| Custom password hashing | Insecure | Use Identity's PasswordHasher<T> |
| Storing plain-text passwords | Security risk | Identity hashes automatically |
| No account lockout | Brute-force vulnerable | Enable lockout options |
| Roles in JWT claims only | Not enforced server-side | Validate from store |
Quick Troubleshooting
| Issue | Likely Cause | Solution |
|---|---|---|
| Login always fails | Wrong password config | Check PasswordOptions |
| User not found | Case sensitivity | Identity is case-insensitive by default |
| Token expired | Short token lifetime | Adjust TokenLifespan |
| External login redirect fails | Wrong callback URL | Check provider's redirect URIs |
Signals
- GitHub stars
- 33
- Forks
- 6
- Last commit
- Sep 2026
Advanced
- Catalog kind
- skill
- Gateway key
aspnet-identity- Source
- github.com/claude-dev-suite/claude-dev-suite