跨域问题详解

【一】介绍

# 1 浏览器同源策略
	-同源策略(Same origin policy)是一种约定,它是浏览器最核心也最基本的安全功能
    -请求的url地址,必须与浏览器上的url地址处于同域上,也就是域名(www.xx.com),端口(80,8080),协议(ftp,https,http)相同.
	-浏览器上就会报错,个就是同源策略的保护
    
    
# 2 浏览器的安全策略
	-访问一个跨域[域名,端口,协议不同]接口---》后端正常执行--》浏览器拦截了
    -只有web端需要处理跨域,小程序,app都不需要
    
# 3 解决跨域问题
	-cors :咱们使用的,后端配置
    -JSONP:忽略
    -nginx代理跨域(服务器代理)
    -vue 代理(开发阶段)
    
    
# 4  CORS(跨域资源共享)简介
CORS需要浏览器和服务器【响应头加东西】同时支持。目前,所有浏览器都支持该功能

整个CORS通信过程,都是浏览器自动完成,不需要用户参与。对于开发者来说,CORS通信与同源的AJAX通信没有差别,代码完全一样。浏览器一旦发现AJAX请求跨源,就会自动添加一些附加的头信息,有时还会多出一次附加的请求,但用户不会有感觉。

因此,实现CORS通信的关键是服务器。只要服务器实现了CORS接口,就可以跨源通信


# 5 cors 两种请求
	-简单请求:请求一次--》直接发送--》服务的处理了cors--》顺利返回--》如果服务的没处理就报错
   
    -非简单请求:先发一次options请求--》服务的如果处理了cors--》再发真正的请求-》如果服务端没处理,它就不发了
  
#  6 简单和非简单区别
	# 符合下面两个条件就是简单请求
	- 请求方法是以下三种方法之一:
        HEAD
        GET
        POST
    -HTTP的头信息不超出以下几种字段:
        Accept
        Accept-Language
        Content-Language
        Last-Event-ID
        Content-Type:只限于三个值application/x-www-form-urlencoded、multipart/form-data、text/plain
        
            
# 7 解决简单请求跨域

【二】自定义中间件处理跨域

  • 简单请求和非简单请求
## 中间件###
from django.utils.deprecation import MiddlewareMixin
class CorsMiddleWare(MiddlewareMixin):
    def process_response(self,request,response):
        if request.method=="OPTIONS":
            #可以加*
            response["Access-Control-Allow-Headers"]="*"
            response['Access-Control-Allow-Methods'] = '*'
        response["Access-Control-Allow-Origin"] = "*"
        return response

# 配置文件配置##
MIDDLEWARE = [
    'utils.common_middleware.CorsMiddleWare'
]

【三】第三方app解决跨域问题

# 1、使用pip安装
pip install django-cors-headers

# 2、添加到setting的app中
INSTALLED_APPS = (
	...
	'corsheaders',
	...
)
# 3、添加中间件
MIDDLEWARE = [  
	...
	'corsheaders.middleware.CorsMiddleware',
	...
]
# 4、setting下面添加下面的配置
CORS_ORIGIN_ALLOW_ALL = True
CORS_ALLOW_METHODS = (
	'DELETE',
	'GET',
	'OPTIONS',
	'PATCH',
	'POST',
	'PUT',
	'VIEW',
)

CORS_ALLOW_HEADERS = (
	'XMLHttpRequest',
	'X_FILENAME',
	'accept-encoding',
	'authorization',
	'content-type',
	'dnt',
	'origin',
	'user-agent',
	'x-csrftoken',
	'x-requested-with',
	'Pragma',
	'token',
)


### 中间件源码分析
if conf.CORS_ALLOW_ALL_ORIGINS and not conf.CORS_ALLOW_CREDENTIALS:
    response[ACCESS_CONTROL_ALLOW_ORIGIN] = "*"
if request.method == "OPTIONS":
            response[ACCESS_CONTROL_ALLOW_HEADERS] = ", ".join(conf.CORS_ALLOW_HEADERS)
            response[ACCESS_CONTROL_ALLOW_METHODS] = ", ".join(conf.CORS_ALLOW_METHODS)
posted @ 2024-05-27 12:05  -半城烟雨  阅读(0)  评论(0编辑  收藏  举报