STAGE02-DAY19-AJAX

历史回顾

监听器(Listener)

监听器是实现了特殊监听接口的类,功能是用来监听作用域的创建、销毁、值的变化及类与session的关系。

一组:监听创建与销毁ServletContext、reqeust、session  3个

二组:监听值的变化  3个

三组:监听类与session的关系--是否绑定对象(要求对象上实现接口),是否钝化与活化

 

过滤器(Filter)

过滤器是实现了Filter接口的类,功能是拦截请求。

AJAX

Ajax 即“Asynchronous Javascript And XML”(异步 JavaScript 和 XML),是指一种创建交互式网页应用的网页开发技术。

Ajax = 异步 JavaScript 和 XML 或者是 HTML(标准通用标记语言的子集)。

Ajax 是一种用于创建快速动态网页的技术。

Ajax 是一种在无需重新加载整个网页的情况下,能够更新部分网页的技术。

通过在后台与服务器进行少量数据交换,Ajax 可以使网页实现异步更新。这意味着可以在不重新加载整个网页的情况下,对网页的某部分进行更新。

传统的网页(不使用 Ajax)如果需要更新内容,必须重载整个网页页面。

 

表单数据提交

a连接数据提交

javascript数据提交

以上三种都需要请求后台但是如果想更新数据必须刷新网页,Ajax完美解决了这个问题。

生活中的例子:如点赞,弹幕等局部实时更新的网页都会用到Ajax技术

原生Ajax--纯js写的Ajax

http://www.w3school.com.cn/ajax/ajax_xmlhttprequest_create.asp

原生AJAX需要借助 XMLHttpRequest 对象实现

原生ajax使用步骤:

  1. 创建一个XMLHttpRequest对象
  2. 调用open并传递三个参数:请求方式、url、true
  3. 发送(send)这个请求
  4. 定义获取返回状态的方法onreadystatechange
  5. 判断这个状态4为成功
  6. 从Response响应主体中获取返回的信息。Ajax获取信息只能通过响应来获得,不能直接从作用域中拿值,且这个响应只能响应一次。如果没有Ajax,response响应的时候会直接显示在网页上,当有Ajax的时候,相当于Ajax拦截了这个响应并为自己所用。

错误:

1.print不能用write只能用print,不然会出现乱码

2.获得返回值时需要定义函数xhr.onreadystatechange=function(){},xhr这边是属性,没有括号

3.var value = xhr.responseText也是属性,后面没有括号

4.JS给文本赋值是 .innerText=,jQuery是 .text=

5.原生js脚本中的选择器不要#.  jQuery和css需要使用,不要搞混了,否则没有结果!!

6.servlet中的pw一定要放在else的外面,否则第一个缺失!!!

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>焰灵姬</title>
<script type="text/javascript">
	function point(){
		//1.创建XMLHTTPRequest对象
		var xhr = new XMLHttpRequest();
		//2.调用xhr的open方法并为其传参
		xhr.open("post","MyServlet",true);//第一个参数为发送方法,第二个为URL,第三个为true
		//3.发送
		xhr.send();
		//4.定义函数,获得返回值
		xhr.onreadystatechange = function(){
		//5.判断返回状态是否为4,是的话就是正常的,可以进行赋值操作
			if(xhr.readyState == 4){
				var value = xhr.responseText;
				//6.赋值
				document.getElementById("sp").innerText = value;
			}
		}
	}
</script>
</head>
<body>
	<img alt="网速不好图片显示不出来的时候显示,或者鼠标移上去的时候显示" src="pic/1.png" width="70%"><br>
	获得点赞次数为:<span id="sp"></span>次!<span></span><br>
	<input type="button" id="bu" value="点赞" onclick="point()">
</body>
</html>
package servlet;

import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.ServletContext;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

@WebServlet("/MyServlet")
public class MyServlet extends HttpServlet{

	private static final long serialVersionUID = 1L;
	@Override
	protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		/*首先我们假定一个作用域,服务器级别的,这样除非关闭服务器,否则点赞数会一直存在,符合实际,
		专门用来存放点赞数,如果值为null的话说明还未创建,我们就创建这个作用域并赋值为0 */
		PrintWriter pw = response.getWriter();//Ajax只能通过响应的方式获取值,其他方式不行
		
		ServletContext context = this.getServletContext();
		
		int num = 1;//初始化变量,这个变量用以记录点赞次数
		
		Object object = context.getAttribute("con");
		
		
		//判断
		if(null == object) {
			context.setAttribute("con", 1);
			num=1;
		}else {
			num = (int)object;//一开始我们需要判断是不是null,所以不能一开始就转型,判断完成之后我们可以给他转成int了
			num++;//每次点赞都+1
			context.setAttribute("con", num);
			System.out.println("点赞次数为:"+num);
		}
		pw.print(num);//一定要放到外面,否则打印不到第一个了!!!!!!!!!!
	}
}

 

jQuery ajax

作为JavaScript一个类库,必然也会有响应的ajax的功能,jQuery认为原生ajax过于复杂,所以进行了一次封装(jQuery的二次封装)。 共定义3种书写ajax的方式。

 

要求:

先导入jQuery类库。也叫脚本文件。

语法:顺序可以不一致

$.ajax({
	url:"",
	data:{},//书写Jason格式的值
	type:"",
	dataType:"",
	success:function(){},//书写函数
	error:function(){}//,书写函数,注意最后一个没有分号  ;
});

解析:

$.ajax:声明使用的jQuery ajax语法结构  $.ajax({.......})

url: 请求的地址

data: 需要发送的数据{} 里面书写json格式的数据 {名字:值,名字:值}

type: 请求类型 get/post

dataType:声明返回数据(响应主体中)的类型/格式

success:执行成功之后调用的方法 等同于 xhr.readyState = 4

error: 执行不等于4 调用的方法。 如果没有错误error可以省略

注意事项:

  1. 注意不要写错单词。
  2. ajax严格区分大小写。
  3. 冒号一定是英文的。
  4. ajax中书写的每一项结尾都要跟随逗号除最后一个!!!
  5. dataType  T要大写。
  6. $.ajax内的选项不区分顺序

 

第一种:$.ajax({...})

注意:三种写法中,只有这个括号中是带大括号的。

servlet代码不变,jsp代码如下

注意,function()括号内传参,逗号不要漏掉!!

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>ajax的jQuery简写格式1</title>
<script type="text/javascript" src="js/jquery-3.3.1.min.js"></script>
<script type="text/javascript">
	$(function(){//就绪函数
		$("#bu").click(function(){//绑定事件
			$.ajax({
				url:"MyServlet",
				data:{},
				dataType:"text",
				type:"post",
				success:function(num){//函数为有参函数,括号里传值,这个值就是我们用pw响应到页面的值
					document.getElementById("sp").innerText = num;
				},//注意逗号不要漏了!!!
				error:function(){
					alert("ajax错误");
				}
			});
		});
	});
</script>
</head>
<body>
	<img alt="网速不好图片显示不出来的时候显示,或者鼠标移上去的时候显示" src="pic/1.png" width="70%"><br>
	获得点赞次数为:<span id="sp"></span>次!<span></span><br>
	<input type="button" id="bu" value="点赞">
</body>
</html>

第二种:$.get();

格式为$.get( url, data, success ,dataType )  顺序固定,但是没有值的时候可以省略不写,否则报错,写的时候直接写值就好不用写标签名,这里只是指定位置。

注意:

1.get()括号后直接跟内容,没有大括号!!!

2.jQuery赋值:$("#id").text(值) 不用等于号,直接在text后括号内给值

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>get方法</title>
<script type="text/javascript" src="js/jquery-3.3.1.min.js"></script>
<script type="text/javascript">
	$(function(){
		$("#bu").click(function(){
			$.get(
				"MyServlet", //url
				//{},//data
				function(num){//success
					$("#sp").text(num);
				},
				"text"//dataType
			);
		});
	});
</script>
</head>
<body>
	<img alt="网速不好图片显示不出来的时候显示,或者鼠标移上去的时候显示" src="pic/1.png" width="70%"><br>
	获得点赞次数为:<span id="sp"></span>次!<span></span><br>
	<input type="button" id="bu" value="点赞">
</body>
</html>

第三种:$.post();

post 格式为 $.get( url, data, success ,dataType ) 

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>ajax简化-post</title>
<script type="text/javascript" src="js/jquery-3.3.1.min.js"></script>
<script type="text/javascript">
	$(function(){
		$("#bu").click(function(){
			$.post(
				"MyServlet",
				//{},  位置不能乱,但是值没有可以省略不写
				function(num){
					$("#sp").text(num);
				},
				"text"
			);
		});
	});
</script>
</head>
<body>
	<img alt="网速不好图片显示不出来的时候显示,或者鼠标移上去的时候显示" src="pic/1.png" width="70%"><br>
	获得点赞次数为:<span id="sp"></span>次!<span></span><br>
	<input type="button" id="bu" value="点赞">
</body>
</html>

 

AJAX可以返回的数据类型

XML:早期AJAX都用XML传输数据(被JSON取代)

text:文本格式,字符串格式(所有数据都能用这种格式接收)

HTML:可以直接返回HTML代码

script:脚本代码

JSON:当今最流行的数据回交互方式

JSONP:也是JSON格式,但是支持跨域访问。

JSON

错误的地方:注意  返回值类型 "json"  一定要写在$.get();  $.post();的括号里面,否则不生效,默认的是text,会直接当成字符串输出,写的时候为了防止犯错,在写完get/post 后直接在括号后加  以区分。

 

