1.Ajax异步刷新
Ajax的工作流程
Jsp页面通过js向服务器(servlet)发送请求获取到数据,将数据获取到js中,js将数据显示到jsp页面中(document来操作element),最后以HTML的形式响应给浏览器。
原生ajax(js实现的ajax)
实现思路
Jsp的元素绑定事件——>调用js的函数——>创建xmlhttprequest对象——>发送请求到servlet(服务器的文件)——>获取请求 赋值给html元素(document)
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Ajax获取服务器文件内容</title>
</head>
<body>
<div align="center">
<span id="mess"></span>
<button id="but" onclick="ajax01()">获取外部文件内容</button>
</div>
<script type="text/javascript">
function ajax01(){
//创建 xmlhttprequest对象 ie
var xmlhttprequest;
if(window.XMLHttpRequest){ //不是ie浏览器
xmlhttprequest=new XMLHttpRequest();
}else{//是ie浏览器
xmlhttprequest=new ActiveXObject("Microsoft.XMLHTTP")
}
//编写请求方式
/*
* method:请求的类型;GET 或 POST
*url:文件在服务器上的位置 也可以是servlet
*async:true(异步)或 false(同步)
*/
xmlhttprequest.open("GET","message.txt",true)
//发送请求
xmlhttprequest.send()
//获取响应数据 根据响应的状态码来进行判断
/*存有 XMLHttpRequest 的状态。从 0 到 4 发生变化。
0: 请求未初始化
1: 服务器连接已建立
2: 请求已接收
3: 请求处理中
4: 请求已完成,且响应已就绪
status
200: "OK"
404: 未找到页面
**/
var count=0;
xmlhttprequest.onreadystatechange=function(){
count++;
alert("我是请求状态改变"+count);
//当 readyState 等于 4 且状态为 200 时,表示响应已就绪:
if(xmlhttprequest.readyState==4 && xmlhttprequest.status==200){
//获取响应的内容 赋值给element元素
var message=xmlhttprequest.responseText;
// alert(message);
//赋值
document.getElementById("mess").innerHTML="<h1>"+message+"</h1>"
}
}
}
</script>
</body>
</html>
想要去Java程序中获取数据,就先编写servlet,将得到的结果通过下面代码相应到界面
PrintWriter writer = response.getWriter();
//可用print和write方法,print()可传递Object类型的,write()只能传递字符,字符数组,字符串,整型
writer.print(stulist);
2.Json介绍
Json是json对象的另外一种展示存储方式,其实就是一个特殊类型的字符串
Json的语法
{ “键” : “值” } 键值必须都是字符串的
键和值都必须加上" "
key(键)必须为字符串型,value(值)字符串, 数字, 对象, 数组, 布尔值或 null
//json数据创建
var json1={"name":"张三","age":20};
alert(json1.name);
//创建json对象数组
var json2=[
{"name":"张三","age":20},
{"name":"李四","age":18}
]
alert(json2[1].age);
//创建json属性对象
var json3={
"stu1":{"name":"张三","age":20},
"stu2":{"name":"李四","age":18}
}
alert(json3.stu1.age);
//创建json属性的数组对象
var json4={
"stu1":[{"name":"张三","age":20},
{"name":"李四","age":18}]
}
alert(json4.stu1[1].age);
Json字符串与js的转换
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Ajax</title>
</head>
<body>
<script>
//json转换为js
var obj1= JSON.parse('{"name":"张三","age":20}');
alert(obj1.name);
//js对象转换为json字符串
var obj2=JSON.stringify({name:"张三",age:20});
alert(obj2);
</script>
</body>
</html>
模糊查询示例
JSP部分代码
<%@ 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>
</head>
<body>
<div align="center">
请输入查询的相关内容:<input type="text" id="like"/>
<button onclick="likeselect()">查询</button>
<table border="1px" cellpadding="0px" cellspacing="0px">
<tr>
<th>编号</th>
<th>姓名</th>
<th>性别</th>
<th>年龄</th>
<th>班级编号</th>
<th>班级名称</th>
</tr>
<tbody id="stubody">
</tbody>
</table>
</div>
<script>
function likeselect(){
var likename=document.getElementById("like").value;
var xml;
if(window.XMLHttpRequest){
xml=new XMLHttpRequest();
}else{
xml=new ActiveXObject("Microsoft.XMLHTTP");
}
//打开资源
xml.open("GET","JsonStudent?likename="+likename,"true");
//发送请求
xml.send();
//如果为post请求,则需更改如下
/*
*xml.open("POST","PostAjaxServlet","true");
*xml.setRequestHeader("Content-type","application/x-www-form-urlencoded");
*xml.send("likename="+likename);
*/
xml.onreadystatechange=function(){
if(xml.readyState==4&&xml.status==200){
//获取请求内容
var stu=xml.responseText;
//将json对象转换为js对象
var jsonstu=eval("("+stu+")");
var str="";
for(var i=0;i<jsonstu.length;i++){
str+="<tr>\r\n" +
" <td>"+jsonstu[i].id+"</td>\r\n" +
" <td>"+jsonstu[i].name+"</td>\r\n" +
" <td>"+jsonstu[i].sex+"</td>\r\n" +
" <td>"+jsonstu[i].age+"</td>\r\n" +
" <td>"+jsonstu[i].c_id+"</td>\r\n" +
" <td>"+jsonstu[i].c_name+"</td>\r\n" +
" </tr>";
}
document.getElementById("stubody").innerHTML=str;
}
}
}
</script>
</body>
</html>
servlet部分代码
package com.xingyun.Servlet;
import java.io.IOException;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.List;
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 com.slxy.slxyDao.StudentinforDao;
import com.slxy.slxyImp.Studentinfor;
import com.xingyun.bean.Student;
import net.sf.json.JSONArray;
/**
* Servlet implementation class JsonStudent
*/
@WebServlet("/JsonStudent")
public class JsonStudent extends HttpServlet {
private static final long serialVersionUID = 1L;
/**
* @see HttpServlet#HttpServlet()
*/
public JsonStudent() {
super();
// TODO Auto-generated constructor stub
}
/**
* @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse response)
*/
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
//设置字符编码
request.setCharacterEncoding("utf-8");
response.setCharacterEncoding("utf-8");
String likename = request.getParameter("likename");
List<Student> list=new ArrayList<Student>();
StudentinforDao stu=new Studentinfor();
list = stu.like(likename);
//将集合转换为JSONArray对象
JSONArray stulist = JSONArray.fromObject(list);
PrintWriter writer = response.getWriter();
writer.print(stulist);
}
/**
* @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse response)
*/
protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
// TODO Auto-generated method stub
doGet(request, response);
}
}
结果
jquery的方式实现ajax
jquery基础语法:
基础语法: $(selector).action()
jQuery是js的封装 ,js操作在jQuery中封装为一系列的函数。
五种实现方法:
Ajax load get post getjson
Ajax中的属性
async 是否异步
type 请求方式
url 请求路径
success 请求成功的操作
beforeSend 请求之前的操作
data 请求的数据
erro 请求出错时的操作
Ajax的get请求
//Ajax的get请求方式
function ajaxget01() {
//给元素绑定事件
$("#but").click(function() {
//使用Ajax函数
$.ajax({
//请求方式
type: "get",
//请求资源路径
url: "AjaxServlet?id=1000",
//异步刷新
async: true,
//请求之前触发的事件
beforeSend: function() {
alert("请求之前触发的事件");
},
success: function(data) {
//请求成功之后的操作
$("sp").html(data);
},
erro: function() {
//请求错误之后的操作
alert("请求错误");
}
});
});
}
Ajax的post请求
//Ajax的post请求方法
function ajaxpost() {
$("#but").click(function() {
$.ajax({
type: "post",
url: "AjaxServlet",
async: true,
//post方法传值方式
data: {
"id": 1000
},
success: function(data) {
$("#sp").html(data);
}
});
});
}
load方式
//load方法
function loadmethod() {
$("#but").click(function() {
//Load 直接加载内容到指定元素
$("#sp").load("AjaxServlet", "id=20", function() {
$("#pic").html("<img src='nba.jpg'/>");
});
});
}
get方式的两种写法
//get请求方法一
function get01() {
$("#but").click(function() {
$.get("AjaxServlet?id=10", function(status, data) {
$("#sp").html(status + "-----" + data);
});
});
}
//get请求方法二
function get02() {
$("#but").click(function() {
$.get({
url: "AjaxServlet?id=100",
success: function(data, status) {
alert(data + "----" + status);
}
})
});
}
post方式的两种写法
//post请求方法一
function post01() {
$("#but").click(function() {
$.post("AjaxServlet", "id=30", function(status, data) {
$("#sp").html(status + "-----" + data);
});
});
}
//post请求方式二
function post02() {
$("#but").click(function() {
$.post({
url: "AjaxServlet",
data: "id=40",
success: function(status, data) {
$("#sp").html(status + "-----" + data);
}
});
});
}
json方式
//JSON方式
function json() {
$("#but").click(function() {
$.getJSON("AjaxServlet", "id=18", function(data) {
$("#sp").html(data.name+"----"+data.id);
});
});
}
Ajax实现跨域请求
跨域问题来源于JavaScript的"同源策略",即只有 协议+主机名+端口号 (如存在)相同,则允许相互访问。也就是说JavaScript只能访问和操作自己域下的资源,不能访问和操作其他域下的资源。跨域问题是针对JS和ajax的,html本身没有跨域问题。
判断是否跨域
http://www.abc.com/a/b 调用 http://www.abc.com/d/c(非跨域)
http://www.abc.com/a/b 调用 http://www.def.com/a/b (跨域:域名不一致)
http://www.abc.com:8080/a/b 调用 http://www.abc.com:8081/d/c (跨域:端口不一致)
http://www.abc.com/a/b 调用 https://www.abc.com/d/c (跨域:协议不同)
注意:localhost和127.0.0.1虽然都指向本机,但也属于跨域。
如何解决跨域请求???
(1)响应头添加Header允许访问
在被访问的servlet中添加以下代码:
response.addHeader(“Access-Control-Allow-Origin”,”*”);//允许所有来源访问
此方式只能针对jsp、servlet。
(2)内部转发的形式
① httpClient内部转发 代理模式
//创建默认连接
CloseableHttpClient client=HttpClients.createDefault();
//创建Http对象,处理get请求
HttpGet get=new HttpGet("http://192.168.1.70:8080/Servlet09--jqueryAjax/ajax.txt");
//执行
CloseableHttpResponse resp=client.execute(get);
//获取状态码
int code=resp.getCode();
if(code==200) {
try {
//获取返回结果
String result=EntityUtils.toString(resp.getEntity());
System.out.println("跨域请求结果为:"+result);
response.getWriter().write(result);
//关闭资源
resp.close();
client.close();
} catch (ParseException | IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
② 使用url
Ajax ——>内部自己的servlet ——>外部不同域的文件
//获取资源路径
URL url=new URL("http://192.168.1.70:8080/Servlet09--jqueryAjax/ajax.txt");
URLConnection con = url.openConnection();
InputStream input = con.getInputStream();
byte[] bytes=new byte[input.available()];
//读取资源存入字节数组
input.read(bytes);
String str=new String(bytes);
response.getWriter().write(str);
跨域请求
在同一个Tomcat中部署多个项目 使用不同端口号
步骤:
- 将webapps赋复制一份
- 将项目的war包分别放到两个文件夹下webapps和新的webapps(newwebapps)
- 修改conf下的server.xml文件,添加一个业务
- ①将新的业务中的Service标签中的name重新起名;
②Connector标签中的port重新修改为新的端口号,例如:“8081”;
③Host标签中的appBase修改为新的部署的项目名字newwebapps。
//原有的
<Service name="Catalina">
<!--The connectors can use a shared executor, you can define one or more named thread pools-->
<!--
<Executor name="tomcatThreadPool" namePrefix="catalina-exec-"
maxThreads="150" minSpareThreads="4"/>
-->
<!-- A "Connector" represents an endpoint by which requests are received
and responses are returned. Documentation at :
Java HTTP Connector: /docs/config/http.html (blocking & non-blocking)
Java AJP Connector: /docs/config/ajp.html
APR (HTTP/AJP) Connector: /docs/apr.html
Define a non-SSL/TLS HTTP/1.1 Connector on port 8080
-->
<Connector port="8080" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
<!-- A "Connector" using the shared thread pool-->
<!--
<Connector executor="tomcatThreadPool"
port="8080" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
-->
<!-- Define a SSL/TLS HTTP/1.1 Connector on port 8443
This connector uses the NIO implementation that requires the JSSE
style configuration. When using the APR/native implementation, the
OpenSSL style configuration is required as described in the APR/native
documentation -->
<!--
<Connector port="8443" protocol="org.apache.coyote.http11.Http11NioProtocol"
maxThreads="150" SSLEnabled="true" scheme="https" secure="true"
clientAuth="false" sslProtocol="TLS" />
-->
<!-- Define an AJP 1.3 Connector on port 8009 -->
<Connector port="8009" protocol="AJP/1.3" redirectPort="8443" />
<!-- An Engine represents the entry point (within Catalina) that processes
every request. The Engine implementation for Tomcat stand alone
analyzes the HTTP headers included with the request, and passes them
on to the appropriate Host (virtual host).
Documentation at /docs/config/engine.html -->
<!-- You should set jvmRoute to support load-balancing via AJP ie :
<Engine name="Catalina" defaultHost="localhost" jvmRoute="jvm1">
-->
<Engine name="Catalina" defaultHost="localhost">
<!--For clustering, please take a look at documentation at:
/docs/cluster-howto.html (simple how to)
/docs/config/cluster.html (reference documentation) -->
<!--
<Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster"/>
-->
<!-- Use the LockOutRealm to prevent attempts to guess user passwords
via a brute-force attack -->
<Realm className="org.apache.catalina.realm.LockOutRealm">
<!-- This Realm uses the UserDatabase configured in the global JNDI
resources under the key "UserDatabase". Any edits
that are performed against this UserDatabase are immediately
available for use by the Realm. -->
<Realm className="org.apache.catalina.realm.UserDatabaseRealm"
resourceName="UserDatabase"/>
</Realm>
<Host name="localhost" appBase="webapps"
unpackWARs="true" autoDeploy="true">
<!-- SingleSignOn valve, share authentication between web applications
Documentation at: /docs/config/valve.html -->
<!--
<Valve className="org.apache.catalina.authenticator.SingleSignOn" />
-->
<!-- Access log processes all example.
Documentation at: /docs/config/valve.html
Note: The pattern used is equivalent to using pattern="common" -->
<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs"
prefix="localhost_access_log" suffix=".txt"
pattern="%h %l %u %t "%r" %s %b" />
</Host>
</Engine>
</Service>
//以下是新增加的service
//新name
<Service name="newCatalina">
<!--The connectors can use a shared executor, you can define one or more named thread pools-->
<!--
<Executor name="tomcatThreadPool" namePrefix="catalina-exec-"
maxThreads="150" minSpareThreads="4"/>
-->
<!-- A "Connector" represents an endpoint by which requests are received
and responses are returned. Documentation at :
Java HTTP Connector: /docs/config/http.html (blocking & non-blocking)
Java AJP Connector: /docs/config/ajp.html
APR (HTTP/AJP) Connector: /docs/apr.html
Define a non-SSL/TLS HTTP/1.1 Connector on port 8080
-->
//新端口8081
<Connector port="8081" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
<!-- A "Connector" using the shared thread pool-->
<!--
<Connector executor="tomcatThreadPool"
port="8080" protocol="HTTP/1.1"
connectionTimeout="20000"
redirectPort="8443" />
-->
<!-- Define a SSL/TLS HTTP/1.1 Connector on port 8443
This connector uses the NIO implementation that requires the JSSE
style configuration. When using the APR/native implementation, the
OpenSSL style configuration is required as described in the APR/native
documentation -->
<!--
<Connector port="8443" protocol="org.apache.coyote.http11.Http11NioProtocol"
maxThreads="150" SSLEnabled="true" scheme="https" secure="true"
clientAuth="false" sslProtocol="TLS" />
-->
<!-- Define an AJP 1.3 Connector on port 8009 -->
<Connector port="8009" protocol="AJP/1.3" redirectPort="8443" />
<!-- An Engine represents the entry point (within Catalina) that processes
every request. The Engine implementation for Tomcat stand alone
analyzes the HTTP headers included with the request, and passes them
on to the appropriate Host (virtual host).
Documentation at /docs/config/engine.html -->
<!-- You should set jvmRoute to support load-balancing via AJP ie :
<Engine name="Catalina" defaultHost="localhost" jvmRoute="jvm1">
-->
<Engine name="Catalina" defaultHost="localhost">
<!--For clustering, please take a look at documentation at:
/docs/cluster-howto.html (simple how to)
/docs/config/cluster.html (reference documentation) -->
<!--
<Cluster className="org.apache.catalina.ha.tcp.SimpleTcpCluster"/>
-->
<!-- Use the LockOutRealm to prevent attempts to guess user passwords
via a brute-force attack -->
<Realm className="org.apache.catalina.realm.LockOutRealm">
<!-- This Realm uses the UserDatabase configured in the global JNDI
resources under the key "UserDatabase". Any edits
that are performed against this UserDatabase are immediately
available for use by the Realm. -->
<Realm className="org.apache.catalina.realm.UserDatabaseRealm"
resourceName="UserDatabase"/>
</Realm>
//appBase 新业务加载war生成项目的位置
<Host name="localhost" appBase="newwebapps"
unpackWARs="true" autoDeploy="true">
<!-- SingleSignOn valve, share authentication between web applications
Documentation at: /docs/config/valve.html -->
<!--
<Valve className="org.apache.catalina.authenticator.SingleSignOn" />
-->
<!-- Access log processes all example.
Documentation at: /docs/config/valve.html
Note: The pattern used is equivalent to using pattern="common" -->
<Valve className="org.apache.catalina.valves.AccessLogValve" directory="logs"
prefix="localhost_access_log" suffix=".txt"
pattern="%h %l %u %t "%r" %s %b" />
</Host>
</Engine>
</Service>
</Server>
在同一Tomcat下可以请求到不同域中的内容。