Cors跨域访问

Http协议访问资源需要符合同源策略,同源策略[same origin policy]是浏览器的一个安全功能, 同源策略是浏览器安全的基石。同源就是必须访问的域名与端口号完全相同。例如下面例子

http://test.com与http?/test.com:81不同源
http://test.com与http?/a.test.com不同源
http://test.com/a.html与http://test.com/b.html同源

互联网应用系统需要高可用和高并发,架构设计需要将也分解到不同的域名,再通过Nginx代理统一起来,这样不可避免地处理不同源间系统访问。为了解决这个问题,提出了跨源资源共享,即 CORS(Cross-Origin Resource Sharing)。

CORS实现原理
传统的Http协议头信息包括:
Accept
Accept-Language
Content-Language
Last-Event-ID
Content-Type

CORS扩展了头信息:
Origin:
Access-Control-Allow-Origin:
Access-Control-Allow-Methods:
Access-Control-Allow-Headers:
Access-Control-Allow-Credentials:
Access-Control-Max-Age:

CORS跨域访问有两种访问方式,一是直接访问,在HTTP请求头上添加Origin字段(记录本域名),如果访问的服务器允许此域名CORS访问,在响应头上添加如下字段
Access-Control-Allow-Origin: http://mydomain1.com
Access-Control-Allow-Methods: GET, POST, PUT, DELETE
Access-Control-Allow-Headers: X-Custom-Header
Access-Control-Allow-Credentials: true
Access-Control-Max-Age: 1728000
如果不允许此域名CORS访问,不需要添加上述响应头信息。

二是间接范围,首先发生一个OPTION请求询问服务器端是否运行本域名跨域访问,如果允许访问返回响应头信息
Access-Control-Allow-Origin: http://mydomain1.com
Access-Control-Allow-Methods: GET, POST, PUT, DELETE
Access-Control-Allow-Headers: X-Custom-Header
Access-Control-Allow-Credentials: true
Access-Control-Max-Age: 1728000

测试不同源Ajax访问结果

mydomain1.com域名下的页面使用Ajax访问mydomain2.com域名下的服务,系统提示错误

mydomain1.com的JSP

<%@page language="java" contentType="text/html; charset=UTF-8"%>
<html>
<head>
<script src="http://libs.baidu.com/jquery/2.1.1/jquery.min.js"></script>

<script>

$(document).ready(function(){ 
   $.ajax({
        type: "get",
        async: false,
        url: "http://mydomain2.com/myjsonp.jsp?city=BeiJing",
        dataType: "jsonp",
        jsonp: "callback",//获取jsonp回调函数名的参数名
        jsonpCallback:"showName2",//自定义的jsonp回调函数名称,必须非空,默认为jQuery自动生成的随机函数名
        success: function(json){
    		var len = json.colleges.length;
    		var str = '';
    		for(var i=0;i<len;i++)
    			str = str + json.colleges[i] +',';
            alert('名称=' + json.name + ' 国家=' + json.country + ' 大学='+str);
        },
        error: function(){
            alert('fail');
        }
    });
});


function doclick()
{
	   $.ajax({
	        type: "get",
	        async: false,
	        url: "http://mydomain2.com/test",
	        success: function(data){
	        	for(var i=0;i<data.length;i++)
	        	{
	    			$('#testdiv').append('<li>'+data[i]+'</li>');
	        	}
	        },
	        error: function(){
	            alert('fail');
	        }
	    });
}
</script>

</head>
<body>
<h2>Hello World!</h2>
<input type="button" value="Test Cors" onclick="doclick()"/>
<div id="testdiv"></div>
</body>
</html>

mydomain2.com下的Controller

package com.gf;

import java.util.ArrayList;
import java.util.List;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

@Controller
public class TestCtrl {
	

	@RequestMapping("/test")
	@ResponseBody
	public List<String> test()
	{
		List<String> lst = new ArrayList<String>();
		lst.add("Java");
		lst.add("Python");
		lst.add("NodeJS");
		return lst;
	}
}

范围结果,出现跨域错误
在这里插入图片描述

SpringBoot服务端添加跨域访问支持

package com.gf;

import java.util.ArrayList;
import java.util.List;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

@Controller
public class TestCtrl {
	
	@CrossOrigin(origins = {"http://mydomain1.com", "null"})
	@RequestMapping("/test")
	@ResponseBody
	public List<String> test()
	{
		List<String> lst = new ArrayList<String>();
		lst.add("Java");
		lst.add("Python");
		lst.add("NodeJS");
		return lst;
	}
}

结果
在这里插入图片描述

为Controller所有方法添加跨域访问支持

package com.gf;

import java.util.ArrayList;
import java.util.List;

import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.CrossOrigin;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

@CrossOrigin(origins = {"http://mydomain1.com", "null"})
@Controller
public class TestCtrl {
	
	@RequestMapping("/test")
	@ResponseBody
	public List<String> test()
	{
		List<String> lst = new ArrayList<String>();
		lst.add("Java");
		lst.add("Python");
		lst.add("NodeJS");
		return lst;
	}
}

为全部Controller设置跨域支持

package com.gf;

import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.CorsRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurerAdapter;

@Configuration
public class WebMvcConfig extends WebMvcConfigurerAdapter {

    @Override
    public void addCorsMappings(CorsRegistry registry) {
        registry.addMapping("/**")
                .allowedOrigins("*")
                .allowedMethods("POST", "GET", "PUT", "OPTIONS", "DELETE")
                .maxAge(3600)
                .allowCredentials(true);
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值