ASP.NET MVCでモデル状態エラーのコレクションを取得するにはどうすればよいですか?


145

ビューでエラーのコレクションを取得するにはどうすればよいですか?

Html Helper Validation SummaryまたはValidation Messageを使用したくありません。代わりに、エラーを確認し、特定の形式で表示するかどうかを確認します。また、入力コントロールで、特定のプロパティエラーをチェックし、入力にクラスを追加したいと思います。

PS私はSpark View Engineを使用していますが、考え方は同じです。

だから私は何かができると思った...

<if condition="${ModelState.Errors.Count > 0}">
  DispalyErrorSummary()
</if>

....and also...

<input type="text" value="${Model.Name}" 
       class="?{ModelState.Errors["Name"] != string.empty} error" />

....

またはそのようなもの。

更新

私の最終的な解決策は次のようになりました:

<input type="text" value="${ViewData.Model.Name}" 
       class="text error?{!ViewData.ModelState.IsValid && 
                           ViewData.ModelState["Name"].Errors.Count() > 0}" 
       id="Name" name="Name" />

これは、このプロパティにエラーがある場合にのみエラーcssクラスを追加します。


回答:


210
<% ViewData.ModelState.IsValid %>

または

<% ViewData.ModelState.Values.Any(x => x.Errors.Count >= 1) %>

特定のプロパティについて...

<% ViewData.ModelState["Property"].Errors %> // Note this returns a collection

1
キー名ViewData.ModelState [「名前」]合格のためにModelStateプロパティには、エラーを取得するために、辞書型である

「ViewData.ModelState ["Property"]。Errors」に関して、「Property」という名前のキーがない場合、これはnull参照例外をスローしますか?エラーを読み取る前に、まずViewData.ModelState ["Property"]でnullを確認する方が良いでしょうか?
David Hollowell-MSFT

@DaveHはい、存在を最初に完全にチェックする必要があります
Alex Lyman

61

ModelStateからエラーを取得するには、次のLinqを使用します。

var modelStateErrors = this.ModelState.Keys.SelectMany(key => this.ModelState[key].Errors);

2
指定した名前のキーがない場合、これはnull参照例外をスローしますか?エラーを読み取る前に、まずViewData.ModelState [key]でnullを確認する方が良いでしょうか?
David Hollowell-MSFT

5
this.ModelState.Keysを反復処理することから始めるため、KeyNotFoundExceptionの可能性はわかりません。チェックはやり過ぎだと思います。
Chris McKenzie


28

これは、カンマ区切りですべてのエラーを含む1つの文字列を提供します

string validationErrors = string.Join(",",
                    ModelState.Values.Where(E => E.Errors.Count > 0)
                    .SelectMany(E => E.Errors)
                    .Select(E => E.ErrorMessage)
                    .ToArray());

これは、このリスト全体で実際にエラーを出力する唯一のものです!ありがとう
ジェイミー

6

チャドありがとう!キーに関連するすべてのエラーを表示するために、ここに私が思いついたものがあります。何らかの理由で、ベースのHtml.ValidationMessageヘルパーは、キーに関連付けられた最初のエラーのみを表示します。

    <%= Html.ShowAllErrors(mykey) %>

HtmlHelper:

    public static String ShowAllErrors(this HtmlHelper helper, String key) {
        StringBuilder sb = new StringBuilder();
        if (helper.ViewData.ModelState[key] != null) {
            foreach (var e in helper.ViewData.ModelState[key].Errors) {
                TagBuilder div = new TagBuilder("div");
                div.MergeAttribute("class", "field-validation-error");
                div.SetInnerText(e.ErrorMessage);
                sb.Append(div.ToString());
            }
        }
        return sb.ToString();
    }

6

上記のいくつかの答えをまとめると、これは私が最終的に使用したものです:

var validationErrors = ModelState.Values.Where(E => E.Errors.Count > 0)
    .SelectMany(E => E.Errors)
    .Select(E => E.ErrorMessage)
    .ToList();

validationErrorsList<string>各エラーメッセージを含むになってしまいます。そこから、そのリストを使用して必要なことを簡単に実行できます。

ここに画像の説明を入力してください


2

こちらがVBです。

Dim validationErrors As String = String.Join(",", ModelState.Values.Where(Function(E) E.Errors.Count > 0).SelectMany(Function(E) E.Errors).[Select](Function(E) E.ErrorMessage).ToArray())

0

エラーの原因となったプロパティがわからない場合は、リフレクションを使用して、すべてのプロパティをループできます。

public static String ShowAllErrors<T>(this HtmlHelper helper) {
    StringBuilder sb = new StringBuilder();
    Type myType = typeof(T);
    PropertyInfo[] propInfo = myType.GetProperties();

    foreach (PropertyInfo prop in propInfo) {
        foreach (var e in helper.ViewData.ModelState[prop.Name].Errors) {
            TagBuilder div = new TagBuilder("div");
            div.MergeAttribute("class", "field-validation-error");
            div.SetInnerText(e.ErrorMessage);
            sb.Append(div.ToString());
        }
    }
    return sb.ToString();
}

Tは「ViewModel」のタイプです。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.