hjg
2024-10-30 8cf23534166c07e711aac2a25911ada317ba01f0
提交 | 用户 | 时间
58d006 1 if ( window.sessionStorage ) {
A 2     sessionStorage.clear();
3 }
4 jQuery.validator.defaults.debug = true;
5 $.mockjaxSettings.log = $.noop;
6
7 $.mockjax({
8     url: "form.php?user=Peter&password=foobar",
9     responseText: 'Hi Peter, welcome back.',
10     responseStatus: 200,
11     responseTime: 1
12 });
13 $.mockjax({
14     url: "users.php",
15     data: { username: /Peter2?|asdf/},
16     responseText: 'false',
17     responseStatus: 200,
18     responseTime: 1
19 });
20 $.mockjax({
21     url: "users2.php",
22     data: { username: "asdf"},
23     responseText: '"asdf is already taken, please try something else"',
24     responseStatus: 200,
25     responseTime: 1
26 });
27 $.mockjax({
28     url: "echo.php",
29     response: function(data) {
30         this.responseText = JSON.stringify(data.data);
31     },
32     responseTime: 100
33 });
34
35 module("validator");
36
37 test("Constructor", function() {
38     var v1 = $("#testForm1").validate();
39     var v2 = $("#testForm1").validate();
40     equal( v1, v2, "Calling validate() multiple times must return the same validator instance" );
41     equal( v1.elements().length, 3, "validator elements" );
42 });
43
44 test("validate() without elements, with non-form elements", 0, function() {
45     $("#doesntexist").validate();
46 });
47
48 test("valid() plugin method", function() {
49     var form = $("#userForm");
50     form.validate();
51     ok ( !form.valid(), "Form isn't valid yet" );
52     var input = $("#username");
53     ok ( !input.valid(), "Input isn't valid either" );
54     input.val("Hello world");
55     ok ( form.valid(), "Form is now valid" );
56     ok ( input.valid(), "Input is valid, too" );
57 });
58
59 test("valid() plugin method", function() {
60     var form = $("#testForm1");
61     form.validate();
62     var inputs = form.find("input");
63     ok( !inputs.valid(), "all invalid" );
64     inputs.not(":first").val("ok");
65     strictEqual( inputs.valid(), false, "just one invalid" );
66     inputs.val("ok");
67     strictEqual( inputs.valid(), true, "all valid" );
68 });
69
70 test("valid() plugin method, special handling for checkable groups", function() {
71     // rule is defined on first checkbox, must apply to others, too
72     var checkable = $("#checkable2");
73     ok( !checkable.valid(), "must be invalid, not checked yet" );
74     checkable.attr("checked", true);
75     ok( checkable.valid(), "valid, is now checked" );
76     checkable.attr("checked", false);
77     ok( !checkable.valid(), "invalid again" );
78     $("#checkable3").attr("checked", true);
79     ok( checkable.valid(), "valid, third box is checked" );
80 });
81
82 test("addMethod", function() {
83     expect( 3 );
84     $.validator.addMethod("hi", function(value) {
85         return value === "hi";
86     }, "hi me too");
87     var method = $.validator.methods.hi,
88         e = $('#text1')[0];
89     ok( !method(e.value, e), "Invalid" );
90     e.value = "hi";
91     ok( method(e.value, e), "Invalid" );
92     ok( jQuery.validator.messages.hi === "hi me too", "Check custom message" );
93 });
94
95 test("addMethod2", function() {
96     expect( 4 );
97     $.validator.addMethod("complicatedPassword", function(value, element, param) {
98         return this.optional(element) || /\D/.test(value) && /\d/.test(value);
99     }, "Your password must contain at least one number and one letter");
100     var v = jQuery("#form").validate({
101         rules: {
102             action: { complicatedPassword: true }
103         }
104     });
105     var rule = $.validator.methods.complicatedPassword,
106         e = $('#text1')[0];
107     e.value = "";
108     strictEqual( v.element(e), true, "Rule is optional, valid" );
109     equal( 0, v.size() );
110     e.value = "ko";
111     ok( !v.element(e), "Invalid, doesn't contain one of the required characters" );
112     e.value = "ko1";
113     ok( v.element(e) );
114 });
115
116 test("form(): simple", function() {
117     expect( 2 );
118     var form = $('#testForm1')[0];
119     var v = $(form).validate();
120     ok( !v.form(), 'Invalid form' );
121     $('#firstname').val("hi");
122     $('#lastname').val("hi");
123     ok( v.form(), 'Valid form' );
124 });
125
126 test("form(): checkboxes: min/required", function() {
127     expect( 3 );
128     var form = $('#testForm6')[0];
129     var v = $(form).validate();
130     ok( !v.form(), 'Invalid form' );
131     $('#form6check1').attr("checked", true);
132     ok( !v.form(), 'Invalid form' );
133     $('#form6check2').attr("checked", true);
134     ok( v.form(), 'Valid form' );
135 });
136
137 test("form(): radio buttons: required", function () {
138     expect( 6 );
139     var form = $('#testForm10')[0];
140
141     var v = $(form).validate({ rules: { testForm10Radio: "required"} });
142     ok(!v.form(), 'Invalid Form');
143     equal($('#testForm10Radio1').attr('class'), 'error');
144     equal($('#testForm10Radio2').attr('class'), 'error');
145
146     $('#testForm10Radio2').attr("checked", true);
147     ok(v.form(), 'Valid form');
148
149     equal($('#testForm10Radio1').attr('class'), 'valid');
150     equal($('#testForm10Radio2').attr('class'), 'valid');
151 });
152
153 test("form(): selects: min/required", function() {
154     expect( 3 );
155     var form = $('#testForm7')[0];
156     var v = $(form).validate();
157     ok( !v.form(), 'Invalid form' );
158     $("#optionxa").attr("selected", true);
159     ok( !v.form(), 'Invalid form' );
160     $("#optionxb").attr("selected", true);
161     ok( v.form(), 'Valid form' );
162 });
163
164 test("form(): with equalTo", function() {
165     expect( 2 );
166     var form = $('#testForm5')[0];
167     var v = $(form).validate();
168     ok( !v.form(), 'Invalid form' );
169     $('#x1, #x2').val("hi");
170     ok( v.form(), 'Valid form' );
171 });
172
173 test("form(): with equalTo and onfocusout=false", function() {
174     expect( 4 );
175     var form = $('#testForm5')[0];
176     var v = $(form).validate({
177         onfocusout: false,
178         showErrors: function() {
179             ok(true, 'showErrors should only be called twice');
180             this.defaultShowErrors();
181         }
182     });
183     $('#x1, #x2').val("hi");
184     ok( v.form(), 'Valid form' );
185     $('#x2').val('not equal').blur();
186     ok( !v.form(), 'Invalid form' );
187 });
188
189
190 test("check(): simple", function() {
191     expect( 3 );
192     var element = $('#firstname')[0];
193     var v = $('#testForm1').validate();
194     ok( v.size() === 0, 'No errors yet' );
195     v.check(element);
196     ok( v.size() === 1, 'error exists' );
197     v.errorList = [];
198     $('#firstname').val("hi");
199     v.check(element);
200     ok( v.size() === 0, 'No more errors' );
201 });
202
203 test("hide(): input", function() {
204     expect( 3 );
205     var errorLabel = $('#errorFirstname');
206     var element = $('#firstname')[0];
207     element.value ="bla";
208     var v = $('#testForm1').validate();
209     errorLabel.show();
210     ok( errorLabel.is(":visible"), "Error label visible before validation" );
211     ok( v.element(element) );
212     ok( errorLabel.is(":hidden"), "Error label not visible after validation" );
213 });
214
215 test("hide(): radio", function() {
216     expect( 2 );
217     var errorLabel = $('#agreeLabel');
218     var element = $('#agb')[0];
219     element.checked = true;
220     var v = $('#testForm2').validate({ errorClass: "xerror" });
221     errorLabel.show();
222     ok( errorLabel.is(":visible"), "Error label visible after validation" );
223     v.element(element);
224     ok( errorLabel.is(":hidden"), "Error label not visible after hiding it" );
225 });
226
227 test("hide(): errorWrapper", function() {
228     expect(2);
229     var errorLabel = $('#errorWrapper');
230     var element = $('#meal')[0];
231     element.selectedIndex = 1;
232
233     errorLabel.show();
234     ok( errorLabel.is(":visible"), "Error label visible after validation" );
235     var v = $('#testForm3').validate({ wrapper: "li", errorLabelContainer: $("#errorContainer") });
236     v.element(element);
237     ok( errorLabel.is(":hidden"), "Error label not visible after hiding it" );
238 });
239
240 test("hide(): container", function() {
241     expect(4);
242     var errorLabel = $('#errorContainer');
243     var element = $('#testForm3')[0];
244     var v = $('#testForm3').validate({ errorWrapper: "li", errorContainer: $("#errorContainer") });
245     v.form();
246     ok( errorLabel.is(":visible"), "Error label visible after validation" );
247     $('#meal')[0].selectedIndex = 1;
248     v.form();
249     ok( errorLabel.is(":hidden"), "Error label not visible after hiding it" );
250     $('#meal')[0].selectedIndex = -1;
251     v.element("#meal");
252     ok( errorLabel.is(":visible"), "Error label visible after validation" );
253     $('#meal')[0].selectedIndex = 1;
254     v.element("#meal");
255     ok( errorLabel.is(":hidden"), "Error label not visible after hiding it" );
256 });
257
258 test("valid()", function() {
259     expect(4);
260     var errorList = [{name:"meal",message:"foo", element:$("#meal")[0]}];
261     var v = $('#testForm3').validate();
262     ok( v.valid(), "No errors, must be valid" );
263     v.errorList = errorList;
264     ok( !v.valid(), "One error, must be invalid" );
265     QUnit.reset();
266     v = $('#testForm3').validate({ submitHandler: function() {
267         ok( false, "Submit handler was called" );
268     }});
269     ok( v.valid(), "No errors, must be valid and returning true, even with the submit handler" );
270     v.errorList = errorList;
271     ok( !v.valid(), "One error, must be invalid, no call to submit handler" );
272 });
273
274 test("submitHandler keeps submitting button", function() {
275     $("#userForm").validate({
276         debug: true,
277         submitHandler: function(form) {
278             // dunno how to test this better; this tests the implementation that uses a hidden input
279             var hidden = $(form).find("input:hidden")[0];
280             deepEqual(hidden.value, button.value);
281             deepEqual(hidden.name, button.name);
282         }
283     });
284     $("#username").val("bla");
285     var button = $("#userForm :submit")[0];
286   var event = $.Event("click");
287   event.preventDefault();
288   $.event.trigger(event, null, button);
289     $("#userForm").submit();
290 });
291
292 test("showErrors()", function() {
293     expect( 4 );
294     var errorLabel = $('#errorFirstname').hide();
295     var element = $('#firstname')[0];
296     var v = $('#testForm1').validate();
297     ok( errorLabel.is(":hidden") );
298     equal( 0, $("label.error[for=lastname]").size() );
299     v.showErrors({"firstname": "required", "lastname": "bla"});
300     equal( true, errorLabel.is(":visible") );
301     equal( true, $("label.error[for=lastname]").is(":visible") );
302 });
303
304 test("showErrors(), allow empty string and null as default message", function() {
305     $("#userForm").validate({
306         rules: {
307             username: {
308                 required: true,
309                 minlength: 3
310             }
311         },
312         messages: {
313             username: {
314                 required: "",
315                 minlength: "too short"
316             }
317         }
318     });
319     ok( !$("#username").valid() );
320     equal( "", $("label.error[for=username]").text() );
321
322     $("#username").val("ab");
323     ok( !$("#username").valid() );
324     equal( "too short", $("label.error[for=username]").text() );
325
326     $("#username").val("abc");
327     ok( $("#username").valid() );
328     ok( $("label.error[for=username]").is(":hidden") );
329 });
330
331 test("showErrors() - external messages", function() {
332     expect( 4 );
333     var methods = $.extend({}, $.validator.methods);
334     var messages = $.extend({}, $.validator.messages);
335     $.validator.addMethod("foo", function() { return false; });
336     $.validator.addMethod("bar", function() { return false; });
337     equal( 0, $("#testForm4 label.error[for=f1]").size() );
338     equal( 0, $("#testForm4 label.error[for=f2]").size() );
339     var form = $('#testForm4')[0];
340     var v = $(form).validate({
341         messages: {
342             f1: "Please!",
343             f2: "Wohoo!"
344         }
345     });
346     v.form();
347     equal( $("#testForm4 label.error[for=f1]").text(), "Please!" );
348     equal( $("#testForm4 label.error[for=f2]").text(), "Wohoo!" );
349
350     $.validator.methods = methods;
351     $.validator.messages = messages;
352 });
353
354 test("showErrors() - custom handler", function() {
355     expect(5);
356     var v = $('#testForm1').validate({
357         showErrors: function(errorMap, errorList) {
358             equal( v, this );
359             equal( v.errorList, errorList );
360             equal( v.errorMap, errorMap );
361             equal( "buga", errorMap.firstname );
362             equal( "buga", errorMap.lastname );
363         }
364     });
365     v.form();
366 });
367
368 test("option: (un)highlight, default", function() {
369     $("#testForm1").validate();
370     var e = $("#firstname");
371     ok( !e.hasClass("error") );
372     ok( !e.hasClass("valid") );
373     e.valid();
374     ok( e.hasClass("error") );
375     ok( !e.hasClass("valid") );
376     e.val("hithere").valid();
377     ok( !e.hasClass("error") );
378     ok( e.hasClass("valid") );
379 });
380
381 test("option: (un)highlight, nothing", function() {
382     expect(3);
383     $("#testForm1").validate({
384         highlight: false,
385         unhighlight: false
386     });
387     var e = $("#firstname");
388     ok( !e.hasClass("error") );
389     e.valid();
390     ok( !e.hasClass("error") );
391     e.valid();
392     ok( !e.hasClass("error") );
393 });
394
395 test("option: (un)highlight, custom", function() {
396     expect(5);
397     $("#testForm1clean").validate({
398         highlight: function(element, errorClass) {
399             equal( "invalid", errorClass );
400             $(element).hide();
401         },
402         unhighlight: function(element, errorClass) {
403             equal( "invalid", errorClass );
404             $(element).show();
405         },
406         errorClass: "invalid",
407         rules: {
408             firstname: "required"
409         }
410     });
411     var e = $("#firstnamec");
412     ok( e.is(":visible") );
413     e.valid();
414     ok( !e.is(":visible") );
415     e.val("hithere").valid();
416     ok( e.is(":visible") );
417 });
418
419 test("option: (un)highlight, custom2", function() {
420     expect(6);
421     $("#testForm1").validate({
422         highlight: function(element, errorClass) {
423             $(element).addClass(errorClass);
424             $(element.form).find("label[for=" + element.id + "]").addClass(errorClass);
425         },
426         unhighlight: function(element, errorClass) {
427             $(element).removeClass(errorClass);
428             $(element.form).find("label[for=" + element.id + "]").removeClass(errorClass);
429         },
430         errorClass: "invalid"
431     });
432     var e = $("#firstname");
433     var l = $("#errorFirstname");
434     ok( !e.is(".invalid") );
435     ok( !l.is(".invalid") );
436     e.valid();
437     ok( e.is(".invalid") );
438     ok( l.is(".invalid") );
439     e.val("hithere").valid();
440     ok( !e.is(".invalid") );
441     ok( !l.is(".invalid") );
442 });
443
444 test("option: focusCleanup default false", function() {
445     var form = $("#userForm");
446     form.validate();
447     form.valid();
448     ok( form.is(":has(label.error[for=username]:visible)"));
449     $("#username").focus();
450     ok( form.is(":has(label.error[for=username]:visible)"));
451 });
452
453 test("option: focusCleanup true", function() {
454     var form = $("#userForm");
455     form.validate({
456         focusCleanup: true
457     });
458     form.valid();
459     ok( form.is(":has(label.error[for=username]:visible)") );
460     $("#username").focus().trigger("focusin");
461     ok( !form.is(":has(label.error[for=username]:visible)") );
462 });
463
464 test("option: focusCleanup with wrapper", function() {
465     var form = $("#userForm");
466     form.validate({
467         focusCleanup: true,
468         wrapper: "span"
469     });
470     form.valid();
471     ok( form.is(":has(span:visible:has(label.error[for=username]))") );
472     $("#username").focus().trigger("focusin");
473     ok( !form.is(":has(span:visible:has(label.error[for=username]))") );
474 });
475
476 test("option: errorClass with multiple classes", function() {
477     var form = $("#userForm");
478     form.validate({
479         focusCleanup: true,
480         wrapper: "span",
481         errorClass: "error error1"
482     });
483     form.valid();
484     ok( form.is(":has(span:visible:has(label.error[for=username]))") );
485     ok( form.is(":has(span:visible:has(label.error1[for=username]))") );
486     $("#username").focus().trigger("focusin");
487     ok( !form.is(":has(span:visible:has(label.error[for=username]))") );
488     ok( !form.is(":has(span:visible:has(label.error1[for=username]))") );
489 });
490
491 test("elements() order", function() {
492     var container = $("#orderContainer");
493     var v = $("#elementsOrder").validate({
494         errorLabelContainer: container,
495         wrap: "li"
496     });
497     deepEqual( v.elements().map(function() {
498         return $(this).attr("id");
499     }).get(), ["order1", "order2", "order3", "order4", "order5", "order6"], "elements must be in document order" );
500     v.form();
501     deepEqual( container.children().map(function() {
502         return $(this).attr("for");
503     }).get(), ["order1", "order2", "order3", "order4", "order5", "order6"], "labels in error container must be in document order" );
504 });
505
506 test("defaultMessage(), empty title is ignored", function() {
507     var v = $("#userForm").validate();
508     equal( "This field is required.", v.defaultMessage($("#username")[0], "required") );
509 });
510
511 test("formatAndAdd", function() {
512     expect(4);
513     var v = $("#form").validate();
514     var fakeElement = { form: $("#form")[0], name: "bar" };
515     v.formatAndAdd(fakeElement, {method: "maxlength", parameters: 2});
516     equal( "Please enter no more than 2 characters.", v.errorList[0].message );
517     equal( "bar", v.errorList[0].element.name );
518
519     v.formatAndAdd(fakeElement, {method: "range", parameters:[2,4]});
520     equal( "Please enter a value between 2 and 4.", v.errorList[1].message );
521
522     v.formatAndAdd(fakeElement, {method: "range", parameters:[0,4]});
523     equal( "Please enter a value between 0 and 4.", v.errorList[2].message );
524 });
525
526 test("formatAndAdd2", function() {
527     expect(3);
528     var v = $("#form").validate();
529     var fakeElement = { form: $("#form")[0], name: "bar" };
530     jQuery.validator.messages.test1 = function(param, element) {
531         equal( v, this );
532         equal( 0, param );
533         return "element " + element.name + " is not valid";
534     };
535     v.formatAndAdd(fakeElement, {method: "test1", parameters: 0});
536     equal( "element bar is not valid", v.errorList[0].message );
537 });
538
539 test("formatAndAdd, auto detect substitution string", function() {
540     var v = $("#testForm1clean").validate({
541         rules: {
542             firstname: {
543                 required: true,
544                 rangelength: [5, 10]
545             }
546         },
547         messages: {
548             firstname: {
549                 rangelength: "at least ${0}, up to {1}"
550             }
551         }
552     });
553     $("#firstnamec").val("abc");
554     v.form();
555     equal( "at least 5, up to 10", v.errorList[0].message );
556 });
557
558 test("error containers, simple", function() {
559     expect(14);
560     var container = $("#simplecontainer");
561     var v = $("#form").validate({
562         errorLabelContainer: container,
563         showErrors: function() {
564             container.find("h3").html( jQuery.validator.format("There are {0} errors in your form.", this.size()) );
565             this.defaultShowErrors();
566         }
567     });
568
569     v.prepareForm();
570     ok( v.valid(), "form is valid" );
571     equal( 0, container.find("label").length, "There should be no error labels" );
572     equal( "", container.find("h3").html() );
573
574     v.prepareForm();
575     v.errorList = [{message:"bar", element: {name:"foo"}}, {message: "necessary", element: {name:"required"}}];
576     ok( !v.valid(), "form is not valid after adding errors manually" );
577     v.showErrors();
578     equal( container.find("label").length, 2, "There should be two error labels" );
579     ok( container.is(":visible"), "Check that the container is visible" );
580     container.find("label").each(function() {
581         ok( $(this).is(":visible"), "Check that each label is visible" );
582     });
583     equal( "There are 2 errors in your form.", container.find("h3").html() );
584
585     v.prepareForm();
586     ok( v.valid(), "form is valid after a reset" );
587     v.showErrors();
588     equal( container.find("label").length, 2, "There should still be two error labels" );
589     ok( container.is(":hidden"), "Check that the container is hidden" );
590     container.find("label").each(function() {
591         ok( $(this).is(":hidden"), "Check that each label is hidden" );
592     });
593 });
594
595 test("error containers, with labelcontainer I", function() {
596     expect(16);
597     var container = $("#container"),
598         labelcontainer = $("#labelcontainer");
599     var v = $("#form").validate({
600         errorContainer: container,
601         errorLabelContainer: labelcontainer,
602         wrapper: "li"
603     });
604
605     ok( v.valid(), "form is valid" );
606     equal( 0, container.find("label").length, "There should be no error labels in the container" );
607     equal( 0, labelcontainer.find("label").length, "There should be no error labels in the labelcontainer" );
608     equal( 0, labelcontainer.find("li").length, "There should be no lis labels in the labelcontainer" );
609
610     v.errorList = [{message:"bar", element: {name:"foo"}}, {name: "required", message: "necessary", element: {name:"required"}}];
611     ok( !v.valid(), "form is not valid after adding errors manually" );
612     v.showErrors();
613     equal( 0, container.find("label").length, "There should be no error label in the container" );
614     equal( 2, labelcontainer.find("label").length, "There should be two error labels in the labelcontainer" );
615     equal( 2, labelcontainer.find("li").length, "There should be two error lis in the labelcontainer" );
616     ok( container.is(":visible"), "Check that the container is visible" );
617     ok( labelcontainer.is(":visible"), "Check that the labelcontainer is visible" );
618     var labels = labelcontainer.find("label").each(function() {
619         ok( $(this).is(":visible"), "Check that each label is visible1" );
620         equal( "li", $(this).parent()[0].tagName.toLowerCase(), "Check that each label is wrapped in an li" );
621         ok( $(this).parent("li").is(":visible"), "Check that each parent li is visible" );
622     });
623 });
624
625 test("errorcontainer, show/hide only on submit", function() {
626     expect(14);
627     var container = $("#container");
628     var labelContainer = $("#labelcontainer");
629     var v = $("#testForm1").bind("invalid-form.validate", function() {
630         ok( true, "invalid-form event triggered called" );
631     }).validate({
632         errorContainer: container,
633         errorLabelContainer: labelContainer,
634         showErrors: function() {
635             container.html( jQuery.validator.format("There are {0} errors in your form.", this.numberOfInvalids()) );
636             ok( true, "showErrors called" );
637             this.defaultShowErrors();
638         }
639     });
640     equal( "", container.html(), "must be empty" );
641     equal( "", labelContainer.html(), "must be empty" );
642     // validate whole form, both showErrors and invalidHandler must be called once
643     // preferably invalidHandler first, showErrors second
644     ok( !v.form(), "invalid form" );
645     equal( 2, labelContainer.find("label").length );
646     equal( "There are 2 errors in your form.", container.html() );
647     ok( labelContainer.is(":visible"), "must be visible" );
648     ok( container.is(":visible"), "must be visible" );
649
650     $("#firstname").val("hix").keyup();
651     $("#testForm1").triggerHandler("keyup", [jQuery.event.fix({ type: "keyup", target: $("#firstname")[0] })]);
652     equal( 1, labelContainer.find("label:visible").length );
653     equal( "There are 1 errors in your form.", container.html() );
654
655     $("#lastname").val("abc");
656     ok( v.form(), "Form now valid, trigger showErrors but not invalid-form" );
657 });
658
659 test("option invalidHandler", function() {
660     expect(1);
661     var v = $("#testForm1clean").validate({
662         invalidHandler: function() {
663             ok( true, "invalid-form event triggered called" );
664             start();
665         }
666     });
667     $("#usernamec").val("asdf").rules("add", { required: true, minlength: 5 });
668     stop();
669     $("#testForm1clean").submit();
670 });
671
672 test("findByName()", function() {
673     deepEqual( new $.validator({}, document.getElementById("form")).findByName(document.getElementById("radio1").name).get(), $("#form").find("[name=radio1]").get() );
674 });
675
676 test("focusInvalid()", function() {
677     // TODO when using custom focusin, this is triggered just once
678     // TODO when using 1.4 focusin, triggered twice; fix once not testing against 1.3 anymore
679     // expect(1);
680     var inputs = $("#testForm1 input").focus(function() {
681         equal( inputs[0], this, "focused first element" );
682     });
683     var v = $("#testForm1").validate();
684     v.form();
685     v.focusInvalid();
686 });
687
688 test("findLastActive()", function() {
689     expect(3);
690     var v = $("#testForm1").validate();
691     ok( !v.findLastActive() );
692     v.form();
693     v.focusInvalid();
694     equal( v.findLastActive(), $("#firstname")[0] );
695     var lastActive = $("#lastname").trigger("focus").trigger("focusin")[0];
696     equal( v.lastActive, lastActive );
697 });
698
699 test("validating multiple checkboxes with 'required'", function() {
700     expect(3);
701     var checkboxes = $("#form input[name=check3]").prop("checked", false);
702     equal(checkboxes.size(), 5);
703     var v = $("#form").validate({
704         rules: {
705             check3: "required"
706         }
707     });
708     v.form();
709     equal(v.size(), 1);
710     checkboxes.filter(":last").prop("checked", true);
711     v.form();
712     equal(v.size(), 0);
713 });
714
715 test("dynamic form", function() {
716     var counter = 0;
717     function add() {
718         $("<input data-rule-required='true' name='list" + counter++ + "' />").appendTo("#testForm2");
719     }
720     function errors(expected, message) {
721         equal(expected, v.size(), message );
722     }
723     var v = $("#testForm2").validate();
724     v.form();
725     errors(1);
726     add();
727     v.form();
728     errors(2);
729     add();
730     v.form();
731     errors(3);
732     $("#testForm2 input[name=list1]").remove();
733     v.form();
734     errors(2);
735     add();
736     v.form();
737     errors(3);
738     $("#testForm2 input[name^=list]").remove();
739     v.form();
740     errors(1);
741     $("#agb").attr("disabled", true);
742     v.form();
743     errors(0);
744     $("#agb").attr("disabled", false);
745     v.form();
746     errors(1);
747 });
748
749 test("idOrName()", function() {
750     expect(4);
751     var v = $("#testForm1").validate();
752     equal( "form8input", v.idOrName( $("#form8input")[0] ) );
753     equal( "check", v.idOrName( $("#form6check1")[0] ) );
754     equal( "agree", v.idOrName( $("#agb")[0] ) );
755     equal( "button", v.idOrName( $("#form :button")[0] ) );
756 });
757
758 test("resetForm()", function() {
759     function errors(expected, message) {
760         equal(expected, v.size(), message );
761     }
762     var v = $("#testForm1").validate();
763     v.form();
764     errors(2);
765     $("#firstname").val("hiy");
766     v.resetForm();
767     errors(0);
768     equal("", $("#firstname").val(), "form plugin is included, therefor resetForm must also reset inputs, not only errors");
769 });
770
771 test("message from title", function() {
772     var v = $("#withTitle").validate();
773     v.checkForm();
774     equal(v.errorList[0].message, "fromtitle", "title not used");
775 });
776
777 test("ignoreTitle", function() {
778     var v = $("#withTitle").validate({ignoreTitle:true});
779     v.checkForm();
780     equal(v.errorList[0].message, $.validator.messages["required"], "title used when it should have been ignored");
781 });
782
783 test("ajaxSubmit", function() {
784     expect(1);
785     stop();
786     $("#user").val("Peter");
787     $("#password").val("foobar");
788     jQuery("#signupForm").validate({
789         submitHandler: function(form) {
790             jQuery(form).ajaxSubmit({
791                 success: function(response) {
792                     equal("Hi Peter, welcome back.", response);
793                     start();
794                 }
795             });
796         }
797     });
798     jQuery("#signupForm").triggerHandler("submit");
799 });
800
801 test("validating groups settings parameter", function() {
802     var form = $("<form>");
803     var validate = form.validate({
804         groups: {
805             arrayGroup: ["input one", "input-two", "input three"],
806             stringGroup: "input-four input-five input-six"
807         }
808     });
809     equal(validate.groups["input one"], "arrayGroup");
810     equal(validate.groups["input-two"], "arrayGroup");
811     equal(validate.groups["input three"], "arrayGroup");
812     equal(validate.groups["input-four"], "stringGroup");
813     equal(validate.groups["input-five"], "stringGroup");
814     equal(validate.groups["input-six"], "stringGroup");
815 });
816
817 test('bypassing validation on form submission',function () {
818     var form = $("#bypassValidation");
819     var normalSubmission = $("form#bypassValidation :input[id=normalSubmit]");
820     var bypassSubmitWithCancel = $("form#bypassValidation :input[id=bypassSubmitWithCancel]");
821     var bypassSubmitWithNoValidate1 = $("form#bypassValidation :input[id=bypassSubmitWithNoValidate1]");
822     var bypassSubmitWithNoValidate2 = $("form#bypassValidation :input[id=bypassSubmitWithNoValidate2]");
823
824     var $v = form.validate({
825         debug : true
826     });
827
828     bypassSubmitWithCancel.click();
829     equal($v.numberOfInvalids(), 0, "Validation was bypassed using CSS 'cancel' class.");
830     $v.resetForm();
831
832     bypassSubmitWithNoValidate1.click();
833     equal($v.numberOfInvalids(), 0, "Validation was bypassed using blank 'formnovalidate' attribute.");
834     $v.resetForm();
835
836     bypassSubmitWithNoValidate2.click();
837     equal($v.numberOfInvalids(), 0, "Validation was bypassed using 'formnovalidate=\"formnovalidate\"' attribute.");
838     $v.resetForm();
839
840     normalSubmission.click();
841     equal($v.numberOfInvalids(), 1, "Validation failed correctly");
842 });
843
844
845 module("misc");
846
847 test("success option", function() {
848     expect(7);
849     equal( "", $("#firstname").val() );
850     var v = $("#testForm1").validate({
851         success: "valid"
852     });
853     var label = $("#testForm1 label");
854     ok( label.is(".error") );
855     ok( !label.is(".valid") );
856     v.form();
857     ok( label.is(".error") );
858     ok( !label.is(".valid") );
859     $("#firstname").val("hi");
860     v.form();
861     ok( label.is(".error") );
862     ok( label.is(".valid") );
863 });
864
865 test("success option2", function() {
866     expect(5);
867     equal( "", $("#firstname").val() );
868     var v = $("#testForm1").validate({
869         success: "valid"
870     });
871     var label = $("#testForm1 label");
872     ok( label.is(".error") );
873     ok( !label.is(".valid") );
874     $("#firstname").val("hi");
875     v.form();
876     ok( label.is(".error") );
877     ok( label.is(".valid") );
878 });
879
880 test("success option3", function() {
881     expect(5);
882     equal( "", $("#firstname").val() );
883     $("#errorFirstname").remove();
884     var v = $("#testForm1").validate({
885         success: "valid"
886     });
887     equal( 0, $("#testForm1 label").size() );
888     $("#firstname").val("hi");
889     v.form();
890     var labels = $("#testForm1 label");
891     equal( 3, labels.size() );
892     ok( labels.eq(0).is(".valid") );
893     ok( !labels.eq(1).is(".valid") );
894 });
895
896 test("successlist", function() {
897     var v = $("#form").validate({ success: "xyz" });
898     v.form();
899     equal(0, v.successList.length);
900 });
901
902 test("success isn't called for optional elements", function() {
903     expect(4);
904     equal( "", $("#firstname").removeAttr("data-rule-required").removeAttr("data-rule-minlength").val() );
905     $("#something").remove();
906     $("#lastname").remove();
907     $("#errorFirstname").remove();
908     var v = $("#testForm1").validate({
909         success: function() {
910             ok( false, "don't call success for optional elements!" );
911         },
912         rules: {
913             firstname: "email"
914         }
915     });
916     equal( 0, $("#testForm1 label").size() );
917     v.form();
918     equal( 0, $("#testForm1 label").size() );
919     $("#firstname").valid();
920     equal( 0, $("#testForm1 label").size() );
921 });
922
923 test("success callback with element", function() {
924     expect(1);
925     var v = $("#userForm").validate({
926         success: function( label, element ) {
927             equal( element, $('#username').get(0) );
928         }
929     });
930     $("#username").val("hi");
931     v.form();
932 });
933
934 test("all rules are evaluated even if one returns a dependency-mistmatch", function() {
935     expect(6);
936     equal( "", $("#firstname").removeAttr("data-rule-required").removeAttr("data-rule-minlength").val() );
937     $("#lastname").remove();
938     $("#errorFirstname").remove();
939     $.validator.addMethod("custom1", function() {
940         ok( true, "custom method must be evaluated" );
941         return true;
942     }, "");
943     var v = $("#testForm1").validate({
944         rules: {
945             firstname: {email:true, custom1: true}
946         }
947     });
948     equal( 0, $("#testForm1 label").size() );
949     v.form();
950     equal( 0, $("#testForm1 label").size() );
951     $("#firstname").valid();
952     equal( 0, $("#testForm1 label").size() );
953
954     delete $.validator.methods.custom1;
955     delete $.validator.messages.custom1;
956 });
957
958 test("messages", function() {
959     var m = jQuery.validator.messages;
960     equal( "Please enter no more than 0 characters.", m.maxlength(0) );
961     equal( "Please enter at least 1 characters.", m.minlength(1) );
962     equal( "Please enter a value between 1 and 2 characters long.", m.rangelength([1, 2]) );
963     equal( "Please enter a value less than or equal to 1.", m.max(1) );
964     equal( "Please enter a value greater than or equal to 0.", m.min(0) );
965     equal( "Please enter a value between 1 and 2.", m.range([1, 2]) );
966 });
967
968 test("jQuery.validator.format", function() {
969     equal( "Please enter a value between 0 and 1.", jQuery.validator.format("Please enter a value between {0} and {1}.", 0, 1) );
970     equal( "0 is too fast! Enter a value smaller then 0 and at least -15", jQuery.validator.format("{0} is too fast! Enter a value smaller then {0} and at least {1}", 0, -15) );
971     var template = jQuery.validator.format("{0} is too fast! Enter a value smaller then {0} and at least {1}");
972     equal( "0 is too fast! Enter a value smaller then 0 and at least -15", template(0, -15) );
973     template = jQuery.validator.format("Please enter a value between {0} and {1}.");
974     equal( "Please enter a value between 1 and 2.", template([1, 2]) );
975     equal( $.validator.format("{0}", "$0"), "$0" );
976 });
977
978 test("option: ignore", function() {
979     var v = $("#testForm1").validate({
980         ignore: "[name=lastname]"
981     });
982     v.form();
983     equal( 1, v.size() );
984 });
985
986 test("option: subformRequired", function() {
987     jQuery.validator.addMethod("billingRequired", function(value, element) {
988         if ($("#bill_to_co").is(":checked")) {
989             return $(element).parents("#subform").length;
990         }
991         return !this.optional(element);
992     }, "");
993     var v = $("#subformRequired").validate();
994     v.form();
995     equal( 1, v.size() );
996     $("#bill_to_co").attr("checked", false);
997     v.form();
998     equal( 2, v.size() );
999
1000     delete $.validator.methods.billingRequired;
1001     delete $.validator.messages.billingRequired;
1002 });
1003
1004 module("expressions");
1005
1006 test("expression: :blank", function() {
1007     var e = $("#lastname")[0];
1008     equal( 1, $(e).filter(":blank").length );
1009     e.value = " ";
1010     equal( 1, $(e).filter(":blank").length );
1011     e.value = "   ";
1012     equal( 1, $(e).filter(":blank").length );
1013     e.value= " a ";
1014     equal( 0, $(e).filter(":blank").length );
1015 });
1016
1017 test("expression: :filled", function() {
1018     var e = $("#lastname")[0];
1019     equal( 0, $(e).filter(":filled").length );
1020     e.value = " ";
1021     equal( 0, $(e).filter(":filled").length );
1022     e.value = "   ";
1023     equal( 0, $(e).filter(":filled").length );
1024     e.value= " a ";
1025     equal( 1, $(e).filter(":filled").length );
1026 });
1027
1028 test("expression: :unchecked", function() {
1029     var e = $("#check2")[0];
1030     equal( 1, $(e).filter(":unchecked").length );
1031     e.checked = true;
1032     equal( 0, $(e).filter(":unchecked").length );
1033     e.checked = false;
1034     equal( 1, $(e).filter(":unchecked").length );
1035 });
1036
1037 module("events");
1038
1039 test("validate on blur", function() {
1040     function errors(expected, message) {
1041         equal(v.size(), expected, message );
1042     }
1043     function labels(expected) {
1044         equal(v.errors().filter(":visible").size(), expected);
1045     }
1046     function blur(target) {
1047         target.trigger("blur").trigger("focusout");
1048     }
1049     $("#errorFirstname").hide();
1050     var e = $("#firstname");
1051     var v = $("#testForm1").validate();
1052     $("#something").val("");
1053     blur(e);
1054     errors(0, "No value yet, required is skipped on blur");
1055     labels(0);
1056     e.val("h");
1057     blur(e);
1058     errors(1, "Required was ignored, but as something was entered, check other rules, minlength isn't met");
1059     labels(1);
1060     e.val("hh");
1061     blur(e);
1062     errors(0, "All is fine");
1063     labels(0);
1064     e.val("");
1065     v.form();
1066     errors(3, "Submit checks all rules, both fields invalid");
1067     labels(3);
1068     blur(e);
1069     errors(1, "Blurring the field results in emptying the error list first, then checking the invalid field: its still invalid, don't remove the error" );
1070     labels(3);
1071     e.val("h");
1072     blur(e);
1073     errors(1, "Entering a single character fulfills required, but not minlength: 2, still invalid");
1074     labels(3);
1075     e.val("hh");
1076     blur(e);
1077     errors(0, "Both required and minlength are met, no errors left");
1078     labels(2);
1079 });
1080
1081 test("validate on keyup", function() {
1082     function errors(expected, message) {
1083         equal(expected, v.size(), message );
1084     }
1085     function keyup(target) {
1086         target.trigger("keyup");
1087     }
1088     var e = $("#firstname");
1089     var v = $("#testForm1").validate();
1090     keyup(e);
1091     errors(0, "No value, no errors");
1092     e.val("a");
1093     keyup(e);
1094     errors(0, "Value, but not invalid");
1095     e.val("");
1096     v.form();
1097     errors(2, "Both invalid");
1098     keyup(e);
1099     errors(1, "Only one field validated, still invalid");
1100     e.val("hh");
1101     keyup(e);
1102     errors(0, "Not invalid anymore");
1103     e.val("h");
1104     keyup(e);
1105     errors(1, "Field didn't loose focus, so validate again, invalid");
1106     e.val("hh");
1107     keyup(e);
1108     errors(0, "Valid");
1109 });
1110
1111 test("validate on not keyup, only blur", function() {
1112     function errors(expected, message) {
1113         equal(expected, v.size(), message );
1114     }
1115     var e = $("#firstname");
1116     var v = $("#testForm1").validate({
1117         onkeyup: false
1118     });
1119     errors(0);
1120     e.val("a");
1121     e.trigger("keyup");
1122     e.keyup();
1123     errors(0);
1124     e.trigger("blur").trigger("focusout");
1125     errors(1);
1126 });
1127
1128 test("validate on keyup and blur", function() {
1129     function errors(expected, message) {
1130         equal(expected, v.size(), message );
1131     }
1132     var e = $("#firstname");
1133     var v = $("#testForm1").validate();
1134     errors(0);
1135     e.val("a");
1136     e.trigger("keyup");
1137     errors(0);
1138     e.trigger("blur").trigger("focusout");
1139     errors(1);
1140 });
1141
1142 test("validate email on keyup and blur", function() {
1143     function errors(expected, message) {
1144         equal(expected, v.size(), message );
1145     }
1146     var e = $("#firstname");
1147     var v = $("#testForm1").validate();
1148     v.form();
1149     errors(2);
1150     e.val("a");
1151     e.trigger("keyup");
1152     errors(1);
1153     e.val("aa");
1154     e.trigger("keyup");
1155     errors(0);
1156 });
1157
1158 test("validate checkbox on click", function() {
1159     function errors(expected, message) {
1160         equal(expected, v.size(), message );
1161     }
1162     function trigger(element) {
1163         element.click();
1164         // triggered click event screws up checked-state in 1.4
1165         element.valid();
1166     }
1167     var e = $("#check2");
1168     var v = $("#form").validate({
1169         rules: {
1170             check2: "required"
1171         }
1172     });
1173     trigger(e);
1174     errors(0);
1175     trigger(e);
1176     equal( false, v.form() );
1177     errors(1);
1178     trigger(e);
1179     errors(0);
1180     trigger(e);
1181     errors(1);
1182 });
1183
1184 test("validate multiple checkbox on click", function() {
1185     function errors(expected, message) {
1186         equal(expected, v.size(), message );
1187     }
1188     function trigger(element) {
1189         element.click();
1190         // triggered click event screws up checked-state in 1.4
1191         element.valid();
1192     }
1193     var e1 = $("#check1").attr("checked", false);
1194     var e2 = $("#check1b");
1195     var v = $("#form").validate({
1196         rules: {
1197             check: {
1198                 required: true,
1199                 minlength: 2
1200             }
1201         }
1202     });
1203     trigger(e1);
1204     trigger(e2);
1205     errors(0);
1206     trigger(e2);
1207     equal( false, v.form() );
1208     errors(1);
1209     trigger(e2);
1210     errors(0);
1211     trigger(e2);
1212     errors(1);
1213 });
1214
1215 test("correct checkbox receives the error", function(){
1216     function trigger(element) {
1217         element.click();
1218         // triggered click event screws up checked-state in 1.4
1219         element.valid();
1220     }
1221     var e1 = $("#check1").attr("checked", false);
1222     var e2 = $("#check1b").attr("checked", false);
1223     var v = $("#form").find('[type=checkbox]').attr('checked', false).end().validate({
1224         rules:{
1225             check: {
1226                     required: true,
1227                     minlength: 2
1228             }
1229         }
1230     });
1231     equal(false, v.form());
1232     trigger(e1);
1233     equal(false, v.form());
1234     ok(v.errorList[0].element.id === v.currentElements[0].id, "the proper checkbox has the error AND is present in currentElements");
1235 });
1236
1237 test("validate radio on click", function() {
1238     function errors(expected, message) {
1239         equal(expected, v.size(), message );
1240     }
1241     function trigger(element) {
1242         element.click();
1243         // triggered click event screws up checked-state in 1.4
1244         element.valid();
1245     }
1246     var e1 = $("#radio1");
1247     var e2 = $("#radio1a");
1248     var v = $("#form").validate({
1249         rules: {
1250             radio1: "required"
1251         }
1252     });
1253     errors(0);
1254     equal( false, v.form() );
1255     errors(1);
1256     trigger(e2);
1257     errors(0);
1258     trigger(e1);
1259     errors(0);
1260 });
1261
1262 test("validate input with no type attribute, defaulting to text", function() {
1263     function errors(expected, message) {
1264         equal(expected, v.size(), message );
1265     }
1266     var v = $("#testForm12").validate();
1267     var e = $("#testForm12text");
1268     errors(0);
1269     e.valid();
1270     errors(1);
1271     e.val('test');
1272     e.trigger('keyup');
1273     errors(0);
1274 });
1275
1276 test("ignore hidden elements", function(){
1277     var form = $('#userForm');
1278     var validate = form.validate({
1279         rules:{
1280             "username": "required"
1281         }
1282     });
1283     form.get(0).reset();
1284     ok(! validate.form(), "form should be initially invalid");
1285     $('#userForm [name=username]').hide();
1286     ok(validate.form(), "hidden elements should be ignored by default");
1287 });
1288
1289 test("ignore hidden elements at start", function(){
1290     var form = $('#userForm');
1291     var validate = form.validate({
1292         rules:{
1293             "username": "required"
1294         }
1295     });
1296     form.get(0).reset();
1297     $('#userForm [name=username]').hide();
1298     ok(validate.form(), "hidden elements should be ignored by default");
1299     $('#userForm [name=username]').show();
1300     ok(! validate.form(), "form should be invalid when required element is visible");
1301 });
1302
1303 test("Specify error messages through data attributes", function() {
1304     var form = $('#dataMessages');
1305     var name = $('#dataMessagesName');
1306     var v = form.validate();
1307
1308     form.get(0).reset();
1309     name.valid();
1310
1311     var label = $('#dataMessages label');
1312     equal( label.text(), "You must enter a value here", "Correct error label" );
1313 });
1314
1315 test("Updates pre-existing label if has error class", function() {
1316     var form = $('#updateLabel'),
1317         input = $('#updateLabelInput'),
1318         label = $('#targetLabel'),
1319         v = form.validate(),
1320         labelsBefore = form.find('label').length,
1321         labelsAfter;
1322
1323     input.val('');
1324     input.valid();
1325     labelsAfter = form.find('label').length;
1326
1327     // label was updated
1328     equal( label.text(), input.attr('data-msg-required') );
1329     // new label wasn't created
1330     equal( labelsBefore, labelsAfter );
1331 });
1332
1333 test("Min date set by attribute", function() {
1334     var form = $('#rangesMinDateInvalid');
1335     var name = $('#minDateInvalid');
1336     var v = form.validate();
1337
1338     form.get(0).reset();
1339     name.valid();
1340
1341     var label = $('#rangesMinDateInvalid label');
1342     equal( label.text(), "Please enter a value greater than or equal to 2012-12-21.", "Correct error label" );
1343 });
1344
1345 test("Max date set by attribute", function() {
1346     var form = $('#ranges');
1347     var name = $('#maxDateInvalid');
1348     var v = form.validate();
1349
1350     form.get(0).reset();
1351     name.valid();
1352
1353     var label = $('#ranges label');
1354     equal( label.text(), "Please enter a value less than or equal to 2012-12-21.", "Correct error label" );
1355 });
1356
1357 test("Min and Max date set by attributes greater", function() {
1358     var form = $('#ranges');
1359     var name = $('#rangeDateInvalidGreater');
1360     var v = form.validate();
1361
1362     form.get(0).reset();
1363     name.valid();
1364
1365     var label = $('#ranges label');
1366     equal( label.text(), "Please enter a value less than or equal to 2013-01-21.", "Correct error label" );
1367 });
1368
1369 test("Min and Max date set by attributes less", function() {
1370     var form = $('#ranges');
1371     var name = $('#rangeDateInvalidLess');
1372     var v = form.validate();
1373
1374     form.get(0).reset();
1375     name.valid();
1376
1377     var label = $('#ranges label');
1378     equal( label.text(), "Please enter a value greater than or equal to 2012-11-21.", "Correct error label" );
1379 });
1380
1381 test("Min date set by attribute valid", function() {
1382     var form = $('#rangeMinDateValid');
1383     var name = $('#minDateValid');
1384     var v = form.validate();
1385
1386     form.get(0).reset();
1387     name.valid();
1388
1389     var label = $('#rangeMinDateValid label');
1390     equal( label.text(), "", "Correct error label" );
1391 });
1392
1393 test("Max date set by attribute valid", function() {
1394     var form = $('#ranges');
1395     var name = $('#maxDateValid');
1396     var v = form.validate();
1397
1398     form.get(0).reset();
1399     name.valid();
1400
1401     var label = $('#ranges label');
1402     equal( label.text(), "", "Correct error label" );
1403 });
1404
1405 test("Min and Max date set by attributes valid", function() {
1406     var form = $('#ranges');
1407     var name = $('#rangeDateValid');
1408     var v = form.validate();
1409
1410     form.get(0).reset();
1411     name.valid();
1412
1413     var label = $('#ranges label');
1414     equal( label.text(), "", "Correct error label" );
1415 });
1416
1417 test("Min and Max strings set by attributes greater", function() {
1418     var form = $('#ranges');
1419     var name = $('#rangeTextInvalidGreater');
1420     var v = form.validate();
1421
1422     form.get(0).reset();
1423     name.valid();
1424
1425     var label = $('#ranges label');
1426     equal( label.text(), "Please enter a value less than or equal to 200.", "Correct error label" );
1427 });
1428
1429 test("Min and Max strings set by attributes less", function() {
1430     var form = $('#ranges');
1431     var name = $('#rangeTextInvalidLess');
1432     var v = form.validate();
1433
1434     form.get(0).reset();
1435     name.valid();
1436
1437     var label = $('#ranges label');
1438     equal( label.text(), "Please enter a value greater than or equal to 200.", "Correct error label" );
1439 });
1440
1441 test("Min and Max strings set by attributes valid", function() {
1442     var form = $('#ranges');
1443     var name = $('#rangeTextValid');
1444     var v = form.validate();
1445
1446     form.get(0).reset();
1447     name.valid();
1448
1449     var label = $('#ranges label');
1450     equal( label.text(), "", "Correct error label" );
1451 });
1452
1453
1454
1455 test("Min and Max type absent set by attributes greater", function() {
1456     var form = $('#ranges');
1457     var name = $('#rangeAbsentInvalidGreater');
1458     var v = form.validate();
1459
1460     form.get(0).reset();
1461     name.valid();
1462
1463     var label = $('#ranges label');
1464     equal( label.text(), "Please enter a value less than or equal to 200.", "Correct error label" );
1465 });
1466
1467 test("Min and Max type absent set by attributes less", function() {
1468     var form = $('#ranges');
1469     var name = $('#rangeAbsentInvalidLess');
1470     var v = form.validate();
1471
1472     form.get(0).reset();
1473     name.valid();
1474
1475     var label = $('#ranges label');
1476     equal( label.text(), "Please enter a value greater than or equal to 200.", "Correct error label" );
1477 });
1478
1479 test("Min and Max type absent set by attributes valid", function() {
1480     var form = $('#ranges');
1481     var name = $('#rangeAbsentValid');
1482     var v = form.validate();
1483
1484     form.get(0).reset();
1485     name.valid();
1486
1487     var label = $('#ranges label');
1488     equal( label.text(), "", "Correct error label" );
1489 });
1490
1491
1492
1493 test("Min and Max range set by attributes valid", function() {
1494     //
1495     // cannot test for overflow: 
1496     // When the element is suffering from an underflow,
1497     // the user agent must set the element's value to a valid
1498     // floating-point number that represents the minimum.
1499     // http://www.w3.org/TR/html5/forms.html#range-state-%28type=range%29
1500     //
1501     var form = $('#ranges');
1502     var name = $('#rangeRangeValid');
1503     var v = form.validate();
1504
1505     form.get(0).reset();
1506     name.valid();
1507
1508     var label = $('#ranges label');
1509     equal( label.text(), "", "Correct error label" );
1510 });
1511
1512
1513 test("Min and Max number set by attributes valid", function() {
1514     var form = $('#ranges');
1515     var name = $('#rangeNumberValid');
1516     var v = form.validate();
1517
1518     form.get(0).reset();
1519     name.valid();
1520
1521     var label = $('#ranges label');
1522     equal( label.text(), "", "Correct error label" );
1523 });
1524
1525
1526 test("Min and Max number set by attributes greater", function() {
1527     var form = $('#ranges');
1528     var name = $('#rangeNumberInvalidGreater');
1529     var v = form.validate();
1530
1531     form.get(0).reset();
1532     name.valid();
1533
1534     var label = $('#ranges label');
1535     equal( label.text(), "Please enter a value less than or equal to 200.", "Correct error label" );
1536 });
1537
1538
1539 test("Min and Max number set by attributes less", function() {
1540     var form = $('#ranges');
1541     var name = $('#rangeNumberInvalidLess');
1542     var v = form.validate();
1543
1544     form.get(0).reset();
1545     name.valid();
1546
1547     var label = $('#ranges label');
1548     equal( label.text(), "Please enter a value greater than or equal to 50.", "Correct error label" );
1549 });
1550