使用promises进行jQuery验证

时间:2015-01-23 22:39:26

标签: javascript jquery jquery-validate promise

我正在使用jQuery Validation plugin作为注册表单,并尝试检查电子邮件地址是否已作为验证的一部分。问题是检查是通过promise进行的,我不知道如何(或者如果)我可以使用验证插件。这就是我目前所拥有的:

$("#signup form").validate({
    rules: {
        emailSignup: {
            email: true,
            required: true,
            remote: checkAvailable
        }
    }
});

function checkAvailable() {
    var email = $("#emailSignup").val(),
        available;

    App.isEmailAvailable(email)
        .then(function(response) {
            available = response;
        })
        .error(function() {
            available = response;
        });

    setTimeout(function() {
        if (available == true) {
            console.log("is available");
            return true;
        } else {
            console.log("not available");
            return false;
        }
    }, 100);
}

在我尝试记录之前,setTimeout只是一种确保我得到响应的hacky方法(我知道这很糟糕,但它只是用于测试)。

问题是,正确地记录is availablenot available,具体取决于我输入的电子邮件地址,因此它可以正常运行。但我似乎无法将true / false实际返回到remote方法,以便启动错误处理。所以,即使它根据响应记录not available,任何语法上有效的电子邮件都会被标记为有效。

这一切都可能吗?


更新:我也尝试在自定义方法中执行此操作:

jQuery.validator.addMethod("email", function(value, element) {
    var field = this,
        available;

    App.isEmailAvailable(value)
        .then(function(response) {
            available = response;
        })
        .error(function() {
            available = response;
        });

    setTimeout(function() {
        if (available == true) {
            console.log("is available");
            return field.optional(element) || /^[\w-+\.]+@([\w-]+\.)+[\w-]{2,4}$/.test(value);
        } else {
            console.log("not available");
            return false;
        }
    }, 100);
}, jQuery.validator.format("Please enter a valid email address."));

所以这里的想法是检查地址是否可用,如果是,那么它会检查它在语法上是否有效。同样,它会根据我输入的地址正确记录is available / not available,但不会正确返回true / false以将字段标记为有效或无效。< / p>

3 个答案:

答案 0 :(得分:1)

你传递给setTimeout()的函数将在以后执行(a.k.a异步) - 在checkAvailable()完成之后。因此,对于checkAvailable(),它的返回值是没有意义的。

你应该做以下事情:

DisableTheForm();

App.isEmailAvailable(value)
        .then(function(response) {
            $("#signup form").validate();
            if( it is valid) {
               EnableTheForm();
               PostFormData(); 
            }
        })
        .error(function() {
           CryAsItIsNotAvailable();
           EnableTheForm();
        });

所以要对你的isEmailAvailable

的积极反馈进行验证

答案 1 :(得分:1)

基于&#34;遥控器&#34; jquery验证规则:

$.validator.addMethod('users_email_exists', function (value, element) {

    var method = 'remote';

    var previous = this.previousValue(element, method);
    var validator = this;

    if (!this.settings.messages[element.name]) {
        this.settings.messages[element.name] = {};
    }

    previous.originalMessage = previous.originalMessage || this.settings.messages[element.name][method];
    this.settings.messages[element.name][method] = previous.message;

    var optionDataString = $.param({data: value});
    if (previous.old === optionDataString) {
        return previous.valid;
    }
    previous.old = optionDataString;

    this.startRequest(element);

    new Promise(function (fulfill) {

        // YOUR STUFF, YOUR AJAX GET/POST REQUEST AND URL WITH PARAMS

        $.get('/backend/users/ajax/filtered-users-list', {email: value})
            .done(function (data) {


                    // YOUR STUFF TO VALIDATE DATA

                    // IF VALID TRUE -> validation success
                    // IF VALID FALSE -> validation failure


                var valid = !data.length;





                fulfill(valid);
            })
    }).then(function(valid) {

        validator.settings.messages[ element.name ][ method ] = previous.originalMessage;

        if ( valid ) {
            submitted = validator.formSubmitted;
            validator.resetInternals();
            validator.toHide = validator.errorsFor( element );
            validator.formSubmitted = submitted;
            validator.successList.push( element );
            validator.invalid[ element.name ] = false;
            validator.showErrors();
        } else {
            errors = {};
            message = validator.defaultMessage( element, { method: method, parameters: value } );


            // YOUR STUFF, YOUR VALIDATION MESSAGE HERE

            errors[ element.name ] = previous.message = 'EMAIL ALREADY ASSIGNED TO AN USER';



            validator.invalid[ element.name ] = true;
            validator.showErrors( errors );
            }
            previous.valid = valid;
            validator.stopRequest( element, valid );
        });

        return "pending";
    },
    "EMAIL ALREADY ASSIGNED TO AN USER"
);

然后调用您的自定义规则:

$("#signup form").validate({
rules: {
    emailSignup: {
        email: true,
        required: true,
        users_email_exists: true
        }
    }
});

将此脚本包含在Promise类引用中:

<!-- promise -->
<script src="https://www.promisejs.org/polyfills/promise-7.0.4.min.js"></script>
<script src="https://www.promisejs.org/polyfills/promise-done-7.0.4.min.js"></script>

答案 2 :(得分:0)

您无法使用remote方法,因为它正在寻找通过ajax()访问“远程”的网址参数。

您显然不会使用ajax()调用JavaScript函数,因此使用remote调用JavaScript函数毫无意义。


您可以使用the .addMethod() method创建自定义功能。但是,如果任何部分异步执行,则会出现问题,因为在获得结果之前将对自定义规则进行评估。