2010-09-14 102 views
23

在我的ASP.NET MVC應用程序的模型中,我希望只有在選中特定複選框時才按需要驗證文本框。屬性依賴於另一個字段

喜歡的東西

public bool retired {get, set}; 

[RequiredIf("retired",true)] 
public string retirementAge {get, set}; 

我怎麼能這樣做?

謝謝。

+1

'[RequiredIf( 「退役==真」)]'[更多這裏](https://github.com/JaroslawWaliszko/ExpressiveAnnotations) – jwaliszko 2014-08-13 12:51:06

回答

3

我還沒有看到任何開箱即可以做到這一點。

我創建了一個類供你使用,它有點粗糙,絕對不靈活..但我認爲它可以解決你目前的問題。或者至少讓你走上正軌。

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Web; 
using System.ComponentModel.DataAnnotations; 
using System.Globalization; 

namespace System.ComponentModel.DataAnnotations 
{ 
    [AttributeUsage(AttributeTargets.Class, AllowMultiple = true, Inherited = true)] 
    public sealed class RequiredIfAttribute : ValidationAttribute 
    { 
     private const string _defaultErrorMessage = "'{0}' is required"; 
     private readonly object _typeId = new object(); 

     private string _requiredProperty; 
     private string _targetProperty; 
     private bool _targetPropertyCondition; 

     public RequiredIfAttribute(string requiredProperty, string targetProperty, bool targetPropertyCondition) 
      : base(_defaultErrorMessage) 
     { 
      this._requiredProperty   = requiredProperty; 
      this._targetProperty   = targetProperty; 
      this._targetPropertyCondition = targetPropertyCondition; 
     } 

     public override object TypeId 
     { 
      get 
      { 
       return _typeId; 
      } 
     } 

     public override string FormatErrorMessage(string name) 
     { 
      return String.Format(CultureInfo.CurrentUICulture, ErrorMessageString, _requiredProperty, _targetProperty, _targetPropertyCondition); 
     } 

     public override bool IsValid(object value) 
     { 
      bool result    = false; 
      bool propertyRequired = false; // Flag to check if the required property is required. 

      PropertyDescriptorCollection properties = TypeDescriptor.GetProperties(value); 
      string requiredPropertyValue   = (string) properties.Find(_requiredProperty, true).GetValue(value); 
      bool targetPropertyValue    = (bool) properties.Find(_targetProperty, true).GetValue(value); 

      if (targetPropertyValue == _targetPropertyCondition) 
      { 
       propertyRequired = true; 
      } 

      if (propertyRequired) 
      { 
       //check the required property value is not null 
       if (requiredPropertyValue != null) 
       { 
        result = true; 
       } 
      } 
      else 
      { 
       //property is not required 
       result = true; 
      } 

      return result; 
     } 
    } 
} 

以上模型類,你應該只需要添加:

[RequiredIf("retirementAge", "retired", true)] 
public class MyModel 

在你看來

<%= Html.ValidationSummary() %> 

應顯示錯誤消息每當退役屬性爲true和所需財產是空的。

希望這會有所幫助。

14

看看這個:http://blogs.msdn.com/b/simonince/archive/2010/06/04/conditional-validation-in-mvc.aspx

我改裝成的代碼有點適合我的需要。也許你也從這些改變中受益。

public class RequiredIfAttribute : ValidationAttribute 
{ 
    private RequiredAttribute innerAttribute = new RequiredAttribute(); 
    public string DependentUpon { get; set; } 
    public object Value { get; set; } 

    public RequiredIfAttribute(string dependentUpon, object value) 
    { 
     this.DependentUpon = dependentUpon; 
     this.Value = value; 
    } 

    public RequiredIfAttribute(string dependentUpon) 
    { 
     this.DependentUpon = dependentUpon; 
     this.Value = null; 
    } 

    public override bool IsValid(object value) 
    { 
     return innerAttribute.IsValid(value); 
    } 
} 

public class RequiredIfValidator : DataAnnotationsModelValidator<RequiredIfAttribute> 
{ 
    public RequiredIfValidator(ModelMetadata metadata, ControllerContext context, RequiredIfAttribute attribute) 
     : base(metadata, context, attribute) 
    { } 

    public override IEnumerable<ModelClientValidationRule> GetClientValidationRules() 
    { 
     // no client validation - I might well blog about this soon! 
     return base.GetClientValidationRules(); 
    } 

    public override IEnumerable<ModelValidationResult> Validate(object container) 
    { 
     // get a reference to the property this validation depends upon 
     var field = Metadata.ContainerType.GetProperty(Attribute.DependentUpon); 

     if (field != null) 
     { 
      // get the value of the dependent property 
      var value = field.GetValue(container, null); 

      // compare the value against the target value 
      if ((value != null && Attribute.Value == null) || (value != null && value.Equals(Attribute.Value))) 
      { 
       // match => means we should try validating this field 
       if (!Attribute.IsValid(Metadata.Model)) 
        // validation failed - return an error 
        yield return new ModelValidationResult { Message = ErrorMessage }; 
      } 
     } 
    } 
} 

然後使用它:

public DateTime? DeptDateTime { get; set; } 
[RequiredIf("DeptDateTime")] 
public string DeptAirline { get; set; } 
+3

你需要添加 'DataAnnotationsModelValidatorProvider.RegisterAdapter( typeof運算(RequiredIfAttribute) , typeof(RequiredIfValidator));' 到你的global.asax.cs來獲得這個工作。 (如鏈接RickardN提供的 – tkerwood 2012-04-13 03:44:57

+0

' ModelMetadata.FromLambdaExpression(ex,html.ViewData).IsRequired'總是返回'false',即使認爲依賴屬性是真/假 – Hanady 2017-08-21 11:26:44

1

試試我的自定義validation attribute

[ConditionalRequired("retired==true")] 
public string retirementAge {get, set}; 

它支持多個條件。

+0

如果您可以提供完整的項目在你的回購中,包括所有必需的引用,如System.Linq.Dynamic。此外,你似乎使用System.Linq.Dynamic的定製版本,因爲Microsoft有一個'ExpressionParser.Parse()'方法,需要1參數,但是你正在調用一個雙參數版本 – 2013-11-21 10:13:51

+0

謝謝@IanKemp,我會考慮你的建議,並改進知識庫 – karaxuna 2013-11-21 16:54:31

+0

@karaxuna我如何處理ExpressionParser有一個錯誤顯示我? – 2016-11-23 11:20:50

9

只需使用萬無一失的驗證庫,在CodePlex上: https://foolproof.codeplex.com/

支持,除其他外,下面的「requiredif」確認屬性/裝飾品:

[RequiredIf] 
[RequiredIfNot] 
[RequiredIfTrue] 
[RequiredIfFalse] 
[RequiredIfEmpty] 
[RequiredIfNotEmpty] 
[RequiredIfRegExMatch] 
[RequiredIfNotRegExMatch] 

上手容易:

  1. 從提供的鏈接下載軟件包
  2. 添加對包含的.dll文件的引用
  3. 導入包含的JavaScript文件
  4. 確保您的視圖在其HTML中引用包含的JavaScript文件,以實現不顯眼的javascript和jquery驗證。
+0

Fullproof不起作用與EF 4+。 – 2014-02-24 02:23:43

+0

鏈接?它似乎對我來說工作正常 - 我使用EF 6.我下載了源代碼以便萬無一失並編譯它我自己也許這解釋了爲什麼它爲我工作? – 2014-02-24 05:26:03

+0

http://foolproof.codeplex.com/workitem/15609和http://forums.asp.net/t/1752975.aspx – 2014-02-24 07:03:07

1

使用NuGet包管理器我intstalled這樣的:https://github.com/jwaliszko/ExpressiveAnnotations

這是我的模型:

using ExpressiveAnnotations.Attributes; 

public bool HasReferenceToNotIncludedFile { get; set; } 

[RequiredIf("HasReferenceToNotIncludedFile == true", ErrorMessage = "RelevantAuditOpinionNumbers are required.")] 
public string RelevantAuditOpinionNumbers { get; set; } 

我向你保證,這將工作!

相關問題