Ajax技术的核心是XMLHttpRequest对象(简称XHR),可以通过使用XHR对象获取到服务器的数据,然后再通过DOM将数据插入到页面中呈现。虽然名字中包含XML,但Ajax通讯与数据格式无关,所以我们的数据格式可以是XML或JSON等格式。
XMLHttpRequest对象用于在后台与服务器交换数据,具体作用如下:
在不重新加载页面的情况下更新网页
在页面已加载后从服务器请求数据
在页面已加载后从服务器接收数据
在后台向服务器发送数据
XMLHttpRequest是一个JavaScript对象,它是由微软设计,并且被Mozilla、Apple和Google采纳,W3C正在标准化它。它提供了一种简单的方法来检索URL中的数据。
我们要创建一个XMLHttpRequest实例,只需new一个就OK了
对于IE6不支持原始的XHR对象,则我们要写一个兼容性版本:
if (window.XMLHttpRequest) {
xhr = new XMLHttpRequest();
} else {
try {
xhr = new ActiveXObject("Msxml2.XMLHTTP");
} catch (e) {
xhr = new ActiveXObject("Microsoft.XMLHTTP");
}
}
在创建XHR对象后,接着我们要调用一个初始化方法open(),它接受五个参数具体定义如下:
void open(
DOMString method, //"GET", "POST", "PUT", "DELETE"
DOMString url,
optional boolean async,
optional DOMString user,
optional DOMString password
);
通过上面的定义我们知道open()方法的签名包含五个参数,其中有参数method和url地址是必填的,假设我们针对var url = “checkUnameJson”发送POST请求获取数据,具体定义如下:
var method = "POST";
var url = "checkUnameJson";
// 相当于输入连接 1
xhr.open(method, url,true);
参数1有get和post两个取值
参数2表示什么就不用说了
重点说下第3个参数:boolean的取值
当该boolean值为true时,服务器请求是异步进行的,也就是脚本执行send()方法后不等待
服务器的执行结果,而是继续执行脚本代码;
当该boolean值为false时,服务器请求是同步进行的,也就是脚本执行send()方法后等待
服务器的执行结果的返回,若在等待过程中超时,则不再等待,继续执行后面的脚本代码
对于POST请求来说以下代码必须写上:
xhr.setRequestHeader("content-type", "application/x-www-form-urlencoded")
通过上述代码会启动一个针对myxhrtest.aspx的GET请求,这里有两点要注意:一是URL相对于执行代码的当前页面(使用绝对路径);二是调用open()方法并不会真正发送请求,而只是启动一个请求准备发送。要真正发送请求要使用send()方法,send()方法接受一个参数,即要作为请求主体发送的数据,如果不需要通过请求主体发送数据,我们必须传递一个null值。在调用send()之后,请求就会被分派到服务器,完整Ajax请求代码如下:
var method = "POST";
var url = "checkUnameJson";
// 相当于输入连接 1
xhr.open(method, url,true);
xhr.setRequestHeader("content-type", "application/x-www-form-urlencoded")
//发送 回车 2
xhr.send("uname=" + document.getElementById("name").value);
在发送请求之后,我们需要检查请求是否执行成功,首先可以通过status属性判断,一般来说,可以将HTTP状态代码为200作为成功标志。这时,响应主体内容会保存到responseText中。此外,状态代码为304表示请求的资源并没有被修改,可以直接使用浏览器缓存的数据,Ajax的同步请求代码如下:
if (xhr.addEventListener) {
xhr.addEventListener("readystatechange", function() {
if (xhr.readyState == 4) {
//当返回状态 200时 读取内容
if (xhr.status == 200) {
document.getElementById("divtext").innerHTML = xhr.responseText;
}
}
});
} else {
xhr.onreadystatechange = function() {
if (xhr.readyState == 4) {
//当返回状态 200时 读取内容
if (xhr.status == 200) {
document.getElementById("divtext").innerHTML = xhr.responseText;
}
}
}
}
var method = "GET";
var url = "hello.txt";
// 相当于输入连接 1
xhr.open(method, url);
//发送 回车 2
xhr.send();
如果我们发送异步请求,那么在请求过程中javascript代码会继续执行,这时可以通过readyState属性判断请求的状态,当readyState = 4时,表示收到全部响应数据,属性值的定义如下:
现在我们对Ajax的请求实现有了初步的了解,接下来我们将通过具体的例子说明Ajax请求的应用场合和局限。
在日常网络生活中,我们在注册页面进行注册时,有时输入用户名当鼠标离开输入框时,页面会立即显示该用户名是否可以,这些就是使用了ajax实现的,现在让我们模拟以下它的实现过程
首先写个注册页面
<form action="" >
姓名:<input type="text" name="uname" id="name" onblur="checkName()">
<span id="sp"></span>
<br>
密码:<input type="password" name="pwd"><br>
<input type="submit" value="注册">
</form>
完整的ajax请求:
<script type="text/javascript">
var xhr;
function checkName() {
if (window.XMLHttpRequest) {
xhr = new XMLHttpRequest();
} else {
try {
xhr = new ActiveXObject("Msxml2.XMLHTTP");
} catch (e) {
xhr = new ActiveXObject("Microsoft.XMLHTTP");
}
}
if (xhr.addEventListener) {
xhr.addEventListener("readystatechange", common);
} else {
xhr.onreadystatechange = common;
}
var method = "POST";
var url = "checkUnameJson";
// 相当于输入连接 1
xhr.open(method, url,true);
xhr.setRequestHeader("content-type", "application/x-www-form-urlencoded")
//发送 回车 2
xhr.send("uname=" + document.getElementById("name").value);
function common() {
if (xhr.readyState == 4) {
//当返回状态 200时 读取内容
if (xhr.status == 200) {
//返回值是json格式的字符串 以下代码是把json格式的字符串转成json
var strJson = xhr.responseText;
var jsonObj = JSON.parse(strJson);
// alert(jsonObj)
console.log(strJson);
if (jsonObj.result) {
document.getElementById("sp").innerHTML = "不可用";
} else {
document.getElementById("sp").innerHTML = "可用";
}
}
}
}
}
</script>
为求方便 我们在servlet中采用list模拟数据库中的用户表:
@WebServlet("/ajax/checkUnameJson")
public class CheckNameJsonServlet extends HttpServlet {
private static final long serialVersionUID = 1L;
private List<String> names = new ArrayList<>();
public CheckNameJsonServlet() {
super();
names.add("z3");
names.add("l4");
names.add("lgh");
}
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.setCharacterEncoding("utf-8");
//设置浏览器使用什么编码去解码
response.setContentType("application/json;charset=utf-8");
//告诉tomcat响应体以utf-8编码 如果设置了上面的响应头 则不再起作用
//response.setCharacterEncoding("utf-8");
String name = request.getParameter("uname");
boolean flag = names.contains(name);
if(flag){
response.getWriter().write("{\"result\":true}");
}else{
response.getWriter().write("{\"result\":false}");
}
}
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
doGet(request, response);
}
}
运行
输入字符“lgh”结果:
输入字符“hello”结果: