Configure Identity primary key data type in ASP.NET Core

ASP.NET Core Identity allows you to configure the data type used to represent a primary key. Identity uses the string data type by default. You can override this behavior.

Customize the primary key data type

  1. Create a custom implementation of the IdentityUser class. It represents the type to be used for creating user objects. In the following example, the default string type is replaced with Guid.

    namespace webapptemplate.Models
    {
        // Add profile data for application users by adding properties to the ApplicationUser class
        public class ApplicationUser : IdentityUser<Guid>
        {
        }
    }
    
  2. Create a custom implementation of the IdentityRole class. It represents the type to be used for creating role objects. In the following example, the default string type is replaced with Guid.

    namespace webapptemplate.Models
    {
        public class ApplicationRole : IdentityRole<Guid>
        {
        }
    }
    
  3. Create a custom database context class. It inherits from the Entity Framework database context class used for Identity. The TUser and TRole arguments reference the custom user and role classes created in the previous step, respectively. The Guid data type is defined for the primary key.

    namespace webapptemplate.Data
    {
        public class ApplicationDbContext : IdentityDbContext<ApplicationUser, ApplicationRole, Guid>
        {
            public ApplicationDbContext(DbContextOptions<ApplicationDbContext> options)
                : base(options)
            {
            }
    
            protected override void OnModelCreating(ModelBuilder builder)
            {
                base.OnModelCreating(builder);
                // Customize the ASP.NET Core Identity model and override the defaults if needed.
                // For example, you can rename the ASP.NET Core Identity table names and more.
                // Add your customizations after calling base.OnModelCreating(builder);
            }
        }
    }
    
  4. Register the custom database context class when adding the Identity service in the app's startup class.

    The AddEntityFrameworkStores method doesn't accept a TKey argument as it did in ASP.NET Core 1.x. The primary key's data type is inferred by analyzing the DbContext object.

    public void ConfigureServices(IServiceCollection services)
    {
        services.AddDbContext<ApplicationDbContext>(options =>
            options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")));
    
        services.AddIdentity<ApplicationUser, ApplicationRole>()
            .AddEntityFrameworkStores<ApplicationDbContext>()
            .AddDefaultTokenProviders();
    
        // Add application services.
        services.AddTransient<IEmailSender, EmailSender>();
    
        services.AddMvc();
    

Test the changes

Upon completion of the configuration changes, the property representing the primary key reflects the new data type. The following example demonstrates accessing the property in an MVC controller.

[HttpGet]
[AllowAnonymous]
public async Task<Guid> GetCurrentUserId()
{
    ApplicationUser user = await _userManager.GetUserAsync(HttpContext.User);
    return user.Id; // No need to cast here because user.Id is already a Guid, and not a string
}