私はかみそりのビュー内の列挙型を、アクション結果にポストバックされる非表示フィールドとして表しています。
HTML内で提供される文字列値をバインドすると、列挙型の値が自動的に検証されることに気付きました。
/// <summary>
/// Quiz Types Enum
/// </summary>
public enum QuizType
{
/// <summary>
/// Scored Quiz
/// </summary>
Scored = 0,
/// <summary>
/// Personality Type Quiz
/// </summary>
Personality = 1
}
かみそり:
@Html.HiddenFor(x => x.QuizType)
レンダリングされたHTML:
<input data-val="true" data-val-required="Quiz Type is not valid" id="QuizType" name="QuizType" type="hidden" value="Scored">
DOM内の値を誤った値に変更してフォームを送信すると、ModelState.IsValid
はfalse
を返し、ModelStateに次のエラーが追加されます。
"The value 'myincorrectvalue' is not valid for QuizType."
それはすべて面倒ですが、ビューモデルを作成した場合、[Required]
属性などのビューモデルに検証ルールを明示的に設定する必要があると考えました。
また、EnumDataType
と呼ばれるこれ専用の検証属性もあります。
[EnumDataType(typeof(QuizType))]
public QuizType QuizType { get; set; }
質問
バインド時に検証が自動的に行われる場合、EnumDataType
データ検証属性のポイントは何ですか?
わかりましたので、自分の質問に対する答えを見つけました。
表示されたエラーメッセージは、バインドが不可能であった場合の一般的なエラーメッセージです。バインディングがHTMLから列挙に列挙値の存在しない文字列表現をバインドしようとすると、エラーが発生します。
The value 'myincorrectvalue' is not valid for QuizType.
文字列値をビューモデルクラス内のint
にバインドしようとすると、まったく同じエラーメッセージが表示されます。
問題は、文字列表現と同様に、列挙型が任意の整数値である可能性があるということです。 enum内にその番号が存在しない場合でも、enumを任意の番号に設定できます。
/// <summary>
/// Quiz Types Enum
/// </summary>
public enum QuizType
{
/// <summary>
/// Scored Quiz
/// </summary>
Scored = 0,
/// <summary>
/// Personality Type Quiz
/// </summary>
Personality = 1
}
したがって、これは有効であり、1000
が私の列挙内に存在しない場合でも、エラーなしで私の列挙値にバインドされます。
<input data-val="true" id="QuizType" name="QuizType" type="hidden" value="1000">
// Binder will bind this just fine
QuizType = 1000
ここで、EnumDataType
検証属性を使用します。検証モデルをビューモデル内の列挙型に追加すると、次のようになります。
[EnumDataType(typeof(QuizType), ErrorMessage = "Quiz type value doesn't exist within enum")]
public QuizType QuizType { get; set;}
属性を配置すると、有効な列挙値(この例では0または1)のみを割り当てることができます。
したがって、HTMLから送信された不正なSTRING表現はバインド時に自動的に検証されますが、整数値のチェックは検証されません。
これにより、ASP.NET MVC内のENUMSの検証がクリアされることを願っています。