2014-12-03 1278 views
2

表單提交後,我的防僞標記存在問題。我不斷收到此錯誤信息:提供的防僞標記用於用戶「{user}」,但當前用戶爲「」

所提供的防僞標記是爲那些用戶「{用戶}」,但當前用戶是「」

之間有什麼其他的都問的區別在這裏和我的是,這是說當前用戶是空白的,反僞造令牌正在尋找一個用戶。這是沒有意義的,因爲當我檢查HttpContext.Current.User.Identity.NameMembership.GetUser()。用戶名,他們確實有用戶防僞令牌正在尋找。這沒有任何意義。

NewRecordEntry.cshtml

<h2>New Record</h2> 
@using (Html.BeginForm()) 
{ 
    @Html.AntiForgeryToken() 
    <div id="new-record-entry"> 
     @Html.DropDownListFor(model => model.recordTypeID, Model.GetRecordTypeList()) 
    </div> 

    <input type="submit" name="NewRecordEntry" id="continue" size="11" /> 
} 

控制器

[HttpPost] 
    [ValidateAntiForgeryToken] 
    public ActionResult NewRecordEntry(FormCollection frm, NewRecordEntryViewModel nrevm) 
    { 
     TempData["NewRecordEntry"] = nrevm; 
     return RedirectToAction("NewRecord", "FakeController"); 
    }  

身份驗證篩選

public class FakeAuthenticationFilter : ActionFilterAttribute, IAuthenticationFilter 
{ 
    public void OnAuthentication(AuthenticationContext filterContext) 
    { 
     // Get userData stored in a session. Workplace environment does not allow cookies 
     UserData userData = (UserData) filterContext.HttpContext.Session[UserInfo.SessionUser]; 
     if (userData != null) 
     { 
      // Get identity and principal 
      var identity = new GenericIdentity(UserInfo.SessionUser, "Forms"); 
      var principal = new FakePrincipal(identity); 

      principal.UserData = userData; 

      // Set the context user. 
      HttpContext.Current.User = principal; 
     } 
     else 
     { 
      filterContext.Result = new RedirectResult("~/Login"); 
     } 
    } 

    public void OnAuthenticationChallenge(AuthenticationChallengeContext filterContext) 
    { 
    } 
    } 

會員

public class FakeMembershipProvider : MembershipProvider 
{ 
    public override bool ValidateUser(string username, string password) 
    { 
     // Check if this is a valid user. 
     // The application sends the username and password to an LDAP DLL which 
     // reurns "Success" if it was a match. 
     string result = LoginService.AuthenticateUser(username, password); 
     if (result == "Success") 
     { 
      return true; 
     } 
     return false; 
    } 

    public override MembershipUser GetUser(string username, bool userIsOnline) 
    { 

     if (LoginService.UserData != null) 
     { 
      return new MembershipUser("FakeMembershipProvider", 
       username, LoginService.UserData.UserID, 
       null, null, null, true, false, 
       DateTime.MinValue, DateTime.MinValue, DateTime.MinValue, 
       DateTime.MinValue, DateTime.MinValue); 
     } 
     return null; 
    } 
} 

登錄後控制器

#region Login Post Controllers 
    [HttpPost] 
    [ValidateAntiForgeryToken] 
    public ActionResult Login(FormCollection frm, LoginViewModel lvm, string returnUrl) 
    { 
     List<string> errorList = null; 
     try 
     { 

      if (ModelState.IsValid) 
      { 
       string result = Services.ValidateLogin(lvm); 

       if (result == "Success") 
       { 
        if (Url.IsLocalUrl(returnUrl) 
         && returnUrl.Length > 1 
         && returnUrl.StartsWith("/") 
         && !returnUrl.StartsWith("//") 
         && !returnUrl.StartsWith("/\\")) 
        { 
         return base.Redirect(returnUrl); 
        } 
        return base.RedirectToAction("Index"); 
       } 
       else 
       { 
        TempData["errors"] = result; 
        ModelState.AddModelError("", result); 
       } 
      } 
      else 
      { 
       errorList = Services.AddErrorMesagesToView(ModelState); 
       TempData["errors"] = errorList; 
      } 
      //return base.RedirectToAction("Admin", new { section = section }); 
      ModelState.Clear(); 
      return View(new LoginViewModel()); 
     } 
     catch (NullReferenceException ne) 
     { 
      if (ne.Source != null) 
       Console.WriteLine("NullReferenceException source: {0}", ne.Source); 
     } 
     catch (HttpException he) 
     { 
      if (he.Source != null) 
       Console.WriteLine("HttpException source: {0}", he.Source); 
     } 
     catch (Exception e) 
     { 
      if (e.Source != null) 
       Console.WriteLine("Exception source: {0}", e.Source); 
     } 
     finally 
     { 
      ModelState.Clear(); 
     } 

     return base.RedirectToAction("Login"); 
    } 
    #endregion 

