[jQuery]使用jQuery.Validate进行客户端验证(高级篇-下)——不使用微软验证控件的理由

来源:互联网 发布:重新分区后数据恢复 编辑:程序博客网 时间:2024/05/20 17:40
 继续上一篇文章使用jQuery.Validate进行客户端验证(高级篇-上),本文将继续介绍jQuery.Validate的高级应用——jQuery.Validate的AJAX验证及简单扩展。

今天主要介绍的内容有:

1、如何使用jQuery.Validate进行AJAX验证?

2、默认jQuery.Validate在进行AJAX验证时返回必须是bool类型,如何返回一个对象包括错误消息及验证结果?

3、在反复使用jQuery.Validate进行AJAX验证时,总是需要编写相关AJAX参数,可否进行进一步封装?

 

第一点:如何使用jQuery.Validate进行AJAX验证?(具体见High-2.aspx

jQuery.Validate为我们提供了一个方便的AJAX验证方式(封装了jQuery的AJAX,同时将jQuery的AJAX和jQuery.Validate的验证很好的结合在一起),在此我仅仅介绍jQuery.Validate在ASP.NET下如何进行AJAX验证,PHP、JSP等请查看官方例子。

我是采用jQuery.Validate+WebService进行AJAX验证,客户端编写jQuery.Validate的remote验证属性,服务器端采用WebSerice进行接收参数进行验证。

首先来看下jQuery.Validate的remote属性如何编写AJAX验证规则:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
function InitRules() {
            opts = {
             rules:
                {
                    <%=txtUid.UniqueID %>: 
                    {
                        required: true,
                        remote:{
                            type: "POST",
                            async: false,
                            url: "WebService.asmx/CheckUid",
                            dataType: "xml",
                            data: {uid:function(){ return jQuery("#<%=txtUid.ClientID %>").val();}}
                        }
                    }
                }
            }
        }

如果使用过jQuery.ajax的朋友肯定会很熟悉这段代码,jQuery.Validate的remote采用和jQuery.ajax相同的参数设置(原因就上面所说的封装了jQuery.ajax的原因)。

这边来详细讲解下jQuery.Validate的remote的一些知识:

1、jQuery.Validate的remote默认可以直接填写远程验证的地址,格式为:remote:”validate.aspx”,但是很多情况下这个远程验证需要提交参数、返回类型等限制,所以就可以采用在“{}”中编写具体属性的方式来包装提交参数。

2、jQuery.Validate的remote官方代码中,远程的输出只能是true或者false,不允许有其他输出,这个我觉得不太好,具体的扩展在后面我会讲到

3、jQuery.Validate的remote在使用时如果想提交参数需要以JSON的方式提交格式如下:

?
1
2
3
4
5
data: {
        uid:function(){ 
                return jQuery("#<%=txtUid.ClientID %>").val();
        }
}

此处肯定会有人不明白,为什么参数需要以function的形式提交,而不是直接写

jQuery("#<%=txtUid.ClientID %>").val();

这里我要说明的是:jQuery.Validate的验证规则是在页面加载的时候就已经被加载了的,如果还是像以往一样直接写"jQuery("#<%=txtUid.ClientID %>").val();",那么验证的时候提交给服务器端的数据永远是页面加载时txtUid控件的值。

而使用function的好处就是在页面加载的时候仅仅告诉jQuery.Validate,在控件需要进行remote验证的时候需要调用function这个函数,这样就保证了在执行remote验证的时候可以获取到最新的值

我还修改了jQuery.Validate的remote方法,先来看下我修改的代码(具体见scripts/jquery.validate1.js 896行):

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
if (previous.old !== value) {
    previous.old = value;
    var validator = this;
    this.startRequest(element);
    var data = {};
    data[element.name] = value;
    $.ajax($.extend(true, {
        //url:url,//此URL无法获取
        url: param.url,//获取param验证规则中所写路径
        mode: "abort",
        port: "validate" + element.name,
        type: param.type,
        dataType: "json",
        //data:data,
        data: param.data || data,//获取param.data或data中所提交的参数
        success: function(response) {
        以下省略...
}

这边我修改了url和data的获取方式,主要是因为在真正执行的时候,变量url是空的,所以需要从param中获取。

而data为什么要改成param.data || data,主要原因就是下面这句代码:

data[element.name] = value;

这句代码的意思就是:为哪个控件设置远程验证就获取哪个控件的值,但是在实际的开发中,当遇到进行AJAX验证的时候会出现需要同时提交多个数据的情况,此时这句代码就是错误的了,所以需要改成

param.data || data,这样就能保证在提交多个数据的时候以多个数据为准。

下面来看下webservice的代码:

?
1
2
3
4
5
[WebMethod]
public bool CheckUid(stringuid)
{
    returnuid == "testuid"? true : false;
}

相当的简单,就是判断下用户名是不是指定的用户名。

注意:webservice.cs中必须将[System.Web.Script.Services.ScriptService]这个特性取消注释,否则AJAX验证将无效!

 

第二点:默认jQuery.Validate在进行AJAX验证时返回必须是bool类型,如何返回一个对象包括错误消息及验证结果?(具体见App_Code/WebService.cs/CheckUid

在第一点中介绍jQuery.Validate知识的时候就提到了,jQuery.Validate默认直接收true或false,但是在具体的开发中,我们会分层开发,三层或者多层,webservice在接收到验证请求后不做具体的处理直接调用逻辑层的验证方法,交由逻辑层进行验证操作(当然你也可以把验证全部写在webservice中,但是这样就体现不出分层的好处了),此时的验证会产生多种情况,以最常见的用户名验证为例:

    1)用户名已存在,此时的消息应该是“用户名已存在,请重新输入!”

    2)用户名不符合规则,此时的消息应该是“用户名不符合规则,请重新输入!”

    3)验证时出现程序异常,此时的消息应该是“程序出现异常,请联系管理员!”

可以看出,仅仅一个用户名验证就会出现这3种信息,如果不返回一个明确的消息,仅仅告诉用户“用户名有误”,客户端的使用者将会相当的痛苦,因为使用者并不知道他的用户名输入到底错在哪了。

所以为了更好的客户体验,以及项目的合理性,我们在服务器端封装一个实体类(具体见AppCode/AjaxClass),代码如下:

?
1
2
3
4
5
6
[Serializable]
public class AjaxClass
{
    publicstring Msg { get; set; }
    publicint Result { get; set; }
}

就是一个最简单的实体类,有2个属性,Msg和Result,Msg用于存放验证失败的信息,Result用于存放结果。

 

看下WebSerivce的代码如何修改:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
[WebMethod]
public AjaxClass CheckUid(string uid)
{
    //return uid == "testuid" ? true : false;
    AjaxClass ajaxClass =new AjaxClass();
    try
    {
        if(uid == "testuid")
        {
            ajaxClass.Msg ="用户名已存在,请重新输入!";
            ajaxClass.Result = 0;
        }
        elseif (uid.IndexOf("test") == -1)
        {
            ajaxClass.Msg ="用户名格式不正确,用户名必须包含test,请重新输入!";
            ajaxClass.Result = 0;
        }
        else
        {
            ajaxClass.Msg ="格式正确!";
            ajaxClass.Result = 1;
        }
    }
    catch
    {
        ajaxClass.Msg ="程序出现异常,请联系管理员!";
        ajaxClass.Result = 0;
    }
    returnajaxClass;
}

上面的WebService就完整的实现了我先前说的3种错误情况(由于这边仅仅是例子所以就只有表示层,实际开发中需要分层开发,此代码应该放入业务逻辑层

注意:在webservice返回值前,如果检查成功必须要为ajaxClass.Result = 1,否则客户端验证会无法通过。

虽然完成了服务器端的代码修改,但是直接运行页面还是会出错,这是因为我上面所说过的,jQuery.Validate的remote远程的输出只能是true或者false,我们来看下具体的代码,其中注释掉的就是原来官方的代码:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
success: function(response) {
    if (response.Result) {//if(response){
        var submitted = validator.formSubmitted;
        validator.prepareElement(element);
        validator.formSubmitted = submitted;
        validator.successList.push(element);
        validator.showErrors();
    } else {
        var errors = {};
        //errors[element.name] = response.Result || validator.defaultMessage(element, "remote");
        errors[element.name] = response.Msg;
        validator.showErrors(errors);
    }
    previous.message = response.Msg; //previous.valid = response;
    previous.valid = response.Result;
    validator.stopRequest(element, response.Result);
}

可以看到一共修改了3处地方:

1、判断返回值,原来是直接判断response,现在则是判断response.Result,因为现在的response已经是一个包含消息及结果的对象了。

2、错误消息,原来的错误消息是直接获取默认配置好的消息,我这边是获取response.Msg。

3、设置previous对象,将previous对象的消息和结果设置为AJAX返回的消息和结果,以供jQuery.Validate下面代码的返回。

这样jQuery.Validate的remote的方法就修改了,但是并没有结束,原因是先前在AJAX提交参数的时候由于jQuery.Validate的验证规则的缘故,提交的参数并不是以JSON的格式提交的而是以{uid:function()}这样的方式,结果就导致了无法设置jQuery.AJAX的contentType:"application/json; charset=utf-8",如果设置了会出现以下错误:

pic24这样从webservice返回的AjaxClass对象就无法像以往的JSON方式直接操作了,所以我们只能换一种格式——XML,因为webservice默认返回的数据是XML格式:

?
1
2
3
4
5
<?xmlversion="1.0"encoding="utf-8"?> 
- <AjaxClassxmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xmlns:xsd="http://www.w3.org/2001/XMLSchema"xmlns="http://tempuri.org/">
  <Msg>用户名格式不正确,用户名必须包含test,请重新输入!</Msg
  <Result>0</Result
  </AjaxClass>

接下来看下具体的remote方法应该如何编写,设置dataType:”xml”,然后将XML数据转换成一个对象以供上面我修改的jQuery.Validate的remote方法中ajaxsuccess的使用,具体看一下代码:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
remote:{
    type: "POST",
    dataType:"json",
    async: false,
    url: "WebService.asmx/CheckUid",
    data: {uid:function(){ return jQuery("#<%=txtUid.ClientID %>").val();}},
    dataFilter: function(dataXML) {
        var result = new Object();
        result.Result = jQuery(dataXML).find("Result").text();
        result.Msg = jQuery(dataXML).find("Msg").text();
        if (result.Result == "-1") {
            result.Result = false;
            return result;
        }
        else {
            result.Result = result.Result == "1" ? true : false;
            return result;
        }
    }
}

就是jQuery.Ajax方法dataFilter,可以在AJAX请求成功后将数据进行过滤处理,这里我就使用了jQuery方法把结果和消息从XML中获取出来直接赋给一个对象,再将这个对象返回,交由ajaxsuccess使用。

这样就算是完成了修改jQuery.Validate的remote方法,使得可以返回验证结果及验证消息,看下效果图:

pic25

 

第三点:在反复使用jQuery.Validate进行AJAX验证时,总是需要编写相关AJAX参数,可否进行进一步封装?(具体见High-3.aspx和jquery.validate.extension.js)

在开发一个系统的时候经常会用到AJAX的验证,而如果每次都要编写上面那么多的代码还是很不方便,所以我现在就来进行一下简单的封装,代码如下:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
//远程验证抽象方法
function GetRemoteInfo(postUrl, data) {
    var remote = {
        type: "POST",
        async: false,
        url: postUrl,
        dataType: "xml",
        data: data,
        dataFilter: function(dataXML) {
            var result = new Object();
            result.Result = jQuery(dataXML).find("Result").text();
            result.Msg = jQuery(dataXML).find("Msg").text();
            if (result.Result == "-1") {
                result.Result = false;
                return result;
            }
            else {
                result.Result = result.Result == "1" ? true : false;
                return result;
            }
        }
    };
    return remote;
}

这个函数主要接收2个参数,一个是远程验证的路径和需要提交的参数,返回包装好的remote对象。

页面调用也很简单,代码如下:

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
<script src="scripts/jquery.validate.extension.js" type="text/javascript"></script>
    <script type="text/javascript">
        function InitRules() {
            var dataInfo = {uid:function(){ return jQuery("#<%=txtUid.ClientID %>").val();}};
            var remoteInfo = GetRemoteInfo('WebService.asmx/CheckUid', dataInfo);
  
            opts = {
             rules:
                {
                    <%=txtUid.UniqueID %>: 
                    {
                        required: true,
                        remote:remoteInfo
                    }
                }
            }
        }
    </script>

怎么样?相比上面的代码一下子干净了很多吧?

页面上只要做3步操作:

1、包装好需要提交的data对象。

2、将远程验证地址和包装好的data对象传递给封装好的方法获取remote对象。

3、将函数返回的remote对象放入规则中。

 

至此使用jQuery.Validate进行客户端验证——不使用微软验证控件的理由这一系列就算全部写完了,大体上将jQuery.Validate在ASP.NET上的一些常见应用讲了一下,同时也提出了许多我自己修改扩展的东西,希望对正在苦恼客户端验证的朋友有所帮助,谢谢大家的支持了!

PS:1、其实这一系列并没有把jQuery.Validate的所有功能介绍完,比如onfocusin,onfocusout,onkeyup等,这些就需要大家在使用的过程中自己查看源代码实验了。

2、本文有点长,而且内容比较多,如果文中有什么错误或者有指导意见欢迎大家提出来,谢谢了!

原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 微信支付月限额怎么办 微信超额20万怎么办 微信支付超额了怎么办 微信零钱超额了怎么办 微信的充值冲错了怎么办 有流量还扣话费怎么办 自动取款机充值到电子账户怎么办 淘宝qb充错了怎么办 q币冲错了人家不给怎么办 qq充值话费错号怎么办 qq充错号码了怎么办 qq交话费不到账怎么办 充错手机号码而且是空号怎么办 微信钱包充错话费怎么办 QQ充值话费充到空号了怎么办 给别人充错话费怎么办 用qq交错话费对方是空号怎么办 号码变成空号了怎么办 qq冲流量冲错了怎么办 流量冲错了套餐怎么办 微信流量充错号码怎么办 微信支付不进账怎么办 充话费充不进去怎么办 用支付宝充话费没到账怎么办 支付宝充话费未到账怎么办 话费充了不到账怎么办 转转买家不确认收货怎么办 充话费错了怎么办啊 淘宝充值流量没到账怎么办 微信手机充错了怎么办 支付宝充话费没到账怎么办 裤子摔了一个洞怎么办 顾客反应衣服质量不好怎么办 淘宝买的衣服味道很大怎么办 三国杀账号忘了怎么办 宽带连接被删了 怎么办 手机被偷了qq怎么办 手机丢了微信怎么办啊 手机店把手机修坏了怎么办 在手机店买到山寨机手机怎么办 有人在qq群上骂我怎么办