Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/asp.net/33.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 如何使用ASP.NET Identity Framework设置密码过期_C#_Asp.net_Passwords_Asp.net Identity - Fatal编程技术网

C# 如何使用ASP.NET Identity Framework设置密码过期

C# 如何使用ASP.NET Identity Framework设置密码过期,c#,asp.net,passwords,asp.net-identity,C#,Asp.net,Passwords,Asp.net Identity,我有一个使用Identity的ASP.NET项目。对于有关密码的身份配置,将使用PasswordValidator。如何将密码的强制执行扩展到PasswordValidator当前拥有的(RequiredLength,RequiredDigit等)之外,以满足要求密码在N天后过期的要求?ASP.NET Identity 2中没有内置此类功能。最简单的方法是在用户上添加一个字段,如LastPasswordChangedDate。然后在每次授权期间检查此字段 public class Applica

我有一个使用Identity的ASP.NET项目。对于有关密码的身份配置,将使用
PasswordValidator
。如何将密码的强制执行扩展到
PasswordValidator
当前拥有的(
RequiredLength
RequiredDigit
等)之外,以满足要求密码在N天后过期的要求?

ASP.NET Identity 2中没有内置此类功能。最简单的方法是在用户上添加一个字段,如LastPasswordChangedDate。然后在每次授权期间检查此字段

public class ApplicationOAuthProvider : OAuthAuthorizationServerProvider
{
    public override async Task GrantResourceOwnerCredentials(OAuthGrantResourceOwnerCredentialsContext context)
    {
        var user = await GetUser(context.UserName, context.Password);
        if(user.LastPasswordChangedDate.AddDays(20) < DateTime.Now)
           // user needs to change password

    }
}
公共类ApplicationAuthProvider:OAuthAuthorizationServerProvider
{
公共重写异步任务GrantResourceOwnerCredentials(OAuthGrantResourceOwnerCredentials上下文)
{
var user=await GetUser(context.UserName、context.Password);
if(user.LastPasswordChangedDate.AddDays(20)
在@Rikard的答案上添加

我将
LastPasswordChangedDate
添加到我的
ApplicationUser
模型中,如下所示:

    public class ApplicationUser : IdentityUser
    {
        public DateTime LastPasswordChangedDate { get; set; }

        public async Task<ClaimsIdentity> GenerateUserIdentityAsync(UserManager<ApplicationUser> manager)
        {
            // Note the authenticationType must match the one defined in CookieAuthenticationOptions.AuthenticationType
            var userIdentity = await manager.CreateIdentityAsync(this, DefaultAuthenticationTypes.ApplicationCookie);
            // Add custom user claims here
            return userIdentity;
        }
    }
然后,在
登录期间
,检查用户是否应重置密码。这只会在成功登录后进行检查,以免对用户造成太多的bug

        [HttpPost]
        [AllowAnonymous]
        [ValidateAntiForgeryToken]
        public async Task<ActionResult> Login(LoginViewModel model, string returnUrl)
        {
            if (!ModelState.IsValid)
            {
                return View(model);
            }

            // This doesn't count login failures towards account lockout
            // To enable password failures to trigger account lockout, change to shouldLockout: true
            var result = await SignInManager.PasswordSignInAsync(model.Email, model.Password, model.RememberMe, shouldLockout: false);
            switch (result)
            {
                case SignInStatus.Success:
                    var user = await UserManager.FindByNameAsync(model.Email);
                    if (user.LastPasswordChangedDate.AddDays(PasswordExpireDays) < DateTime.UtcNow)
                    {
                        return RedirectToAction("ChangePassword", "Manage");
                    }
                    else
                    {
                        return RedirectToLocal(returnUrl);
                    }
                case SignInStatus.LockedOut:
                    return View("Lockout");
                case SignInStatus.RequiresVerification:
                    return RedirectToAction("SendCode", new { ReturnUrl = returnUrl, RememberMe = model.RememberMe });
                case SignInStatus.Failure:
                default:
                    ModelState.AddModelError("", "Error: Invalid username or password");
                    return View(model);
            }
        }

@RickAnd MSFT下面的答案在哪里?@EricFalsken他在一年前发布了一个答案,但似乎被删除了。上述解决方案是处理密码退出的最简单和最好的方法。没有这样的内置功能。此时他们已登录。他们可以忽略更改密码。如何强制?如何注销它们?因此,在他们更改密码之前,他们无法做任何事情。因为你允许他们在移动到更改密码屏幕之前登录,用户难道不能点击不同的url,从而绕过更改密码吗?@JohnnyFun是对的。您应该在
Login
方法中使用
CheckPasswordSignInAsync
而不是
PasswordSignInAsync
来解决此问题
        [HttpPost]
        [AllowAnonymous]
        [ValidateAntiForgeryToken]
        public async Task<ActionResult> Login(LoginViewModel model, string returnUrl)
        {
            if (!ModelState.IsValid)
            {
                return View(model);
            }

            // This doesn't count login failures towards account lockout
            // To enable password failures to trigger account lockout, change to shouldLockout: true
            var result = await SignInManager.PasswordSignInAsync(model.Email, model.Password, model.RememberMe, shouldLockout: false);
            switch (result)
            {
                case SignInStatus.Success:
                    var user = await UserManager.FindByNameAsync(model.Email);
                    if (user.LastPasswordChangedDate.AddDays(PasswordExpireDays) < DateTime.UtcNow)
                    {
                        return RedirectToAction("ChangePassword", "Manage");
                    }
                    else
                    {
                        return RedirectToLocal(returnUrl);
                    }
                case SignInStatus.LockedOut:
                    return View("Lockout");
                case SignInStatus.RequiresVerification:
                    return RedirectToAction("SendCode", new { ReturnUrl = returnUrl, RememberMe = model.RememberMe });
                case SignInStatus.Failure:
                default:
                    ModelState.AddModelError("", "Error: Invalid username or password");
                    return View(model);
            }
        }
    [HttpPost]
    [ValidateAntiForgeryToken]
    public async Task<ActionResult> ChangePassword(ChangePasswordViewModel model)
    {
        if (!ModelState.IsValid)
        {
            return View(model);
        }
        var result = await UserManager.ChangePasswordAsync(User.Identity.GetUserId(), model.OldPassword, model.NewPassword);
        if (result.Succeeded)
        {
            var user = await UserManager.FindByIdAsync(User.Identity.GetUserId());
            if (user != null)
            {
                user.LastPasswordChangedDate = DateTime.UtcNow;
                await UserManager.UpdateAsync(user);

                await SignInManager.SignInAsync(user, isPersistent: false, rememberBrowser: false);
            }
            return RedirectToAction("Index", new { Message = ManageMessageId.ChangePasswordSuccess });
        }
        AddErrors(result);
        return View(model);
    }