NerdDinnerのASP.NET MVCで有効なModelState.IsValidとは何ですか?


148

Professional ASP.NET MVC 1.0NerdDinnerの例では、コピーされた次のように新しいディナーを作成する方法があります(無料のNerdDinnerバージョンの89ページ)。

そこで、ModelState.IsValidがtrueかどうかをチェックします。モデルがデータベースに対して有効かどうかを確認しているようです(つまり、無効な形式の日付などのデータ型変換をキャッチしますが、ビジネスルールはキャッチしません)。本当?

フォームを送信するときに日付にエラーがある場合、ModelState.IsValidはfalseになり、エラーが返されますが、AddRuleViolationsが実行されなかったために日付に対してのみ発生します。ModelState.IsValidのチェックを完全に削除すると、無効な日付のマークを含め、すべてのエラー(例外による)が表示されます。次に、ModelState.IsValidのチェックがまったく存在するのはなぜですか?何か不足していますか?

// 
// POST: /Dinners/Create 

[AcceptVerbs(HttpVerbs.Post)] 
public ActionResult Create(Dinner dinner) {
    if (ModelState.IsValid) {
        try {
            dinner.HostedBy = "SomeUser"; 

            dinnerRepository.Add(dinner);
            dinnerRepository.Save();

            return RedirectToAction("Details", new {id = dinner.DinnerID }); 
        } catch {
            ModelState.AddRuleViolations(dinner.GetRuleViolations());
        } 
    } 
    return View(dinner); 
} 

回答:


143

ModelState.IsValidにモデルエラーが追加されているかどうかを通知しますModelState

デフォルトのモデルバインダーは、基本的な型変換の問題(たとえば、「int」であるものに非数を渡すなど)に対していくつかのエラーを追加します。使用している検証システムに基づいて、ModelStateをより完全に入力できます。

サンプルDataAnnotationsモデルバインダーはDataAnnotations、モデルの属性から取得した検証エラーでモデルの状態を満たします。


ブラッドは、ModelStateのないDataAnnotations "IsValid"で装飾されたモデルかどうかを確認する方法はありません。(たとえば、オブジェクトがファイルからロードされるか、コンソールアプリなどで使用されるとします)
runxc1 Bret Ferrier '10

1
いいえ、ModelState.IsValidは、モデルのバインド中に検証(またはデータ変換)エラーがあったかどうかを確認する唯一の方法です。
Brad Wilson、

@Brad、「使用している検証システムに基づいて、ModelStateをより完全に入力できる」と言ったとき、それはどのように行われますか?ViewModelのModelState検証コードを解読する方法はありますか?私はEF4を使用しているので、私の検証の大部分は標準で自動的に行われます。
WEFX 2011

13
使用:var errors = ModelState.Values.SelectMany(v => v.Errors);ブレークポイントを指定して、検証の問題を表示します。
full_prog_full

プロパティ名が変更されている場合、関連テーブルでエラーが発生することがあります。移行が実行されず、結果としてSaveChanges()が実行されます。変更のために失敗し、発生することはありません。
Oracular Man

25

エラッタから: ModelState.AddRuleViolations(dinner.GetRuleViolations());

する必要があります:

ModelState.AddModelErrors(dinner.GetRuleViolations());

参照:http : //www.wrox.com/WileyCDA/WroxTitle/Professional-ASP-NET-MVC-1-0.productCd-0470384611,descCd-ERRATA.html


5
2015年現在、このAddModelErrors方法は存在しません。
フェリペコレア

6
2016年現在、このModelState.AddModelErrors()方法が存在します
ジョン

7
2017年現在、非複数ModelState.AddModelError方式が存在します。
Zachafer 2017年

0

はい、JaredとKelly Orrは正しいです。編集例外のように、次のコードを使用します。

foreach (var issue in dinner.GetRuleViolations())
{
    ModelState.AddModelError(issue.PropertyName, issue.ErrorMessage);
}

の代わりに

ModelState.AddRuleViolations(dinner.GetRuleViolations());

0

明確なタイプを持つすべてのモデルフィールドは、コントローラーに返されるときに検証する必要があります。モデルフィールドのいずれかが定義されたタイプと一致しない場合、ModelState.IsValidはfalseを返します。なぜなら、これらのエラーはModelStateに追加されるからです。

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