How to Make Ef-Core Use a Guid Instead of String for Its Id/Primary Key

How to make EF-Core use a Guid instead of String for its ID/Primary key

You need custom ApplicationUser inherit from IdentityUser<TKey> and custom Role inherit from IdentityRole<TKey>

public class ApplicationUser : IdentityUser<Guid> { }    
public class Role : IdentityRole<Guid> { }

Custom context class inherit from IdentityDbContext<ApplicationUser, Role, TKey> and use fluent api for auto generate guid keys.

public class ApplicationDbContext : IdentityDbContext<ApplicationUser, Role, Guid>
{
protected override void OnModelCreating(ModelBuilder builder)
{
base.OnModelCreating(builder);

builder.Entity<ApplicationUser>(b =>
{
b.Property(u => u.Id).HasDefaultValueSql("newsequentialid()");
});

builder.Entity<Role>(b =>
{
b.Property(u => u.Id).HasDefaultValueSql("newsequentialid()");
});
}
}

then in Startup add Identity service to container like this

services.AddIdentity<ApplicationUser, Role>()
.AddEntityFrameworkStores<ApplicationDbContext, Guid>()
.AddDefaultTokenProviders()
.AddUserStore<UserStore<ApplicationUser, Role, ApplicationDbContext, Guid>> ()
.AddRoleStore<RoleStore<Role, ApplicationDbContext, Guid>>();

If you have not created the database, clear the migrations folder and run ef commands

Entity Framework Core Auto Generated guid

The problem you are experiencing is not specific for autogenerated Guids. The same happens for any autogenerated key values, including the commonly used auto increment (identity) columns.

It's caused by a specific Data Seeding (HasData) requirement:

This type of seed data is managed by migrations and the script to update the data that's already in the database needs to be generated without connecting to the database. This imposes some restrictions:

  • The primary key value needs to be specified even if it's usually generated by the database. It will be used to detect data changes between migrations.
  • Previously seeded data will be removed if the primary key is changed in any way.

Note the first bullet. So while for normal CRUD your PK will be auto generated, you are required to specify it when using HasData fluent API, and the value must be constant (not changing), so you can't use Guid.NewGuid(). So you need to generate several Guids, take their string representation and use something like this:

mb.Entity<User>().HasData(
new User() { Id = new Guid("pre generated value 1"), ... },
new User() { Id = new Guid("pre generated value 2"), ... },
new User() { Id = new Guid("pre generated value 3"), ... }
);

Why does ASP.Net Core Identity using string for its Primary Key properties?

I cannot comment on your question at this time, but I believe this has the answers to the question you are asking:

Why asp.net Identity user id is string?

Second answer from above post:
https://stackoverflow.com/a/30029268/11191898

Depending on which version of ASP.Net authentication you're using, on the database ASP.NET Identity v2 should be storing it as a uniqueidentifier (Guid) in the AspNetUsers table. In more preceding versions it will store the user id as an int in the webpages_Membership table.

I believe it surfaces it as a string so it can be any data type you like under the hood and this can then be cast within your code as required.

.Net Core auto-generated string primary key

You need to have the attribute [DatabaseGenerated(DatabaseGeneratedOption.Identity)] added to the column. See the official documentation for more details.

How to use a missing primary key when its value is a GUID instead of int? (ASP Net Core, EF, C#)

You need to Follow as:

  1. Change DataType of DB Column With UniqueId from Int/BigInt

  2. Create/Change Property Data Type in Model class

    Public Guid Id { get; set;} or if it is nullable then Public Guid? Id { get; set;}

Then check if it is null or not while using Id == Guid.Empty

// Pseudo code

if(Id == Guid.Empty ? "Create" : "Update"){
}

Mark it Solve if answers your question



Related Topics



Leave a reply



Submit