User.Claims.FirstOrDefault()。在登录操作(ASP.NET 身份 3)时值为空?
User.Claims.FirstOrDefault().Value is null at Login action (ASP.NET Identity 3)?
在使用 "Individual User Account" 创建默认 ASP.NET 核心后,我试图在登录操作中从用户对象获取 "id" 值,它始终为 returns 空值。该行是 (var objUser = User.Claims.FirstOrDefault().Value;)
[HttpPost]
[AllowAnonymous]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Login(LoginViewModel model, string returnUrl = null)
{
ViewData["ReturnUrl"] = returnUrl;
if (ModelState.IsValid)
{
// This doesn't count login failures towards account lockout
// To enable password failures to trigger account lockout, set lockoutOnFailure: true
var result = await _signInManager.PasswordSignInAsync(model.Email, model.Password, model.RememberMe, lockoutOnFailure: false);
if (result.Succeeded)
{
var objUser = User.Claims.FirstOrDefault().Value;
_logger.LogInformation(1, "User logged in.");
return RedirectToLocal(returnUrl);
}
if (result.RequiresTwoFactor)
{
return RedirectToAction(nameof(SendCode), new { ReturnUrl = returnUrl, RememberMe = model.RememberMe });
}
if (result.IsLockedOut)
{
_logger.LogWarning(2, "User account locked out.");
return View("Lockout");
}
else
{
ModelState.AddModelError(string.Empty, "Invalid login attempt.");
return View(model);
}
}
// If we got this far, something failed, redisplay form
return View(model);
}
从 Home/Index
等其他操作访问时,用户对象不为空
public IActionResult Index()
{
var x = User.Claims.FirstOrDefault().Value;
return View();
}
有没有办法在 result.Succeeded 之后在登录操作中拥有用户对象?
谢谢,
AG
我想我找到了答案。
var u = await _userManager.FindByEmailAsync(model.Email);
var u_Id = u.Id;
谢谢,
AG
我认为这里的问题是,在用户登录时创建了 claimsprincipal,并且 cookie 身份验证中间件将其序列化为身份验证 cookie,该 cookie 添加到响应中,因此它作为响应。
由于 cookie 的机制,在浏览器将其传回服务器的下一个请求之前,您无法读取 cookie。这是因为您在将 cookie 传回 Web 浏览器的 Response 上设置了 cookie,并且您在 Web 浏览器将 cookie 传递给服务器的 Request 上读取了 cookie。在 post 登录时浏览器还没有通过身份验证 cookie,因为它还没有收到它。您已将其设置在响应中,但如前所述,要从服务器代码访问它,它来自请求而不是响应。
在下一个请求中,cookie 作为 header 传递,然后 cookie 身份验证中间件可以将其从 cookie 反序列化为 ClaimsPrincipal,这就是您的代码中的 "User"控制器。因此,填充的用户和声明在下一个请求之前不可用,然后您可以从请求而不是响应中获取它。
因此,例如,如果您需要根据登录期间分配的声明选择重定向到哪里,您可以这样做的一种方法是重定向到另一个操作,并且该操作是一个新请求,因此可以访问从 cookie 中反序列化的 claimsprincipal,然后可以根据声明再次重定向。缺点是双重重定向。
您也可以按照您在自己的答案中显示的那样查找用户,如果这能满足您的需要,但是您得到的是 ApplicationUser 或 class 代表您的用户的任何东西,这不是一回事作为 ClaimsPrincipal。
在使用 "Individual User Account" 创建默认 ASP.NET 核心后,我试图在登录操作中从用户对象获取 "id" 值,它始终为 returns 空值。该行是 (var objUser = User.Claims.FirstOrDefault().Value;)
[HttpPost]
[AllowAnonymous]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Login(LoginViewModel model, string returnUrl = null)
{
ViewData["ReturnUrl"] = returnUrl;
if (ModelState.IsValid)
{
// This doesn't count login failures towards account lockout
// To enable password failures to trigger account lockout, set lockoutOnFailure: true
var result = await _signInManager.PasswordSignInAsync(model.Email, model.Password, model.RememberMe, lockoutOnFailure: false);
if (result.Succeeded)
{
var objUser = User.Claims.FirstOrDefault().Value;
_logger.LogInformation(1, "User logged in.");
return RedirectToLocal(returnUrl);
}
if (result.RequiresTwoFactor)
{
return RedirectToAction(nameof(SendCode), new { ReturnUrl = returnUrl, RememberMe = model.RememberMe });
}
if (result.IsLockedOut)
{
_logger.LogWarning(2, "User account locked out.");
return View("Lockout");
}
else
{
ModelState.AddModelError(string.Empty, "Invalid login attempt.");
return View(model);
}
}
// If we got this far, something failed, redisplay form
return View(model);
}
从 Home/Index
等其他操作访问时,用户对象不为空public IActionResult Index()
{
var x = User.Claims.FirstOrDefault().Value;
return View();
}
有没有办法在 result.Succeeded 之后在登录操作中拥有用户对象?
谢谢, AG
我想我找到了答案。
var u = await _userManager.FindByEmailAsync(model.Email);
var u_Id = u.Id;
谢谢, AG
我认为这里的问题是,在用户登录时创建了 claimsprincipal,并且 cookie 身份验证中间件将其序列化为身份验证 cookie,该 cookie 添加到响应中,因此它作为响应。
由于 cookie 的机制,在浏览器将其传回服务器的下一个请求之前,您无法读取 cookie。这是因为您在将 cookie 传回 Web 浏览器的 Response 上设置了 cookie,并且您在 Web 浏览器将 cookie 传递给服务器的 Request 上读取了 cookie。在 post 登录时浏览器还没有通过身份验证 cookie,因为它还没有收到它。您已将其设置在响应中,但如前所述,要从服务器代码访问它,它来自请求而不是响应。
在下一个请求中,cookie 作为 header 传递,然后 cookie 身份验证中间件可以将其从 cookie 反序列化为 ClaimsPrincipal,这就是您的代码中的 "User"控制器。因此,填充的用户和声明在下一个请求之前不可用,然后您可以从请求而不是响应中获取它。
因此,例如,如果您需要根据登录期间分配的声明选择重定向到哪里,您可以这样做的一种方法是重定向到另一个操作,并且该操作是一个新请求,因此可以访问从 cookie 中反序列化的 claimsprincipal,然后可以根据声明再次重定向。缺点是双重重定向。
您也可以按照您在自己的答案中显示的那样查找用户,如果这能满足您的需要,但是您得到的是 ApplicationUser 或 class 代表您的用户的任何东西,这不是一回事作为 ClaimsPrincipal。