在 MVC 5 模板中实现 Facebook 登录,添加了应用程序 ID 和密码。
最初登录失败,因为它返回空值
public async Task<ActionResult> ExternalLoginCallback(string returnUrl)
{
// Crashes on this line
var loginInfo = await AuthenticationManager.GetExternalLoginInfoAsync();
if (loginInfo == null)
{
return RedirectToAction("Login");
}
}
搜索后发现一个解决方案,它说用这个替换现有的 ExternalLoginCallback 方法
[AllowAnonymous]
public async Task<ActionResult> ExternalLoginCallback(string returnUrl)
{
var result = await AuthenticationManager.AuthenticateAsync(DefaultAuthenticationTypes.ExternalCookie);
if (result == null || result.Identity == null)
{
return RedirectToAction("Login");
}
var idClaim = result.Identity.FindFirst(ClaimTypes.NameIdentifier);
if (idClaim == null)
{
return RedirectToAction("Login");
}
var login = new UserLoginInfo(idClaim.Issuer, idClaim.Value);
var name = result.Identity.Name == null ? "" : result.Identity.Name.Replace(" ", "");
// Sign in the user with this external login provider if the user already has a login
var user = await UserManager.FindAsync(login);
if (user != null)
{
await SignInAsync(user, isPersistent: false);
return RedirectToLocal(returnUrl);
}
else
{
// If the user does not have an account, then prompt the user to create an account
ViewBag.ReturnUrl = returnUrl;
ViewBag.LoginProvider = login.LoginProvider;
return View("ExternalLoginConfirmation", new ExternalLoginConfirmationViewModel { UserName = name });
}
}
现在该问题已解决,但当我尝试关联您的 Facebook 帐户时。您已成功通过 Facebook 的身份验证。请在下面输入此站点的用户名,然后单击“注册”按钮完成登录。
[HttpPost]
[AllowAnonymous]
[ValidateAntiForgeryToken]
public async Task<ActionResult> ExternalLoginConfirmation(ExternalLoginConfirmationViewModel model, string returnUrl)
{
if (User.Identity.IsAuthenticated)
{
return RedirectToAction("Manage");
}
if (ModelState.IsValid)
{
// Here comes the error System.NullReferenceException: Object reference not set to an instance of an object.
var info = await AuthenticationManager.GetExternalLoginInfoAsync();
if (info == null)
{
return View("ExternalLoginFailure");
}
var user = new ApplicationUser() { UserName = model.UserName };
var result = await UserManager.CreateAsync(user);
if (result.Succeeded)
{
result = await UserManager.AddLoginAsync(user.Id, info.Login);
if (result.Succeeded)
{
await SignInAsync(user, isPersistent: false);
return RedirectToLocal(returnUrl);
}
}
AddErrors(result);
}
ViewBag.ReturnUrl = returnUrl;
return View(model);
}
在调试用户名时也无法弄清楚为什么会抛出异常。
我认为当它到达返回 null 的 GetExternalLoginInfoSync
时。
我遇到了同样的问题,下面是我如何设法解决它并从 Facebook 收到电子邮件。
- 更新以下 NuGet 包
Microsoft.Owin
至版本 3.1.0-rc1
Microsoft.Owin.Security
到版本 3.1.0-rc1
Microsoft.Owin.Security.Cookies
到版本 3.1.0-rc1
Microsoft.Owin.Security.OAuth
到版本 3.1.0-rc1
Microsoft.Owin.Security.Facebook
到版本 3.1.0-rc1
然后在Identity Startup
类中添加如下代码
var facebookOptions = new FacebookAuthenticationOptions()
{
AppId = "your app id",
AppSecret = "your app secret",
BackchannelHttpHandler = new FacebookBackChannelHandler(),
UserInformationEndpoint = "https://graph.facebook.com/v2.8/me?fields=id,name,email,first_name,last_name",
Scope = { "email" }
};
app.UseFacebookAuthentication(facebookOptions);
这是 FacebookBackChannelHandler()
的定义类:
using System;
using System.Net.Http;
public class FacebookBackChannelHandler : HttpClientHandler
{
protected override async System.Threading.Tasks.Task<HttpResponseMessage> SendAsync(
HttpRequestMessage request,
System.Threading.CancellationToken cancellationToken)
{
// Replace the RequestUri so it's not malformed
if (!request.RequestUri.AbsolutePath.Contains("/oauth"))
{
request.RequestUri = new Uri(request.RequestUri.AbsoluteUri.Replace("?access_token", "&access_token"));
}
return await base.SendAsync(request, cancellationToken);
}
}
我是一名优秀的程序员,十分优秀!