2012-04-14 3 views
0

こんにちは、私はこの答えすでに発見した: グループ名のチェックにかなり特有のものであり、リフレクションを使用していますMVC3 Validation - Require One From GroupMVC3カスタム検証属性「は、少なくとも1つが必要とされる」状況

私の例はおそらく少しシンプルで、もっと単純な方法があるのだろうかと思っていました。

私は以下の持っている:私は検証を追加したい

public class TimeInMinutesViewModel { 

    private const short MINUTES_OR_SECONDS_MULTIPLIER = 60; 

    //public string Label { get; set; } 

    [Range(0,24, ErrorMessage = "Hours should be from 0 to 24")] 
    public short Hours { get; set; } 

    [Range(0,59, ErrorMessage = "Minutes should be from 0 to 59")] 
    public short Minutes { get; set; } 

    /// <summary> 
    /// 
    /// </summary> 
    /// <returns></returns> 
    public short TimeInMinutes() { 
     // total minutes should not be negative 
     if (Hours <= 0 && Minutes <= 0) { 
      return 0; 
     } 
     // multiplier operater treats the right hand side as an int not a short int 
     // so I am casting the result to a short even though both properties are already short int 
     return (short)((Hours * MINUTES_OR_SECONDS_MULTIPLIER) + (Minutes * MINUTES_OR_SECONDS_MULTIPLIER)); 
    } 
} 

は...営業時間&ミニッツプロパティまたはクラス自体のいずれかの属性やアイデアは、ちょうどこれらの特性の確認、少なくとも1にすることです(Hours OR minutes)には、カスタム検証属性を使用した値、サーバーおよびクライアント側の検証があります。

誰でもこの例をお持ちくださいか?

おかげ

答えて

2

あなたは多くの柔軟性を与える、プロパティに属性を適用することにより、グループを定義するためにリンクされている例。その柔軟性のコストはリフレクション・コードです。あまり柔軟性のないアプローチは実装が簡単ですが、より狭く適用可能です。

このようなアプローチのためのIsValidメソッドは次のとおりです。私は他の例の残りの部分を適応させるためにあなたにそれを残しておきます:

protected override ValidationResult IsValid(object value, ValidationContext validationContext) 
{ 
    var viewModel = value as TimeInMinutesViewModel; 
    if (viewModel == null) 
    { 
     //I don't know whether you need to handle this case, maybe just... 
     return null; 
    } 

    if (viewModel.Hours != 0 || viewModel.Minutes != 0) 
     return null; 

    return new ValidationResult(FormatErrorMessage(validationContext.DisplayName)); 
} 
+0

こんにちは、ありがとう、私はちょうどここであなたの例では、この行のために、クラスの属性を使用すると仮定して尋ねることができます: "varViewModel = ValueIn TimeInMinutesViewModel"。各プロパティに属性を適用するだけでは、同じことを達成するのは難しいでしょうか?ありがとう – Pricey

+0

@Priceyはい、この回答は、属性がクラスに適用されていることを前提としています。もちろん、この属性は* one *クラスにのみ適用できます。私が言ったように、柔軟性がなく狭いです。 2つのプロパティの属性を使ってこれを行うには、反射ベースのアプローチ(これは私がやっていることです、率直に)を使うか、 'ValidationContext'から必要な情報を得ることができると仮定して、プロパティに適用する狭義に特化した属性。残念ながら、それが実現可能かどうかを知るためにValidationContextについて十分に知りません。 – phoog

+0

もう一度ありがとう:-) – Pricey

3

はFluentValidation http://fluentvalidation.codeplex.com/をチェックアウトまたは少なくとも一つのプロパティに値を持っている場合は、すべてのViewModelあなたたいのチェックのために、この小さなヘルパーを使用することができ、または変更しますそれはあなたのニーズに応えます。

public class OnePropertySpecifiedAttribute : ValidationAttribute 
{  
    public override bool IsValid(object value) 
    {    
     Type typeInfo = value.GetType(); 
     PropertyInfo[] propertyInfo = typeInfo.GetProperties(); 
     foreach (var property in propertyInfo) 
     { 
      if (null != property.GetValue(value, null)) 
      {      
       return true; 
      } 
     }   
     return false; 
    } 
} 

そして、あなたのViewModelにそれを適用します。

[OnePropertySpecified(ErrorMessage="Either Hours or Minutes must be specified.")] 
public class TimeInMinutesViewModel 
{ 
    //your code 
} 

よろしく。

+0

+1は、クラスのすべてのプロパティを評価する例です。 – Pricey

関連する問題