JSON是一种数据的格式,本质就是一个特殊格式的字符串。 JSON格式的数据也可以直接使用text去接收。

JSON(JavaScript Object Notation, JS 对象简谱) 是一种轻量级的数据交换格式。它基于 ECMAScript (欧洲计算机协会制定的js规范)的一个子集,采用完全独立于编程语言的文本格式来存储和表示数据。简洁和清晰的层次结构使得 JSON 成为理想的数据交换语言。 易于人阅读和编写,同时也易于机器解析和生成,并有效地提升网络传输效率。

 

使用AJAX的时候所有JSON返回类型的数据,只要格式正确默认都已经将返回的字符串转化成了对象。可以直接操作这个对象。只要是对象就可以  .   只要是数组就可以遍历

 

第一种格式:数组格式

[2,3,4,5,6]

首先我们测试以text格式输出:得到一个字符串,只能进行字符串相关操作,比如取0下标的值,返回的会是 "[" 而不是2

STAGE02-DAY19-AJAX

下面我们测试以json格式输出:得到一个数组对象,可以进行根据下标取值等操作。

STAGE02-DAY19-AJAX

第二种格式:键值对格式(对象格式),常规的JSON格式

{"name":"张三","age":49}

STAGE02-DAY19-AJAX

STAGE02-DAY19-AJAX

第三种格式:混合模式,对象的数组

json中的遍历:for(var i in obj){ ...... }

[{"name":"张三","age":49},{"name":"李四","age":3}]

STAGE02-DAY19-AJAX

第四种格式:可以支持直接返回boolean值

STAGE02-DAY19-AJAX

JSON转化工具

jsonlib  比较常见一种转化工具,通用但是功能不是特别强大

fastjson 这个工具功能很强大,但是在Hibernate框架中转化会出现异常。解决不彻底(死循环)。

jackson 我们一般用这种工具。是一个将对象、集合、数据等各种数据格式转化为JSON字符串的一个工具。

使用的时候需要导三个包。STAGE02-DAY19-AJAX

 

测试一:数组类型不需要转化直接打印回去即可。

测试二:转化对象

方法:

  1. 定义一个对象映射器  ObjectMapper mapper = new ObjectMapper();
  2. 将对象传入writeValueAsString(obj)方法中,得到字符串,以便json传递  String values1 = mapper.writeValueAsString(s1);

STAGE02-DAY19-AJAX

STAGE02-DAY19-AJAX

测试三:转化集合

方法基本和上面一样

STAGE02-DAY19-AJAX

STAGE02-DAY19-AJAX

AJAX进阶之Error回调函数

只有程序在发生错误的才会执行error回调,如果程序没问题,是不执行。STAGE02-DAY19-AJAX

error回调函数中有三个参数

XMLHttpRequest : 原生Ajax的核心对象| 在jQuery1.5之后简写jqXHR

textState :返回异常的文本标识

errorThrown :返回ajax抛出异常信息

STAGE02-DAY19-AJAX

STAGE02-DAY19-AJAX

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

@WebServlet("/MyJackson")
public class MyJackson extends HttpServlet {

	private static final long serialVersionUID = 1L;

	@Override
	protected void service(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
		PrintWriter pw = response.getWriter();
		pw.print("hhh");
	}
}
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
<script type="text/javascript" src="js/jquery-3.3.1.min.js"></script>
<script type="text/javascript">
	$(function(){
		$("#bu").click(function(){
			$.ajax({
				url:"",//第三个报错的原因,加上Servlet地址即可,最后行数是0代表没错
				data:{},
				dataType:"json",//第二个出错的原因,解析错误,如果改成text即可消除错误
				type:"post",
				success:function(){
					alert("成功");
				},
				error:function(XMLHttpRequest ,textState ,errorThrown ){
					alert("XMLHttpRequest"+XMLHttpRequest);
					alert("textState"+textState);
					alert("errorThrown"+errorThrown);
				}
			});
		});
	});
</script>
</head>
<body>
	<input type="button" id="bu" value="json">
</body>
</html>

XMLHttpRequest

1.5之后使用jqXHR 代替

这个参数对象中有两个方法

第一个获取当前执行的步骤状态代码

 

jqXHR.readyState

 

状态码含义:

0  未初始化成功

1  ajax正在发送请求

2  ajax已经请求至后台

3  解析返回的数据  

4  数据已经成功返回。

 

status 直接返回响应状态码

200 (成功)

404

500....

textState

返回异常的文本状态

error:服务器内部发生错误(伴随500产生) 说直白点就是Java类错了

parseerror 解析异常。(检查ajax返回类型)

timeout:请求超时、响应超时。

null : 这个后台的错误太奇葩为定义这个返回文本状态

errorThrown

返回ajax部分执行的异常

只有ajax部分的异常才能返回,Java类中的异常是不能返回的。

STAGE02-DAY19-AJAX