简介
CORS是一个W3C标准,全称是"跨域资源共享"(Cross-origin resource sharing)。
它允许浏览器向跨源服务器,发出XMLHttpRequest请求,从而克服了AJAX只能同源使用的限制。
CORS详细介绍请点击《跨域资源共享 CORS 详解》
示例
说明
本示例将使用原始HttpServlet的方式来实现,能更加清晰的理解该协议。第三方框架(如Spring framework 4.2以上版本可通过注解@CrossOrigin设置跨域)大多实现了该协议,简单配置即可使用,不再赘述。
可利用内网穿透的方式(如:http://xxx.xxx.com/Cors/index)访问主页,并设置ajax请求为http://localhost:8080/Cors/corsTest访问测试接口。以达到模拟跨域测试的目的。或者开启两个端口不同的Tomcat,如多加8081,可从8081的页面访问8080接口进行跨域测试。
相关代码如下
测试页面
<html>
<title>Cors Test</title>
<style type="text/css">
.container {
display: flex;
align-items: center; /* 垂直居中 */
justify-content: center; /* 水平居中 */
}
.container div {
width: 100px;
height: 100px;
}
</style>
<body class="container">
<font id="msg" size="20px" color="red"></font>
<button onclick="todo();"
style="width: 200px; height: 50px; background: #FF6666; color: white">跨域测试</button>
</body>
</html>
<script src="http://libs.baidu.com/jquery/2.1.1/jquery.min.js"></script>
<script>
function todo() {
var xmlhttp = new XMLHttpRequest();
//简单请求
xmlhttp.open("GET", "http://localhost:8080/Cors/corsTest", false);
//非简单请求
//xmlhttp.open("POST","http://localhost:8080/Cors/corsTest", false);
//xmlhttp.setRequestHeader('Content-Type',"application/json");
try {//此处通过捕获异常的方式判断跨域的成功或失败有误!
xmlhttp.send();
var corsText = xmlhttp.responseText;
console.log(corsText);
$('#msg').html(corsText);
} catch (e) {
console.log("跨域请求失败");
$('#msg').html("跨域请求失败");
}
}
</script>
页面接口
package com.back.cors;
import java.io.IOException;
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("/index")
public class Index extends HttpServlet {
private static final long serialVersionUID = 1L;
public Index() {
super();
}
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
request.getRequestDispatcher("/WEB-INF/index.html").forward(request, response);
}
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
在接口上设置跨域
package com.back.cors;
import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
* 在接口上设置跨域
*
* @author Back
*
*/
@WebServlet("/corsTest")
public class Cors extends HttpServlet {
private static final long serialVersionUID = 1L;
public Cors() {
super();
}
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
// 取消下一行注释即可跨域请求。
// response.addHeader("Access-Control-Allow-Origin", "*");
// response.addHeader("Access-Control-Expose-Headers","Access-Control-Allow-Origin");
response.setCharacterEncoding("utf-8");
response.setContentType("text/html;charset=utf-8");
response.getWriter().println("简单请求-跨域请求成功!");
}
protected void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
// 需在请求头的ContentType设置为application/json,模拟非简单请求
response.setCharacterEncoding("utf-8");
response.setContentType("application/json;charset=utf-8");
response.getWriter().println("{\"msg\",\"非简单请求-跨域请求成功!\"}");
}
}
在过滤器里设置跨域
package com.back.filter;
import java.io.IOException;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletResponse;
/**
* 在过滤器里设置跨域
*
* @author Back
*
*/
@WebFilter(urlPatterns = "/*")
public class CrosFilter implements Filter {
@Override
public void destroy() {
// TODO Auto-generated method stub
}
@Override
public void doFilter(ServletRequest arg0, ServletResponse arg1, FilterChain arg2)
throws IOException, ServletException {
HttpServletResponse response = (HttpServletResponse) arg1;
// 非简单请求因需要预检,但是预检不进入方法,因此只能在过滤器设置跨域
// 简单或非简单均需要该字段
response.addHeader("Access-Control-Allow-Origin", "*");
//非简单请求
//response.addHeader("Access-Control-Allow-Headers", "Content-Type");
arg2.doFilter(arg0, arg1);
}
@Override
public void init(FilterConfig arg0) throws ServletException {
// TODO Auto-generated method stub
}
}
本文由 Administrator 创作,采用 知识共享署名4.0 国际许可协议进行许可
本站部分文章采集自互联网,因某些原因未注明出处,如有侵权,请留言告知。