|
Django 解决 CORS 跨域问题
★ CORS 基本概念
- CORS(Cross-Origin Resource Sharing 跨域资源共享)是一种用于在Web浏览器中处理跨域请求的机制。跨域请求指的是在浏览器中,从一个域名的网页去请求另一个域名的资源。在默认情况下,浏览器限制了跨域请求,以保护用户的安全和隐私。
复制代码 ★ CORS 作用
- 浏览器采用了同源保护策略,为了防御恶意攻击,会检查Request消息与Response消息的域名 Domain与端口 Port,如果不相同,则表示响应消息与请求消息不是同源,可能是伪造的响应消息,因此浏览器添加了CORS限制功能,默认不接受非同源的响应消息。
复制代码 ★ CORS 工作机制
- CORS通过在服务器端设置响应头来允许跨域请求。当浏览器发起跨域请求时,服务器可以在响应头中添加一些特定的字段,告诉浏览器该请求是被允许的。这些字段包括Access-Control-Allow-Origin、Access-Control-Allow-Methods、Access-Control-Allow-Headers等。
- Access-Control-Allow-Origin: 指定了允许访问该资源的域名。可以设置为特定的域名,也可以设置为*表示允许任意域名访问。
- Access-Control-Allow-Methods: 指定了允许的HTTP方法,如GET、POST等。
- Access-Control-Allow-Headers: 指定了允许的请求头。
- 浏览器在收到服务器的响应后,会检查响应头中的CORS字段,如果与当前页面的域名匹配并且字段值符合要求,浏览器就会允许该跨域请求,并将响应返回给页面。
复制代码
- 说明
- 需要注意的是,CORS只在浏览器中起作用,不会影响非浏览器环境下的请求。此外,CORS并不能完全解决跨域问题,仍然需要其他安全措施来保护Web应用程序的安全性。
复制代码 ★ 解决CORS跨域请求的思路
- 方式一:通过自定义中间件修改Response头部
- 1-在 myproject/myapp/ 目录下,新建 middlewares.py 文件存放中间件
- class CorsMiddleware(object):
- """中间件:跨域访问"""
- def __init__(self, get_response):
- self.get_response = get_response
-
- def __call__(self, request):
- return self.get_response(request)
-
- # process_template_response(), process_response() 只能二选一、根据view的response类型,重载相应方法。
- def process_template_response(self,request,response):
- # 如果view 使用了render渲染response,使用这个中间件
- response["Access-Control-Allow-Origin"] = "*"
- return response
-
- def process_response(self,request,response):
- # 如果view使用HttpResponse, 将使用这个中间件
- response["Access-Control-Allow-Origin"] = "*"
- return response
复制代码 - 2-将新定义的中间件 CorsMiddleware 添加到 settings.py 的 MIDDLEWARE 的列表
- MIDDLEWARE = [
- 'django.middleware.security.SecurityMiddleware',
- 'django.contrib.sessions.middleware.SessionMiddleware',
- 'django.middleware.common.CommonMiddleware',
- 'django.middleware.csrf.CsrfViewMiddleware',
- 'django.contrib.auth.middleware.AuthenticationMiddleware',
- 'django.contrib.messages.middleware.MessageMiddleware',
- 'django.middleware.clickjacking.XFrameOptionsMiddleware',
- 'myapp.middlewares.CorsMiddleware', # 允许跨域访问中间件
- ]
复制代码 - 3-测试
- 操作说明
- 再次发起跨域的Ajax请求,可以成功接收到django的响应数据。使用浏览器DevTools检查Response响应头部参数,可以看到已经添加了Access-Control-Allow-Origin: *
复制代码 - 示例
- HTTP/1.1 200 OK
- Date: Sat, 21 Aug 2023 08:26:17 GMT
- Server: WSGIServer/0.2 CPython/3.11.4
- Content-Type: text/html; charset=utf-8
- Access-Control-Allow-Origin: *
- X-Frame-Options: DENY
- Content-Length: 5177
- Vary: Cookie
- X-Content-Type-Options: nosniff
- Referrer-Policy: same-origin
复制代码
- 总结
- 此方法虽然简单易行,Access-Control-Allow-Origin 设置为*, 允许任何跨域访问,显然不太安全,每次修改须更新代码,因此仅适用于开发测试环境。
复制代码
- 方式二:通过 django-cors-headers 库来实现 (生产环境下推荐使用)
- 1-安装
- pip install django-cors-headers
复制代码 - 2-修改 settings.py 配置文件
- 添加到应用列表
- INSTALLED_APPS = (
- ##...
- 'corsheaders'
- )
复制代码 - 添加中间件列表 corsheaders.middleware.CorsMiddleware
- MIDDLEWARE = [
- 'django.middleware.security.SecurityMiddleware',
- 'django.contrib.sessions.middleware.SessionMiddleware',
- 'django.middleware.common.CommonMiddleware',
- 'django.middleware.csrf.CsrfViewMiddleware',
- 'corsheaders.middleware.CorsMiddleware',
- ......
复制代码 - 添加允许访问的域名
- 允许所有域名访问
- CORS_ORIGIN_ALLOW_ALL = True
复制代码 - 允许指定的域访问
- CORS_ORIGIN_ALLOW_ALL = False
- # 允许域名加入白名单
- CORS_ORIGIN_WHITELIST = (
- 'http//:localhost:8000',
- )
复制代码
★ 总结
- 在测试环境中,可以允许所有domain来访问,以避免 CORS问题,前后端分离项目在生产环境下,通常应该部署在同域下,
- 如果确实需要跨域,则将前端域名添加到白名单 CORS_ORIGIN_WHITELIST配置项中,禁止其它域访问。
复制代码 来源:https://www.cnblogs.com/cs-songbai/p/18249319
免责声明:由于采集信息均来自互联网,如果侵犯了您的权益,请联系我们【E-Mail:cb@itdo.tech】 我们会及时删除侵权内容,谢谢合作! |
|