您好,欢迎访问三七文档
当前位置:首页 > 临时分类 > 探讨Ajax获取表单值向Servlet传递的设计方案
探讨Ajax获取表单值向Servlet传递的设计方案现在JavaWeb领域,MVC框架越来越多,比较出名的有Struts、Struts2、SpringMVC、WebWork等。而Ajax,作为一种与特定的动态Web编程语言(如Java、C#、PHP)无关的技术,也已经被引入到了JavaMVC框架的各家各户。而这些MVC框架,归根到底,都是对Servlet技术的封装。同时,支持Ajax的JavaScript框架(or类库)也越来越多,出名的如Jquery、Ext、Prototype、DWR等,而它们实现异步传输功能还是离不开JavaScript中的XMLHttpRequest这个对象。好,转入正题吧。Ajax通过XMLHttpRequest对象实现异步传输,那我们首先要获取这个对象。由于浏览器的差异,为了兼容各种常用的浏览器,先写一个初始化XMLHttpRequest对象的方法,代码如下:Js代码/***Get方式向服务器端异步发送数据*@paramurl服务器端的路径,数据发送的目的地*@paramdata发送的数据,格式如:key1=value1&key2=value2*@paramcallback回调函数,*/functiondoGet(url,data,callback){varurl=url;if(url.indexOf(?)==-1){url=url+?+data;}else{url=url+&+data;}initXmlHttp();xmlHttp.onreadystatechange=callback;//注册回调函数xmlHttp.open(GET,url,true);//设置连接信息xmlHttp.send(null);}/***Post方式向服务器端异步发送数据*@paramurl服务器端的路径,数据发送的目的地*@paramdata发送的数据,格式如:key1=value1&key2=value2*@paramcallback回调函数*@return*/functiondoPost(url,data,callback){initXmlHttp();//初始化xmlHttp.onreadystatechange=callback;//注册回调函数xmlHttp.open(POST,url,true);xmlHttp.setRequestHeader(Content-Type,application/x-);xmlHttp.send(data);}/***默认回调函数*只在测试时使用,在doGet和doPost函数中的第三个参数callback,可由用户自定义回调函数,*若不设定,则调用默认的回调函数*/functioncallback(){//判断对象的状态是否交互完成if(xmlHttp.readyState==4){//判断http的交互是否成功if(xmlHttp.status==200){//获取服务器返回的纯文本数据varresponseText=xmlHttp.responseText;//获取服务器返回的XML格式数据//varresponseXml=xmlHttp.responseXML;//Alert从服务器端返回的信息window.alert(responseText);}}}对上面的代码,在这里解析一下:XMLHttpRequest对象的请求状态(readyState)有0、1、2、3、4,其中,0表示未初始化,1表示open方法成功调用,2表示服务器应答客户端请求,3表示交互中,HTTP头信息已经收到,但响应数据还没有接收,4表示数据接收完成。我们通过“xmlHttp.onreadystatechange=callback;”来设置如果XMLHttpRequest对象的请求状态发生改变了,则会执行回调函数callback。我们可以看到,在callback方法体中,我们只关心readyState==4(交互完成)的情况,再获取从服务器端返回的状态码status,常见的状态码有:200表示交互成功,404表示页面没找到,500表示服务器处理错误等。接着,通过XMLHttpRequest的responseText属性得到从服务器端返回的文本数据,或者通过responseXML属性获得XML格式的数据。在上面的代码中,doGet方法和doPost方法都有参数”data”,它由XMLHttpRequest负责从客户端传送到服务器端,对于Get方法,附在URL尾部,例如:member.jsp?name=xxx&sex=male。对于Post方式,可调用XMLHttpRequest的send方法发送。data的数据形式比较灵活,可以是普通的参数格式、XML格式,JSON格式或者是其他格式,只要你能发送过去,服务器端就有办法将你解析出来。在这里,我们降低难度,就用最简单的参数格式,即key1=value1&key2=value2&key3=value3&……我们都知道,HTTP协议的Get方式传输数据,是通过把这些key-value串附到URL后面的,也就是我们只要点表单的提交按钮,就可以看到地址栏后面会多了一串key-value,代表表单里各输入框的名和值。然后,我们要做异步发送数据,就不能用表单的自动提交了,也就是说,得自己一个一个获取到各输入框的数据,然后再一个一个拼成上面的key-value串再发送。有没有一种简单的办法来组织这些数据呢?大家看到key-value是否会想到Java中的什么类?请看下面代码,我用JavaScript写了一个Map类(JavaScript中的“function”可以看作是方法,也可以看作是面向对象的“类”),就是类似于Java中我们常用的Map接口。Java代码/***Map类*实现了类似于Java语言中的Map接口的常用方法*/functionMap(){//key集this.keys=newArray();//value集this.values=newArray();//添加key-value进Mapthis.put=function(key,value){if(key==null||key==undefined)return;varlength=this.size();for(vari=0;ilength;i++){//如果keys数组中有相同的记录,则不覆盖原记录的值if(this.keys[i]==key)this.values[i]=value;}this.keys.push(key);this.values.push(value);};//获取指定key的valuethis.get=function(key){varlength=this.size();for(vari=0;ilength;i++){if(this.keys[i]==key){returnthis.values[i];}else{continue;}returnnull;}};//移除指定key所对应的mapthis.remove=function(key){varlength=this.size();for(vari=0;ilength;i++){if(this.keys[i]==key){while(ilength-1){this.keys[i]=this.keys[i+1];this.values[i]=this.values[i+1];i++;}//处理最后一个元素this.keys.pop();this.values.pop();break;}}};//是否包含指定的keythis.containsKey=function(key){varlength=this.size();for(vari=0;ilength;i++){if(this.keys[i]==key){returntrue;}}returnfalse;};//是否包含指定的valuethis.containsValue=function(value){varlength=this.size();for(vari=0;ilength;i++){if(this.values[i]==value){returntrue;}}returnfalse;};//包含记录总数this.size=function(){returnthis.keys.length;};//是否为空this.isEmpty=function(){returnthis.size()==0?true:false;};//清空Mapthis.clear=function(){this.keys=newArray();this.values=newArray();};//将map转成字符串,格式:key1=value1,key2=value2this.toString=function(){varlength=this.size();varstr=;for(vari=0;ilength;i++){str=str+this.keys[i]+=+this.values[i];if(i!=length-1)str+=,;}returnstr;};}代码比较长,有些方法在本例中可能用不到,但也写出来了,或者在其他地方可能有用吧。当我们使用这个Map类来存储HTTP的参数时,发觉有几个不妥的地方:一是put方法,在Java的Map接口中,是不允许有重复的key存在的,而在JavaScript中作为传输参数的载体时,很多时候会出现多个同名的key的,例如处理表单的checkbox时,同一个name的有几个checkbox,构成一个复选框组,组织参数时就形如“key=value1&key=value2”,故put方法必须改。也是由于这个原因,get方法和remove方法也要改。二是toString方法,key=value对,不是用“,”号隔开的,而是用“&”号,故toString方法也须改。而有时候想想,如果把Map类改了,如果其他地方要用到的话,是不是还是改回来,与其改来改去的,不如继承它,重写put、get、remove和toString方法。好主意,代码如下:Js代码/***ParamMap类,用于存储HTTP请求中的Get方法或者Post方法所传递的参数*继承于Map类,但改写一些方法,以适合HTTP请求中的参数格式*与Map不同之处有:ParamMap允许多个同名的key存在,*toString方法返回的key=value对以&号连接,而不是,号,等等。*/functionParamMap(){//继承Map类Map.call(this);//重写put方法,允许多个同名key存在this.put=function(key,value){if(key==null||key==undefined)return;this.keys.push(key);this.values.push(value);};//重写get方
本文标题:探讨Ajax获取表单值向Servlet传递的设计方案
链接地址:https://www.777doc.com/doc-2452494 .html