2017-04-14 138 views
0

當用戶在輸入新密碼後嘗試在重置密碼屏幕上重置密碼時,我們會收到無效令牌錯誤消息。通常這對每個人都適用,即使是像#這樣的特殊字符。我們現在有一種情況,有人在復位pw屏幕上將新密碼放入*中,只是因爲這個特殊字符而得到這個錯誤信息。ASP.Net密碼重置時的密碼重置爲「無效令牌」,密碼爲

我已經嘗試了數小時的研究來找到解決方案,爲什麼發生這種情況,但沒有運氣。我找到了this solution here,它在用戶名中有特殊字符的問題,但我們沒有這個問題。密碼中的特殊字符只有一個問題。由於我們已經在生產,我們不能在密碼中禁止該字符。

有人有線索?

生成令牌控制方法:

[HttpPost] 
[AllowAnonymous] 
public async Task<ActionResult> ForgotPassword(ForgotPasswordViewModel model) 
{ 
    if (ModelState.IsValid) 
    { 
     var user = await _userManager.FindByNameAsync(model.Email.ToLower()); 
     if (user == null || !(await _userManager.IsEmailConfirmedAsync(user.UserName))) 
     { 
      // Don't reveal that the user does not exist or is not confirmed 
      return View("ForgotPasswordConfirmation"); 
     } 

     // For more information on how to enable account confirmation and password reset please visit http://go.microsoft.com/fwlink/?LinkID=320771 
     // Send an email with this link 
     var code = await _userManager.GeneratePasswordResetTokenAsync(user.UserName); 
     code = HttpUtility.UrlEncode(code); 
     var callbackUrl = Url.Action("ResetPassword", "Account", new { userId = user.UserName, code = code }, protocol: Request.Url.Scheme); 

     await _emailService.CreateResetPasswordEmailAsync(user, callbackUrl); 
     return RedirectToAction("ForgotPasswordConfirmation", "Account"); 
    } 

    // If we got this far, something failed, redisplay form 
    return View(model); 
} 

重置密碼控制器的方法:

[HttpPost] 
[AllowAnonymous] 
public async Task<ActionResult> ResetPassword(ResetPasswordViewModel model) 
{ 
    if (!ModelState.IsValid) 
    { 
     return View(model); 
    } 

    var user = await _userManager.FindByNameAsync(model.Email.ToLower()); 
    if (user == null) 
    { 
     // Don't reveal that the user does not exist 
     return RedirectToAction("ResetPasswordConfirmation", "Account"); 
    } 

    var result = await _userManager.ResetPasswordAsync(user.UserName, HttpUtility.UrlDecode(model.Code), model.Password); 
    if (result.Succeeded) 
    { 
     return RedirectToAction("ResetPasswordConfirmation", "Account"); 
    } 

    AddErrors(result); 
    return View(); 
} 
+0

你是如何generaing令牌?令牌不包含與密碼有關的任何內容,因此您看到的錯誤與您聲明的問題相關的方式非常不清楚。 – DavidG

+0

我已經添加了代碼片段 – Hypi

+0

您在哪一行看到異常發生? – DavidG

回答

1

的問題是,你是雙編碼重置令牌。在這裏:

var code = await _userManager.GeneratePasswordResetTokenAsync(user.UserName); 
code = HttpUtility.UrlEncode(code); //<--problem is this line 
var callbackUrl = Url.Action("ResetPassword", "Account", 
    new { userId = user.UserName, code = code }, protocol: Request.Url.Scheme); 

你編碼的令牌,然後Url.Action會再次這樣做。所以解決方法是不要手動編碼,讓MVC爲你處理 - 只需在這裏刪除第二行。

此外,在另一端,現在有沒有必要再進行解碼,所以你的代碼會出現:

var result = await _userManager.ResetPasswordAsync(user.UserName, 
    model.Code, model.Password); 
+0

謝謝@DavidG :) – Hypi