i using fluentvalidation in asp.net mvc 4 application. have known rules automatically generating attributes jquery validation library. , script library has known must check example in case of data-rule-required
, data-rule-range
, on.
i know there functions in fluentvalidation, these not include client-side. example: .equal(true)
. have checked @darindimitrov answer here , implemented without problem.
but, don't want create new class inherited fluentvalidationpropertyvalidator
. , must add provider in global.asax:
provider.add(typeof(equalvalidator), (metadata, context, description, validator) => new equaltovalueclientrule(metadata, context, description, validator));
in case equalvalidator
implemented in fluentvalidation. but, if have created validator when
keyword. example, have:
this.rulefor(phone => phone.digits) .length(7) .when(phone => phone.prefixid == 2) .withmessage("numbers in 2nd city must contain 7 characters"); this.rulefor(phone => phone.digits) .length(7) .when(phone => phone.prefixid > 64) .withmessage("mobile number must contain 7 characters"); this.rulefor(phone => phone.digits) .length(5) .when(phone => phone.prefixid != 2) .withmessage("numbers in other cities must contain 5 characters")
of course, can check jquery/javascript without problem. but, approach not good. , in other cases have write code generating custom attributes in client side , add new function adapter. or, use jquery/javascript? or other thing? may can add javascript function name fluentvalidationpropertyvalidator
?
what recommend me?
i have thought lot , find best way create new validator inherits propertyvalidator
, implements iclientvalidatable
interface. result, contain server-side validation , generate unobtrusive attributes wish. must need register new validator in unobtrusive library.
for example, validator rules in question be:
public class mustfittophoneprefix<tmodel, tproperty> : propertyvalidator, iclientvalidatable { private string dependencyelement; public mustfittophoneprefix(expression<func<tmodel, tproperty>> expression) : base("format wrong") { dependencyelement = (expression.body memberexpression).member.name; } // server side validation protected override bool isvalid(propertyvalidatorcontext context) { // instance of class contains property must validated var phone = context.parentcontext.instancetovalidate phonedetail; ... // custom logic ... // valid return true; } // generate jquery unobtrusive attributes public ienumerable<modelclientvalidationrule> getclientvalidationrules(modelmetadata metadata, controllercontext context) { var rule = new modelclientvalidationrule { errormessage = this.errormessagesource.getstring(), // default error message validationtype = "fittoprefix" // name of validatoin used inside unobtrusive library }; rule.validationparameters["prefixelement"] = dependencyelement; // html element includes prefix information yield return rule; }
and can register our client-side validator:
// check if phone number fits phone prefix $.validator.addmethod('fittoprefix', function (value, element, params) { var parent = getparentpropertyname(element); var prefixid = $("#{0}_{1}".format(parent, params.prefixelement)).val(); var digitslength = $(element).val().length; ... // custom logic ... return true; }); // registration - check if phone number fits phone prefix $.validator.unobtrusive.adapters.add('fittoprefix', ['prefixelement'], function (options) { options.rules['fittoprefix'] = options.params; if (options.message != null) { options.messages['fittoprefix'] = options.message; } });
and @ last, can set our validator:
this.rulefor(m => m.digits) .setvalidator(new mustfittophoneprefix<phonedetail, int>(m => m.prefixid));