AJAX 是与服务器交换数据并更新部分网页的艺术,在不重新加载整个页面的情况下。
它由下列技术组合而成。
1.使用CSS和XHTML来表示。
2.使用DOM模型来交互和动态显示。
3.使用XMLHttpRequest来和服务器进行异步通信。
4.使用javascript来绑定和调用。
AJAX 的核心是 XMLHttpRequest 对象。
Ajax的工作原理
Ajax的工作原理相当于在用户和服务器之间加了—个中间层(A JAX引擎),使用户操作与服务器响应异步化。并不是所有的用户请求都提交给服务器。像—些数据验证和数据处理等都交给Ajax引擎自己来做,,只有确定需要从服务器读取新数据时再由Ajax引擎代为向服务器提交请求。
XMLHttpRequest常用属性
1.onreadystatechange 属性
onreadystatechange 属性存有处理服务器响应的函数。 下面的代码定义一个空的函数,可同时对onreadystatechange 属性进行设置
xmlHttp.onreadystatechange = function() { //代码}
- readyState 属性
readyState 属性存有服务器响应的状态信息。每当 readyState 改变时,onreadystatechange 函数就会被执行。
readyState 属性可能的值:
onreadystatechange 函数添加一条 If 语句,来测试响应是否已完成(意味着可获得数据):
xmlHttp.onreadystatechange = function() {
if (xmlHttp.readyState == 4) {
//从服务器的response获得数据
}
}
- responseText 属性
通过 responseText 属性来取回由服务器返回的数据。
xmlHttp.onreadystatechange = function() {
if (xmlHttp.readyState == 4) {
document.myForm.time.value = xmlHttp.responseText;
}
}
XMLHttpRequest方法
- open() 方法
open() 有三个参数。第一个参数定义发送请求所使用的方法,第二个参数规定服务器端脚本的URL,第三个参数规定应当对请求进行异步地处理。
xmlHttp.open("GET","test.php",true);
2.send() 方法
send() 方法将请求送往服务器。如果我们假设 HTML 文件和 PHP 文件位于相同的目录,那么代码是这样的:
xmlHttp.send(null);
Ajax编程步骤
- 创建XMLHttpRequest对象。
- 设置请求方式。
- 调用回调函数。
- 发送请求
1.创建XMLHttpRequest对象
var xmlHttp=new XMLHttpRequest();
//IE5或者IE6浏览器,则使用ActiveX对象
var xmlHttp=new ActiveXObject("Microsoft.XMLHTTP");
手写A JAX的时候,首先要判断该浏览器是否支持XMLHttpRequest对象,如果支持则创建该对象,如果不支持则创建ActiveX对象。
//第一步:创建XMLHttpRequest对象
var xmlHttp;
if (window.XMLHttpRequest) {
//非IE
xmlHttp = new XMLHttpRequest();
} else if (window.ActiveXObject) {
//IE
xmlHttp = new ActiveXObject("Microsoft.XMLHTTP")
}
2 设置请求方式
WEB开发中,请求有两种形式,一个是get,一个是post,XMLHttpRequest对象的open()方法就是来设置请求方式的
var url = "http://localhost:8080/JsLearning3/getAjax";
xmlHttp.open("POST", url, true);
open() 方法的 async 参数必须设置为 true
回调函数
XMLHttpRequest对象有一个onreadystatechange属性,这个属性返回的是一个匿名的方法,所以回调函数就在
这里写xmlHttp.onreadystatechange=function{},function{}内部就是回调函数的内容。所谓回调函数,就是请求在后台处理完,再返回到前台所实现的功能
xmlHttp.onreadystatechange = function() {
if (xmlHttp.readyState == 4) {
if (xmlHttp.status == 200) {
var obj = document.getElementById(id);
obj.innerHTML = xmlHttp.responseText;
} else {
alert("AJAX服务器返回错误!");
}
}
}
xmlHttp.readyState是存有XMLHttpRequest 的状态。从 0 到 4 发生变化。0: 请求未初始化。1:服务器连接已建立。2: 请求已接收。3: 请求处理中。4: 请求已完成,且响应已就绪。所以这里我们判断只有当xmlHttp.readyState为4的时候才可以继续执行。
xmlHttp.status是服务器返回的结果,其中200代表正确。404代表未找到页面
xmlHttp对象有两个属性都可以获取后台返回的数据,分别是:responseText和responseXML,其中
responseText是用来获得字符串形式的响应数据,
responseXML是用来获得 XML 形式的响应数据
AJAX状态值是指,运行AJAX所经历过的几种状态,无论访问是否成功都将响应的步骤,可以理解成为AJAX运行步骤
AJAX状态码是指,无论AJAX访问是否成功,由HTTP协议根据所提交的信息,服务器所返回的HTTP头信息代码,该信息使用“ajax.status”所获得
AJAX状态码说明 1:请求收到,继续处理 2:操作成功收到,分析、接受 3:完成此请求必须进一步处理 4:请求包含一个错误语法或不能完成 5:服务器执行一个完全有效请求失败
发送请求
//第四步:设置发送请求的内容和发送报送。然后发送请求
var uname= document.getElementsByName("userName")[0].value;
var upass= document.getElementsByName("userPass")[0].value ;
var params = "userName=" + uname+ "&userPass=" +upass+ "&time=" + Math.random();
// 增加time随机参数,防止读取缓存
xmlHttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded;charset=UTF-8");
// 向请求添加 HTTP 头,POST如果有数据一定加加!!!!
xmlHttp.send(params);
实例:
index.jsp
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>$Title$</title>
<script type="text/javascript">
function test1() {
//1.创建XMLHttpRequest对象
var xmlHttp;
if (window.XMLHttpRequest) {
//非IE
xmlHttp = new XMLHttpRequest();
} else if (window.ActiveXObject) {
//IE
xmlHttp = new ActiveXObject("Microsoft.XMLHTTP")
}
//2.打开连接
var username=document.getElementById("username").value;
// xmlHttp.open("get","/testuname?uname="+username,true);
xmlHttp.open("post","/testuname",true);
//3.指定回调函数
xmlHttp.onreadystatechange=function(){
//3.1 判断状态
if(xmlHttp.readyState==4){
//3.2 接受返回的内容
var text = xmlHttp.responseText;
document.getElementById("rs").innerText=text;
}
}
//4.发送
// xmlHttp.send(null);
xmlHttp.setRequestHeader("Content-type", "application/x-www-form-urlencoded;charset=UTF-8");
xmlHttp.send("uname="+username)
}
</script>
</head>
<body>
<h1>注册</h1>
用户名:<input type="text" id="username" name="uname"onblur="test1()"><span id="rs"></span>
</body>
</html>
处理Servlet:
TestServlet.java
package com.yhp.web;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
@WebServlet(value = "/testuname")
public class TestServlet extends HttpServlet {
@Override
protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
//1.接受参数
String uname = req.getParameter("uname");
resp.setContentType("text/html;charset=utf-8");
PrintWriter writer = resp.getWriter();
//2.验证,注意:ajax请求处理完毕后,返回数据时使用PrintWriter输出流,且ajax默认返回原页面
if("admin".equals(uname)){
//用户名已存在
writer.print("用户名已存在");
}else{
//用户名可用
writer.print("用户名可用");
}
}
}
JQuery的ajax
ajax()方法
可以通过发送 HTTP请求加载远程数据,是 jQuery 最底层的 Ajax 实现,具有较高灵活性
$.ajax({
url:请求地址
type:"get | post | put | delete " 默认是get,
data:请求参数 {"id":"123","pwd":"123456"},
dataType:请求数据类型"html | text | json | xml | script | jsonp ",
success:function(data,dataTextStatus,jqxhr){ },//请求成功时
error:function(jqxhr,textStatus,error)//请求失败时
})
get() 方法通过远程 HTTP GET 请求载入信息
$.get(url,data,function(result) {
//省略将服务器返回的数据显示到页面的代码
//url:请求的路径
//data:发送的数据
//success:成功函数
//datatype 返回的数据
});
post() 方法通过远程 HTTP POST 请求载入信息。
$.post(url,data,function(result) {
//省略将服务器返回的数据显示到页面的代码
//url:请求的路径
//data:发送的数据
//success:成功函数
//datatype 返回的数据
});
实例:
.jsp页面
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>$Title$</title>
<script type="text/javascript" src="js/jquery-1.8.0.min.js"></script>
<script type="text/javascript">
$(function(){
$("#username").blur(function(){
//1.接受参数
var uname=$(this).val();
//2.使用ajax发送请求
$.ajax({
url:"/testuname",
data:"uname="+uname,
type:"get",
dataType:"text",
success:function (result) {//通过参数来接受服务器返回的内容
$("#rs").html(result);
}
});
$.post("/testuname","uname="+uname,function (result) {
$("#rs").html(result);
});
$.get("/testuname","uname="+uname,function (result) {
$("#rs").html(result);
});
});
})
</script>
</head>
<body>
<h1>注册</h1>
用户名:<input type="text" id="username" name="uname"><span id="rs"></span>
</body>
</html>
数据处理页面就是上面的TestServlet.java
JSON
JSON (JavaScript Object Notation) 是一种轻量级的数据交换格式
JSON的定义
var 变量名 = {
“key” : value , // Number类型
“key2” : “value” , // 字符串类型
“key3” : [] , // 数组类型
“key4” : {}, // json 对象类型
“key5” : [{},{}] // json 数组
};
可以使用 变量名.key值 的方式访问json变量,
java与json之间的转换时用fastjson和gjson进行;
基础概念:
Serialization:序列化,使Java对象到Json字符串的过程。
Deserialization:反序列化,字符串转换成Java对象
Gson的两个基础方法
toJson();
fromJson();
Gson的创建方式一:直接new Gson对象
// 使用new方法
Gson gson = new Gson();
// toJson 将bean对象转换为json字符串
String jsonStr = gson.toJson(user, User.class);
// fromJson 将json字符串转为bean对象
Student user= gson.fromJson(jsonStr, User.class);
// **序列化List**
String jsonStr2 = gson.toJson(list);
// **反序列化成List时需要使用到TypeToken getType()**
List<User> retList = gson.fromJson(jsonStr2,new TypeToken<List<User>>(){}.getType());
Gson的创建方式二:使用GsonBuilder
使用new Gson(),此时会创建一个带有默认配置选项的Gson实例,如果不想使用默认配置,那么就可以使用GsonBuilder
//serializeNulls()是GsonBuilder提供的一种配置,当字段值为空或null时,依然对该字段进行转换
Gson gson = new GsonBuilder().serializeNulls().create();
使用GsonBuilder创建Gson实例的步骤:
首先创建GsonBuilder,然后调用GsonBuilder提供的各种配置方法进行配置,
最后调用GsonBuilder的create方法,将基于当前的配置创建一个Gson实例。
Gson gson = new GsonBuilder()
.excludeFieldsWithoutExposeAnnotation() //不对没有用@Expose注解的属性进行操作
.enableComplexMapKeySerialization() //当Map的key为复杂对象时,需要开启该方法
.serializeNulls() //当字段值为空或null时,依然对该字段进行转换
.setDateFormat("yyyy-MM-dd HH:mm:ss:SSS") //时间转化为特定格式
.setPrettyPrinting() //对结果进行格式化,增加换行
.disableHtmlEscaping() //防止特殊字符出现乱码
.registerTypeAdapter(User.class,new UserAdapter()) //为某特定对象设置固定的序列或反序列方式,自定义Adapter需实现JsonSerializer或者JsonDeserializer接口
.create();
Gosn对复杂Map的处理时需要用到其中的
enableComplexMapKeySerialization() 配置:
Gson gson = new GsonBuilder().enableComplexMapKeySerialization().create(); //开启复杂处理Map方法
Map<List<User>, String> map = new HashMap<List<User>, String>();
// TODO 向map中添加数据
String jsonStr = gson.toJson(map); //toJson
Map<List<User>, String> resultMap = gson.fromJson(jsonStr,new TypeToken<Map<List<User>, String>>() {}.getType()); //fromJson
如果Map的key为String,则可以不使用GsonBuilder的enableComplexMapKeySerialization()方法,或者直接new Gson();
Gson的注解:
@Expose注解
public class User {
@Expose
private String firstName;
@Expose(serialize = false)
private String lastName;
@Expose(deserialize = false)
private String emailAddress;
private String password;
}
@Expose中serialize和deserialize属性是可选的,默认两个都为true。
如果serialize为true,调用toJson时会序列化该属性,
如果deserialize为true,调用fromJson生成Java对象时不会进行反序列化。
注意:如果采用new Gson()方式创建Gson,@Expose没有任何效果。需要使用 gsonBuilder.excludeFieldsWithoutExposeAnnotation()方法。
Fast使用;
常用API:
public static final Object parse(String text);
// 把JSON文本parse为JSONObject或者JSONArray
public static final JSONObject parseObject(String text);
// 把JSON文本parse成JSONObject
public static final <T> T parseObject(String text, Class<T> clazz);
// 把JSON文本parse为JavaBean
public static final JSONArray parseArray(String text);
// 把JSON文本parse成JSONArray
public static final <T> List<T> parseArray(String text, Class<T> clazz);
//把JSON文本parse成JavaBean集合
public static final String toJSONString(Object object);
// 将JavaBean序列化为JSON文本
public static final String toJSONString(Object object, boolean prettyFormat);
// 将JavaBean序列化为带格式的JSON文本
public static final Object toJSON(Object javaObject);
//将JavaBean转换为JSONObject或者JSONArray。