2010-07-02 75 views
7

我试图排除一个必需的属性(密码),所以模型状态不验证该属性,但由于某种原因,即使我试图排除它仍然验证。ModelState.IsValid不排除必需的属性

控制器:

[Authorize, AcceptVerbs(HttpVerbs.Post)] 
    public ActionResult _Edit(int id, [Bind(Exclude = "Password")]FormCollection collection) 
    { 
     var user = Proxy.GetUser(id); 

     TryUpdateModel(user, null, null, new[]{"Password"}); 

     if(!ModelState.IsValid) 
      return PartialView(user); 

     Proxy.UpdateUser(user); 
    } 

查看:

... 
    <tr> 
     <td class="label"> 
      <label class="row_description" for="Password"><%= S._("Password")%></label> 
     </td> 
     <td> 
      <%= Html.Password("Password", null, new { @class = "row_input" })%> 
      <%= Html.ValidationMessage("Password", "*")%> 
     </td> 
    </tr> 

用户(使用dataannotation):使用VS2008

[Required] 
public string Password { get; set; } 

IM,MVC2,火狐

也许我只是累了并且可以'没有看到它。任何帮助表示赞赏

回答

14

我目前遇到类似的问题与MVC3。

尽管[Bind(Exclude = "Password")]在我的操作中,ModelState.IsValid仍然返回false。

我注意到TryUpdateModel(user, null, null, new string[]{"Password"});正在成功更新模型;但仍然返回错误。然后我发现(在stackoverflow的某处,对于没有链接的道歉)TryUpdateModel实际上返回ModelState.IsValid

因此,问题不在于TryUpdateModel,而是在ModelState.IsValid

注意:这也意味着你不需要验证这两次......你可以使用此代码:

if (!TryUpdateModel(user, null, null, new string[]{"Password"})) 
    return PartialView(user); 

因此出现问题,因为,如果ModelState中仍确认已排除特性你的FormCollection

我能够从ModelState去除场呼吁TryUpdateModel之前解决此问题:

ModelState.Remove("Password"); 

注意TryUpdateModel仍然需要属性的列表,从更新按照上面的代码中排除。

+0

我也在为此而苦苦挣扎。执行ModelState.Remove时,显然应该被排除,这似乎很棘手。任何人都可以解释为什么MC3 validaton忽略绑定(排除=)? – automagic 2011-05-13 17:13:35

+0

@James:我同意,TryUpdateModel排除了excludeProperty中列出的属性,但IsValid并不排除在Bind(排除)(或excludeProperty)中列出的属性。 – 2011-05-14 09:14:25

+0

我想我找到了答案:http://bradwilson.typepad.com/blog/2010/01/input-validation-vs-model-validation-in-aspnet-mvc.html – 2011-05-15 06:24:54

0

也许你应该更换

TryUpdateModel(user, null, null, new[]{"Password"}); 

TryUpdateModel(user, null, null, new string[] {"Password"}); 

,因为它可能会造成混乱,其过载TryUpdateModel使用。 只是说...

+0

THX的响应,但我认为我的问题与我使用相同的模型进行创建和编辑有关。我想在创建时需要密码,但在编辑时不需要密码。白色/黑色列表显然与modelstate无效有关:D – larole 2010-07-05 07:52:40

3

我在ASP中使用以下方法成功了。NET MVC 2

TryUpdateModel(user); 
ModelState.Remove("Password"); 
if (!ModelState.IsValid) return PartialView(user); 

要绑定到特定模型的属性保持TryUpdate您可以创建一个包含模板,如下面的一个:

public interface IUserValidateBindable 
{ 
    string UserId { get; set; } 
} 

public class User : IUserValidateBindable 
{ 
    [Required] 
    public string UserId { get; set; } 
    [Required] 
    public string Password { get; set; } 
} 

的更新TryUpodateModel电话如下:

TryUpdateModel<IUserValidateBindable>(user); 
0

我用成功[Bind(Exclude = "Property")]ModelState.Remove("Property")在一起,它的工作就像魅力。

-2

好像我回复得太晚了,但我也面临同样的问题。

检查您的ModelState.Keys集合。键可能是modelObjectName.Password的形式,其余的模型属性也是如此。

所以在这种情况下ModelState.Remove("Password")将无法​​正常工作。你应该尝试ModelState.Remove("modelObjectName.Password")

希望这会解决一个人的问题:)

0

你可以使用一个扩展方法,像这样:

public static bool IsValidExclude(this ModelStateDictionary modelState, params string[] exclude) 
{ 
    foreach (var key in exclude) 
    { 
     if (modelState.ContainsKey(key)) 
      modelState.Remove(key); 
    } 

    return modelState.All(m => m.Value.Errors.Count == 0); 
} 

然后,只需拨打:

var result = ModelState.IsValidExclude("Password");