1

I am using DataAnnotations for validation (including client side)

I have a form with multiple fields. Basic validation for individual fields work fine. Now there are a couple of fields of which atleast one needs to have a value (if there are 3 fields then either 1st or 2nd or 3rd field should have a value).

I have read quite a few posts on this site and couple of blog entries. But I couldn't find a solution that works in the above mentioned scenario. I might have missed something or doing it incorrectly.

Can you help with this please?

Brian Tompsett - 汤莱恩
  • 5,753
  • 72
  • 57
  • 129
byte
  • 1,665
  • 1
  • 19
  • 36

1 Answers1

2

try this

[AttributeUsage(AttributeTargets.Class, AllowMultiple = true, Inherited = true)]
public sealed class EitherOr : ValidationAttribute
{
    private const string _defaultErrorMessage = "'{0}' OR '{1}' OR '{2}' must have a value";
    private readonly object _typeId = new object();

    public EitherOr(string prop1, string prop2, string prop3)
        : base(_defaultErrorMessage)
    {
        Prop1 = prop1;
        Prop2 = prop2;
        Prop3 = prop3;

    }

    public string Prop1 { get; private set; }
    public string Prop2 { get; private set; }
    public string Prop3 { get; private set; }

    public override object TypeId
    {
        get
        {
            return _typeId;
        }
    }

    public override string FormatErrorMessage(string name)
    {
        return String.Format(CultureInfo.CurrentUICulture, ErrorMessageString, Prop1, Prop2,Prop3);
    }

    public override bool IsValid(object value)
    {
        if(string.IsNullOrEmpty(Prop1)&&string.IsNullOrEmpty(Prop2) && string.IsNullOrEmpty(Prop3))
        {
            return false;
        }
        return true;
    }

then mark your class with the EitherOr attribute:

[EitherOr("Bar","Stool","Hood", ErrorMessage = "please supply one of the properties")]
    public class Foo
    {
        public string Bar{ get; set;}
        public string Stool{ get; set;}
        public string Hood{ get; set;}
    }

Please note that i made use of string properties, if your property is of other type, makle sure to change the IsValid(object value) validation

stoic
  • 4,700
  • 13
  • 58
  • 88
  • Thanks Dusty, what javacript validation script should I write in this case? should I still implement DataAnnotationsModelValidator and register it? – byte Sep 22 '10 at 15:39
  • You shouldn't have to write any javascript if you use the default `Html.ValidationSummary`. the error messagfe will be displayed in your validation summary. however, if you want it displayed next to each of the form fields you will have to make use of: ModelState.AddModelError("Bar", "requires a value"); – stoic Sep 22 '10 at 15:55
  • Thanks. Does this validation happen at server side then? I am looking at input validation on client side as well to give better UI and avoid server trip where possible. Server side validation will always be around. – byte Sep 22 '10 at 15:58
  • You can enable clientside validation on mvc2, have a look here http://dotnetaddict.dotnetdevelopersjournal.com/clientvalidation_mvc2.htm, it will validate against your model and it's appropriate data annotations – stoic Sep 22 '10 at 16:39
  • Also take note that if you go the ModelState.AddModelError route you will have to validate server side – stoic Sep 22 '10 at 16:41
  • Dusty, Looks like I have to use reflection. I used your example and in IsValid I see the values of Prop1 = "Bar" and not the value of "Bar" – byte Sep 27 '10 at 08:48