ASP.NET标识AddLoginAsync失败 - 名称/电子邮件X已被占用

时间:2017-07-10 23:50:28

标签: c# asp.net asp.net-identity

我遇到了使用ASP.NET身份添加外部登录的默认代码的问题。

我的帐户控制器ExternalLoginConfirmation方法中包含以下代码:

var user = new ApplicationUser { UserName = model.Email, Email = model.Email };
var result = await UserManager.CreateAsync(user);
if (result.Succeeded)
{
   result = await UserManager.AddLoginAsync(user.Id, info.Login);
   if (result.Succeeded)
   {
      //do stuff
   }
}

CreateAsync调用返回result.Succeeded == true。但是,当它流经AddLoginAsync方法时,该方法返回result.Succeeded == false,并显示以下错误:

Name foo@bar.com is already taken.
Email 'foo@bar.com' is already taken.

当我查看aspnetusers表时,我看到了CreateUserAsync方法所期望的该用户的新行。如果AddLoginAsync应该向现有用户添加登录,为什么它会抛出错误,就像它期望用户不存在一样?如果没有先在新用户实例中填充UserName和Email,则无法调用CreateAsync。

开箱即用的身份设置之间的唯一区别是我创建了一个客户ApplicationUser类,它使用int作为Id而不是字符串。

有什么想法吗?

2 个答案:

答案 0 :(得分:0)

错误消息是红鲱鱼。即使这是MS在您创建新的Web应用程序时提供的默认代码,CreateAsync调用也不会更新user对象,因为它会让您相信。在这种情况下,user.Id在传递到AddLoginAsync时仍然等于0,因此在创建用户时,您没有该对象的当前实例。

更改

var user = new ApplicationUser { UserName = model.Email, Email = model.Email };
var result = await UserManager.CreateAsync(user);

var newuser = new ApplicationUser { UserName = model.Email, Email = model.Email };
var result = await UserManager.CreateAsync(newuser);
var user = await UserManager.FindByEmailAsync(model.Email);

解决了这个问题。

答案 1 :(得分:-1)

您使用的是外部登录提供商吗?如果没有,则不应该调用AddLoginAsync()。

CreateAsync(user)正在您的本地环境中为您创建用户记录。之后,您可以选择使用SignInAsync()登录用户,但我认为您不需要调用AddLoginAsync()。