web-dev-qa-db-ja.com

データ注釈を使用したモデル検証のエラーメッセージ

次のクラスがあるとします。

using System.ComponentModel.DataAnnotations;

public class Book{
   public Contact PrimaryContact{get; set;}
   public Contact SecondaryContact{get; set;}

   [Required(ErrorMessage="Book name is required")]
   public string Name{get; set;}
}
public class Contact{
    [Required(ErrorMessage="Name is required")]
    public string Name{get; set;}
}

Contactを使用してBookDataAnnotationsのインスタンスごとに個別のエラーメッセージを表示できるクリーンな方法はありますか?たとえば、名前がPrimaryContactインスタンスにない場合、エラーは「主要連絡先名が必要です」と表示されます。

私の現在の解決策は、フィールドのエラーがないかモデルの状態をチェックする検証サービスを作成してから、そのエラーを削除し、希望する特定の言語を使用してそれらを追加し直すことです。

22
IaCoder

これが私が知っている唯一の方法ですが、それはきれいにはほど遠いです。これには、サブクラス化とMetaDataクラスを使用してエラーメッセージを「オーバーライド」することが含まれます。

public class Book
{
    public PrimaryContact PrimaryContact { get; set; }
    public SecondaryContact SecondaryContact { get; set; }

    [Required(ErrorMessage = "Book name is required")]
    public string Name { get; set; }
}

public class Contact
{
    [Required(ErrorMessage = "Name is required")]
    public string Name { get; set; }
}

[MetadataType(typeof(PrimaryContactMD))]
public class PrimaryContact : Contact
{
    class PrimaryContactMD
    {
        [Required(ErrorMessage = "Primary Contact Name is required")]
        public string Name { get; set; }
    }
}

[MetadataType(typeof(SecondaryContactMD))]
public class SecondaryContact : Contact
{
    class SecondaryContactMD
    {
        [Required(ErrorMessage = "Secondary Contact Name is required")]
        public string Name { get; set; }
    }
}
39
Jab

私はこれが古いことを理解していますが、この問題に遭遇し、私と同じようにこの質問に出くわした人を助けるために、そのようなプロパティにCustomValidation属性を使用する代わりに、 Required属性。

CustomValidationを使用すると、検証するプロパティに合わせて検証メッセージをより詳細に調整できます。 context.DisplayName簡潔にするために検証されているプロパティの名前を動的に表示しますが、これは必要に応じてさらにカスタマイズできます。

さらにカスタマイズが必要な場合は、コード例で行ったものと同じものを再利用するのではなく、個々のプロパティごとに異なるCustomValidationハンドラーを作成できます。

using System.ComponentModel.DataAnnotations;

public class Book {
    [CustomValidation(typeof(Book), "ValidateContact")]
    public Contact PrimaryContact { get; set; }

    [CustomValidation(typeof(Book), "ValidateContact")]
    public Contact SecondaryContact { get; set; }

    [Required(ErrorMessage = "Book name is required")]
    public string Name { get; set; }

    public static ValidationResult ValidateContact(Contact contact, ValidationContext context) {
        ValidationResult result = null;

        if (contact == null) {
            result = new ValidationResult(string.Format("{0} is required.", context.DisplayName));
        } else if (string.IsNullOrWhiteSpace(contact.Name)) {
            result = new ValidationResult(string.Format("{0} name is required.", context.DisplayName));
        }

        return result;
    }
}

public class Contact {
    [Required(ErrorMessage = "Name is required")]
    public string Name { get; set; }
}
11
synthetik

私もこれに対する答えを探しています。エラーメッセージで「{0}連絡先名が必要です」のような場合にこれまでに見つけたものは、変数の名前を自動的に置き換えます。この機能を明示的に使用する方法があると思います。

0
Chris Stephens