FluentValidation: Check if one of two fields are empty

匿名 (未验证) 提交于 2019-12-03 02:49:01

问题:

I have this model

public class Person {     public int Id { get; set; }     public string FirstName { get; set; }     public string LastName { get; set; }   } 

I want to create a validation where either FirstName or LastName must be filled in by user. I installed FluentValidation and created a customvalidator class

public class PersonValidator:AbstractValidator<Person> {     public PersonValidator()     {         RuleFor((person=>person.FirstName)//don't know how to check if one is empty     } } 

To check just one field I could just do RuleFor(person => person.FirstName).NotNull();

But how do I check if one of them is null.

Also, is it possible, once validation is created via fluentValidation, use it on the client side to show error?

Edit1

    protected void Application_Start()     {         AreaRegistration.RegisterAllAreas();          FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);         RouteConfig.RegisterRoutes(RouteTable.Routes);         BundleConfig.RegisterBundles(BundleTable.Bundles);         FluentValidationModelValidatorProvider.Configure();     } //creating validation namespace WebApplication1.Models.CustomValidator {     public class PersonValidator:AbstractValidator<Person>     {         public PersonValidator()         {             RuleFor(m => m.FirstName).NotEmpty().When(m => string.IsNullOrEmpty(m.LastName)).WithMessage("*Either First Name or Last Name is required");             RuleFor(m => m.LastName).NotEmpty().When(m => string.IsNullOrEmpty(m.FirstName)).WithMessage("*Either First Name or Last Name is required");         }     }  } //model class [Validator(typeof(PersonValidator))] public class Person {     public Person()     {         InterestList = new List<string>();     }     public int Id { get; set; }     public int ContactId { get; set; }     [RequiredIfEmpty("LastName")]     public string FirstName { get; set; }     [RequiredIfEmpty("FirstName")]     public string LastName { get; set; }     public string EmailAddress { get; set; }     public string Phone { get; set; }     public string Country { get; set; }     public List<string> InterestList { get; set; }  } //view @model WebApplication1.Models.Person  <script src="@Url.Content("~/Scripts/jquery-1.8.2.min.js")"></script> <script src="@Url.Content("~/Scripts/jquery.validate.min.js")"></script> <script src="@Url.Content("~/Scripts/jquery.validate.unobtrusive.min.js")"></script> <script src="@Url.Content("~/Scripts/jquery.unobtrusive-ajax.min.js")" type="text/javascript"></script>  @Html.ValidationSummary(true) @using(Html.BeginForm("AddPerson","Person",FormMethod.Post)) {     <div class="label">First Name</div>     <div class="input-block-level">@Html.TextBoxFor(m=>m.FirstName)@Html.ValidationMessageFor(m=>m.FirstName)</div>     <br/>     <div class="label">Last Name</div>     <div class="input-block-level">@Html.TextBoxFor(m=>m.LastName)@Html.ValidationMessageFor(m=>m.LastName)</div>     <button type="submit" class="btn-primary">Submit</button> } 

回答1:

You can use When/Unless condition:

RuleFor(m => m.FirstName).NotEmpty().When(m => string.IsNullOrEmpty(m.LastName)); RuleFor(m => m.LastName).NotEmpty().When(m => string.IsNullOrEmpty(m.FirstName)); 

or

RuleFor(m => m.FirstName).NotEmpty().Unless(m => !string.IsNullOrEmpty(m.LastName)); RuleFor(m => m.LastName).NotEmpty().Unless(m => !string.IsNullOrEmpty(m.FirstName)); 

As for your second question, FluentValidation works with client-side validation, but not all rules are supported. Here you can find validators, that are supported on the client-side:

  1. NotNull/NotEmpty
  2. Matches (regex)
  3. InclusiveBetween (range)
  4. CreditCard
  5. Email
  6. EqualTo (cross-property equality comparison)
  7. Length

For rules that are not in the list you have to write your own FluentValidationPropertyValidator and implement GetClientValidationRules. You can find a few samples of this on the StackOverflow by doing simple search.



回答2:

Try this

RuleFor(person => person).Must(person => !string.IsNullOrEmpty(person.FirstName) || !string.IsNullOrEmpty(person.LastName)) 


回答3:

I did like this to check charges entered are same to previous one or not. If charges are same as previous one than it'll give an error. This worked for me.

public class CasualMealChargeValidator : AbstractValidator<CasualMealCharge> {     public CasualMealChargeValidator(CasualMealCharge CMC)     {         //RuleFor(x => x.BankName).NotEmpty().When(pm => pm.PaymentMode == "Cheque").WithMessage("Enter Bank.");         RuleFor(x => x).Must(x => x.DN != CMC.DN || x.BF != CMC.BF || x.LN != CMC.LN).WithMessage("Not Saved - Meal charges are same as current charges.").WithName("CMFor");     } } 


回答4:

I don't know that library, but if you just want to check those two properties for null, then you can use this:

RuleFor(person => person.FirstName ?? person.LastName).NotNull();

EDIT This doesn't work, because it throws an InvalidOperationException. Use Zabavsky's solution instead.



回答5:

RuleFor(person => person).Must(person => !string.IsNullOrEmpty(person.FirstName) || !string.IsNullOrEmpty(person.LastName)).WithName("Name")



回答6:

A nice rule-set to check if one of two fields are empty, as well as coming up with meaningful error codes is the following:

public CustomerSourceValidator()     {         CascadeMode = CascadeMode.StopOnFirstFailure;          RuleFor(x => x)             .Null().WithErrorCode("source_id_or_email_required")             .When(source => source.Email == null && source.Id == null);          RuleFor(x => x.Id)             .NotNull().WithErrorCode("source_id_required")             .Matches(CommonValidationRegex.CustomerIdRegexString).WithErrorCode("source_id_invalid")             .When(source => source.Id != null);          RuleFor(x => x.Email)             .NotNull().WithErrorCode("source_email_required")             .Matches(CommonValidationRegex.EmailRegexString).WithErrorCode("source_email_invalid")             .When(source => source.Email != null);     } 


标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!