我正在将用户迁移到AspNet.Identity架构。我必须使用基于int的主键。我想将用户从旧表迁移到新的Aspnet.Users
表,以便旧表中的旧主键值也用于同一记录的新表中。
为此我启用了Identity_Insert
,但UserManager
忽略了它。是否可以使用基于int的PK-s并UserManager
将预定义值插入Identity列?
这是我到目前为止所尝试的:
static void Main(string[] args)
{
AppContext appctx = new AppContext();
IdUserStore store = new IdUserStore(appctx);
IdUserManager manager = new IdUserManager(store);
DbContextTransaction t = appctx.Database.BeginTransaction();
appctx.Database.ExecuteSqlCommand("SET Identity_INSERT dbo.AspNetUsers ON");
IdUser u = new IdUser()
{
//id is set, UserManagerManager ignores this values in the insert
Id = 123,
UserName = "examplename",
Email = "hello@example.com"
};
IdentityResult r = manager.CreateAsync(u).Result;
t.Commit();
}
抛出的异常说:
当IDENTITY_INSERT设置为ON或复制用户插入NOT FOR REPLICATION标识列时,必须为表'AspNetUsers'中的标识列指定显式值。
这是生成的T-SQL,它缺少IdUser对象上的Id值:
INSERT [dbo].[AspNetUsers]([Email], [EmailConfirmed], [PasswordHash], [SecurityStamp], [PhoneNumber], [PhoneNumberConfirmed], [TwoFactorEnabled],[LockoutEndDateUtc], [LockoutEnabled], [AccessFailedCount], [UserName])
VALUES (@0, @1, NULL, @2, NULL, @3, @4, NULL, @5, @6, @7)
SELECT [Id]
FROM [dbo].[AspNetUsers]
WHERE @@ROWCOUNT > 0 AND [Id] = SCOPE_IDENTITY()
答案 0 :(得分:1)
您必须指示实体框架,Id属性不是由DB生成的,可以通过代码进行设置。
您可以在映射中确认它,如下所示:
Property(x => x.Id)
.HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
或者,如果您使用声明方式,请将DatabaseGenerated attribute添加到Id属性:
[DatabaseGenerated(DatabaseGeneratedOption.None)]
迁移完所有数据后,请删除此配置以恢复数据库中的默认ID生成。