OK, I give up. After trying endless permutations of inline functions, callbacks, return parameters, I still cannot get this to behave how I want. Any help would be appreciated.
好吧,我放弃。在尝试了连续的内联函数、回调函数、返回参数的排列之后,我仍然不能让它表现出我想要的样子。如有任何帮助,我们将不胜感激。
Current status: everything works except the 'checkEmail' error message. The javascript popups convey the proper messages to the user, but the field will not show any error message, whether true or false is returned by the handlers.
当前状态:除了“检查电子邮件”错误消息外,一切正常。javascript弹出窗口将正确的消息传递给用户,但该字段不会显示任何错误消息,无论处理程序返回的是真还是假。
The desired outcome is that if the JSON payload from the AJAX call is anything other than a 200, to pop a Javascript alert and highlight the field as invalid with the appropriate error message. Currently, it pops the alerts, but doesn't mark the field as invalid.
理想的结果是,如果AJAX调用的JSON有效负载不是200,则弹出一个Javascript警告,并在适当的错误消息中突出显示该字段无效。目前,它会弹出警报,但不会将字段标记为无效。
(Sorry, this is jQuery 1.7 + jquery.validation plugin)
(对不起,这是jQuery 1.7 + jQuery。验证插件)
JSON responses:
Our JSON response payloads look like this:
我们的JSON响应有效载荷如下:
{"message": "Email is not in use.", "code": 200, "email": "test-39485787@mailinator.com"}
or
或
{"message": "Duplicate email address detected", "code": 401}
The code
<html>
<head>
<script>
// You'd think this should be false, but no
// Also it apparently needs to be a quoted
// string: http://*.com/a/11496502/814669
var checkEmailStatus = "true";
// Success Handling
checkEmailSuccess = function(data, textStatus, jqXHR) {
checkEmailStatus = "true";
switch (data.code) {
case 200:
checkEmailStatus = "false"; // Nothing set here matters
return false; // Return valued from here don't matter
case 401:
alert("Sorry, our system has detected that an account with this email address already exists.");
break;
case undefined:
alert("An undefined error occurred.");
break;
default:
alert("An undefined error occurred.");
break;
}
return checkEmailStatus;
};
// Error Handling
checkEmailError = function(jqXHR, textStatus, errorThrown) {
if (jqXHR.status == 404) {
alert("Could not find the API Server (404). We apologize for the inconvenience.");
} else {
alert("Terrible things have happened" + textStatus);
}
return false;
};
// The Validator
jQuery.validator.addMethod("checkEmail", function(value, element) {
$.ajax({
type: "POST",
cache: "false",
async: "false",
url: "/json/checkEmail",
dataType: "json",
data: {
email: function() {
return $("email").val();
}
},
success: checkEmailSuccess,
error: checkEmailError
});
// Seems checkEmailStatus value never gets changed:
return checkEmailStatus;
}, "Email Address Problem");
// The Binding
$(document).ready(function(){
$('#MyForm').validate({
onfocusout: false,
onkeyup: false,
rules: {
"email": {
required: true,
minlength: 2,
maxlength: 42,
email: true,
checkEmail: true
}
}
});
});
</script>
</head>
<body>
<!-- the Form -->
<form id="MyForm">
<input type="text" name="email"/>
<input type="submit" name="submit"/>
</form>
</body>
</html>
3 个解决方案
#1
13
The correct answer here is to indeed use the "remote" option, but do all of your response processing using "dataFilter":
这里的正确答案是确实使用“remote”选项,但是使用“dataFilter”完成所有的响应处理:
checkEmailSuccess = function(response) {
switch (jQuery.parseJSON(response).code) {
case 200:
return "true"; // <-- the quotes are important!
case 401:
alert("Sorry, our system has detected that an account with this email address already exists.");
break;
case undefined:
alert("An undefined error occurred.");
break;
default:
alert("An undefined error occurred");
break;
}
return false;
};
"email": {
required: true,
minlength: 2,
maxlength: 42,
email: true,
remote: {
url: "/json/checkEmail",
type: "POST",
cache: false,
dataType: "json",
data: {
email: function() { return $("#email").val(); }
},
dataFilter: function(response) {
return checkEmailSuccess(response);
}
}
},
#2
2
The addMethod expects a true/false response inmediately and you are doing an AJAX call which is an async operation so the variable checkEmailStatus will return its initial value. Please look into "remote" validation, this is what you need:
addMethod期望得到正确/错误的响应,您正在执行一个AJAX调用,这是一个异步操作,因此变量checkEmailStatus将返回它的初始值。请查看“远程”验证,这是您需要的:
http://jqueryvalidation.org/remote-method/
http://jqueryvalidation.org/remote-method/
Update: I just noticed the async = false. Try to avoid that option. It reduces the user experience.
更新:我刚刚注意到async = false。尽量避免这种选择。它减少了用户体验。
Try this:
试试这个:
$('#MyForm').validate({
onfocusout: false,
onkeyup: false,
rules: {
"email": {
required: true,
minlength: 2,
maxlength: 42,
email: true,
//checkEmail: true
remote:{
url: "/json/checkEmail", //make sure to return true or false with a 200 status code
type: "post",
data: {
email: function() {
return $("email").val();
}
}
}
}
}
});
#3
0
If you want to use actual http response codes, you can use the error function of the $.ajax call, it will work inside the validation plugin.
如果希望使用实际的http响应代码,可以使用$的error函数。ajax调用,它将在验证插件中工作。
remote: {
url: "/json/checkEmail",
type: "POST",
cache: false,
dataType: "json",
data: {
email: function() { return $("#email").val(); }
},
error: function(jqXHR, textStatus, errorThrown) {
alert(jqXHR.status);
alert(textStatus);
alert(errorThrown);
}
#1
13
The correct answer here is to indeed use the "remote" option, but do all of your response processing using "dataFilter":
这里的正确答案是确实使用“remote”选项,但是使用“dataFilter”完成所有的响应处理:
checkEmailSuccess = function(response) {
switch (jQuery.parseJSON(response).code) {
case 200:
return "true"; // <-- the quotes are important!
case 401:
alert("Sorry, our system has detected that an account with this email address already exists.");
break;
case undefined:
alert("An undefined error occurred.");
break;
default:
alert("An undefined error occurred");
break;
}
return false;
};
"email": {
required: true,
minlength: 2,
maxlength: 42,
email: true,
remote: {
url: "/json/checkEmail",
type: "POST",
cache: false,
dataType: "json",
data: {
email: function() { return $("#email").val(); }
},
dataFilter: function(response) {
return checkEmailSuccess(response);
}
}
},
#2
2
The addMethod expects a true/false response inmediately and you are doing an AJAX call which is an async operation so the variable checkEmailStatus will return its initial value. Please look into "remote" validation, this is what you need:
addMethod期望得到正确/错误的响应,您正在执行一个AJAX调用,这是一个异步操作,因此变量checkEmailStatus将返回它的初始值。请查看“远程”验证,这是您需要的:
http://jqueryvalidation.org/remote-method/
http://jqueryvalidation.org/remote-method/
Update: I just noticed the async = false. Try to avoid that option. It reduces the user experience.
更新:我刚刚注意到async = false。尽量避免这种选择。它减少了用户体验。
Try this:
试试这个:
$('#MyForm').validate({
onfocusout: false,
onkeyup: false,
rules: {
"email": {
required: true,
minlength: 2,
maxlength: 42,
email: true,
//checkEmail: true
remote:{
url: "/json/checkEmail", //make sure to return true or false with a 200 status code
type: "post",
data: {
email: function() {
return $("email").val();
}
}
}
}
}
});
#3
0
If you want to use actual http response codes, you can use the error function of the $.ajax call, it will work inside the validation plugin.
如果希望使用实际的http响应代码,可以使用$的error函数。ajax调用,它将在验证插件中工作。
remote: {
url: "/json/checkEmail",
type: "POST",
cache: false,
dataType: "json",
data: {
email: function() { return $("#email").val(); }
},
error: function(jqXHR, textStatus, errorThrown) {
alert(jqXHR.status);
alert(textStatus);
alert(errorThrown);
}