ASP.NET Core与SSMS自动生成GUID型字符串主键及迁移报错处理
解决ASP.NET Core EF迁移中主键从int转GUID字符串类型的错误
错误根源
你之前的两次尝试都混淆了SQL的uniqueidentifier类型与目标的nvarchar(450)字符串类型:
- 第一次直接将字符串列转为
uniqueidentifier,但原有int格式的字符串无法转换为合法GUID,触发类型转换错误。 - 第二次新增了
uniqueidentifier类型的列,但你的需求是字符串类型的GUID,且defaultValue: "NEWID()"会被EF当作字符串值而非SQL函数执行,同样引发转换错误。
正确迁移脚本
目标是创建nvarchar(450)类型的主键列,同时保留现有数据并自动填充合法的GUID字符串:
migrationBuilder.DropPrimaryKey( name: "PK_ml", table: "ml"); // 重命名旧Id列,避免直接删除丢失数据(后续可根据需要删除) migrationBuilder.RenameColumn( name: "Id", table: "ml", newName: "OldId"); // 添加新的nvarchar(450)类型Id列,设置SQL默认值生成GUID字符串 migrationBuilder.AddColumn<string>( name: "Id", table: "ml", type: "nvarchar(450)", nullable: false, defaultValueSql: "CAST(NEWID() AS nvarchar(450))"); // 为现有行填充GUID字符串(如果需要保留旧数据关联,可跳过此步,但主键必须唯一) migrationBuilder.Sql(@"UPDATE ml SET Id = CAST(NEWID() AS nvarchar(450))"); // 添加新主键 migrationBuilder.AddPrimaryKey( name: "PK_ml", table: "ml", column: "Id"); // 可选:如果确认旧列无用途,可删除 // migrationBuilder.DropColumn( // name: "OldId", // table: "ml");
ASP.NET Core实体配置
确保实体类的Id配置与数据库列匹配,实现代码层面自动生成GUID:
public class ml { public string Id { get; set; } // 其他属性... } // 在DbContext的OnModelCreating中配置 protected override void OnModelCreating(ModelBuilder modelBuilder) { modelBuilder.Entity<ml>(entity => { entity.HasKey(e => e.Id); entity.Property(e => e.Id) .IsRequired() .HasColumnType("nvarchar(450)") .HasDefaultValueSql("CAST(NEWID() AS nvarchar(450))") .ValueGeneratedOnAdd(); // 告诉EF该值由数据库生成 }); }
SSMS手动插入支持
由于已设置列的defaultValueSql,在SSMS中手动插入行时,无需指定Id值,数据库会自动生成GUID格式的字符串填充。
内容的提问来源于stack exchange,提问作者L. Wallach
相关产品推荐
相关产品推荐

