[英]How to add new users from a logged-in user?
当我从头开始创建新用户(注册)并从登录用户创建新用户时,我有这种奇怪的行为,这些用户不依赖于下面的数据库(在这种情况下我使用的是postgreSQL)。 但首先是这里的关系:
现在,无论是在注册时间还是登录时间,我都使用UserManager
来创建用户。
首先,我创建一个新的UserSetting
, SaveChanges()
然后将AppUser
属性UserSettingId
分配给新创建的实体的Id
值。
如果您已经是已注册和登录的用户,或者您是新注册用户,则此处失败取决于该代码不会更改:
var userSettings = await _userService.UserSettings.AddAsync(new UserSettings
{
LanguageId = langId,
ThemeId = themeId
});
//wrapper to the Context.SaveChangesAsync()
//failure point!
if (!await _userService.SaveChangesAsync<bool>())
并且异常错误(在已经登录的用户创建新用户时)讨论了已经存在的PK_LanguageId
就好像我正在创建一个新的Language实体一样,但正如您所看到的,我只是分配一个默认值langId
到新的UserSetting
。 这是例外截图:
(抱歉意大利语,它会自动翻译)简短翻译: Languages
重复键,就像它试图插入一个新的Language
实体一样。
在Startup
,注册服务( _userService
)是暂时的。
这是OnModelCreating
的模型类及其配置:
public class AppUser : IdentityUser
{
public long UserSettingsId { get; set; }
public virtual UserSettings UserSettings { get; set; }
//...other properties
}
public class UserSettings
{
public long Id { get; set; }
public int LanguageId { get; set; }
public virtual Language Language { get; set; }
public int ThemeId { get; set; }
public virtual Theme Theme { get; set; }
public virtual AppUser AppUser { get; set; }
}
public class Theme
{
[Key]
public int Id { get; set; }
[StringLength(10)]
public string Type { get; set; }
}
public class Language
{
[Key]
public int Id { get; set; }
public string Name { get; set; }
[MaxLength(2)]
public string Code { get; set; }
}
builder.Entity<AppUser>().HasKey(u => u.Id);
builder.Entity<AppUser>().HasOne(u => u.UserSettings).WithOne(us => us.AppUser);
builder.Entity<UserSettings>().HasKey(us => us.Id);
builder.Entity<UserSettings>().Property(us => us.Id).ValueGeneratedOnAdd();
builder.Entity<UserSettings>().HasOne(us => us.Language);
builder.Entity<UserSettings>().HasOne(us => us.Theme);
我做错了什么? 为什么它的表现如此不同? 是否有不同的方法从已登录的用户创建用户?
问题可能是您正在将对象添加到数据库上下文,并将其标记为已添加。 因为数据库上下文不知道存在Language
和Theme
对象,所以它试图插入所有这些对象。
它可能与postgreSQL提供程序有关。 您可能想要检查已打开的问题。
我建议先尝试从数据库加载Language
对象,然后尝试添加新的UserSettings
。
找到行为的来源,这是该死的UserManager.GetUserAsync()
,我用它来获取当前登录的用户,稍后添加UserSettings
将“管理员”的设置传播到新的创建帐户。
GetUserAsync(User)
确实返回一个确实被跟踪的实体(而不是像我想的那样,像AsNoTracking()
)。 因此,当我填写它的UserSetting
我确实添加了一个带有新子类属性的新UserSetting
!
Sooo,永远不要指望UserManager
会在没有跟踪的情况下为用户提供!
感谢所有参与这项工作的人。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.