ValidateLogin

public static string ValidateLogin(LoginViewModel lvm) 
    { 
     /* string ldapServer = WebConfigurationManager.AppSettings["LDAPServer"]; 
     string result = Fakeauthenticate.Fakeauth.LdapAuth(lvm.Login, lvm.Password, ldapServer); 
     */ 
     string result = null; 
     const int INACTIVE = 1; 

     FakeEntities db = new FakeEntities(); 

     // This is the only feasible way to call an SQL user-defined scalar function 
     string sqlQuery = "SELECT [dbo].[Util_GetUserActivationStatus] ({0})"; 
     Object[] parameters = { lvm.Login }; 
     int status = db.Database.SqlQuery<int>(sqlQuery, parameters).FirstOrDefault(); 

     if (status == INACTIVE) 
     { 
      return "The user is currently locked out."; 
     } 

     if (Membership.ValidateUser(lvm.Login, lvm.Password)) 
     { 
      HttpContext.Current.Session[UserInfo.SessionUser] = LoginBusiness.GetUserData(lvm.Login); 
      HttpContext.Current.Session.Timeout = UserInfo.Timeout; 

      result = "Success"; 
     } 
     else 
     { 
      result = LoginBusiness.AuthenticateUser(lvm.Login, lvm.Password); 
      if (result == "Login_Failure") 
      { 
       if (HttpContext.Current.Session[lvm.Login] == null) 
       { 
        HttpContext.Current.Session[lvm.Login] = 1; 
       } 
       else 
       { 
        uint loginFailures = (uint)HttpContext.Current.Session[lvm.Login]; 
        HttpContext.Current.Session[lvm.Login] = ++loginFailures; 

        // If the maximum number of login failures have been reached, then lock the user out. 
        if ((uint)HttpContext.Current.Session[lvm.Login] == UserInfo.MAX_LOGIN_FAILURES) 
        { 
         db.Util_LockUserOut(lvm.Login); 
         return "Your account has been temporarily locked."; 
        } 
       } 
      } 
     } 

     return result; 
    } 
+0

顯示一些代碼也許? – 2014-12-03 15:34:52

+0

什麼部分的代碼顯示? – 2014-12-03 16:04:07

+0

您認爲相關的零件... – 2014-12-03 16:07:22

回答

0

你應該檢查是否有您的形式不止一個@Html.AntiForgeryToken()。如果是,請除去一個。

此外請確保您沒有提交表單兩次。這會搞亂AntiForgeryToken

如果要禁用此檢查,將以下添加到您的Application_Start方法:

AntiForgeryConfig.SuppressIdentityHeuristicChecks = true 
+0

這基本上是唯一的方法嗎? – 2014-12-03 16:04:46

+0

這取決於。你在哪裏使用這個反僞造令牌? – 2014-12-03 16:07:45

+0

當我即將創造一個新紀錄的時候,第一個網頁要求記錄的類型。這是一種形式。之後,它會根據類型轉到新記錄表單。順便說一下,我嘗試了你的建議,但仍然無效。 – 2014-12-03 16:50:15

0

問題就出在你的FakeAuthenticationFilter。我猜你正在加載頁面的控制器動作上使用這個過濾器。 FakeAuthenticationFilter設置HttpContext.Current.User =新的FakePrincipal(標識)。此主體可能具有Name屬性,這是您在錯誤消息中看到的用戶。 .NET使用此委託人在頁面上生成令牌,但是當您提交令牌時,HttpContext將不具有相同的委託人。

一個解決方案可能是將FakeAuthenticationFilter放在您的NewRecordEntry操作上。