I am using jQuery (1.8.2) and the Validation plugin (1.10.0) to validate a form. My problem is that when setting a custom invalidHandler, my form is submitted even when there are errors.
The long version
The form is quite long and has several fields that can be hidden from view (using jQuery.toggle()) to make the form easier to work with. Now, some of these fields are “optionally required”, i.e. I only care about their content if a corresponding checkbox is checked. So I have validators looking similar to this:
emailInvitationTitle: {
required: function() {
return $("#emailInvitation_chk").prop("checked");
}
},
emailInvitationBody: {
required: function() {
return $("#emailInvitation_chk").prop("checked");
}
}
So far, so good. However, if any of these “maybe hidden, maybe required” fields are invalid on submit, I want to show the relevant hidden sections (with class “messageEditor”). So I have an invalidHandler like this:
invalidHandler: function(form, validator) {
// If either title or body is empty, make sure their parent div is visible
if (!(validator.element("#emailInvitationTitle")
&& validator.element("#emailInvitationBody"))) {
$("#emailInvitationTitle").closest(".messageEditor").show();
}
}
The issue is that it seems by defining this invalidHandler, my form is always submitted, regardless whether the validation succeeds or not. I dug around in jquery.validate.js and observed the following (at line 331 and onward):
// http://docs.jquery.com/Plugins/Validation/Validator/form
form: function() {
this.checkForm();
$.extend(this.submitted, this.errorMap);
this.invalid = $.extend({}, this.errorMap);
if (!this.valid()) {
$(this.currentForm).triggerHandler("invalid-form", [this]);
}
this.showErrors();
return this.valid();
},
I won’t pretend I understand even half of it. But when tracing through this, I noticed that this.valid() correctly returns false on the first call, which causes my invalidHandler to trigger. However, return this.valid() yields true immediately after. Somehow the trigger (?) clears the validator’s errorList array, causing the invalid form to be submitted.
Is this a bug with the validate plugin, or jQuery itself (or something else)?
Any suggestions for a fix/workaround?
Answering my own question with the workaround I eventually came to use.
I hacked around this problem by modifying the
formfunction injquery.validate.js:Still doesn’t quite feel like the right way to go about it, but it worked for me.