浏览器的同源策略及跨域解决方案

同源策略

一个源的定义

如果两个页面的协议,端口(如果有指定)和域名都相同,则两个页面具有相同的

举个例子:

下表给出了相对http://a.xyz.com/dir/page.html同源检测的示例: 

URL结果原因
http://a.xyz.com/dir2/other.html成功 
http://a.xyz.com/dir/inner/another.html成功 
https://a.xyz.com/secure.html失败不同协议 ( https和http )
http://a.xyz.com:81/dir/etc.html失败不同端口 ( 81和80)
http://a.opq.com/dir/other.html失败不同域名 ( xyz和opq)

同源策略是什么

同源策略是浏览器的一个安全功能,不同源的客户端脚本在没有明确授权的情况下,不能读写对方资源。所以xyz.com下的js脚本采用ajax读取abc.com里面的文件数据是会被拒绝的。

同源策略限制了从同一个源加载的文档或脚本如何与来自另一个源的资源进行交互。这是一个用于隔离潜在恶意文件的重要安全机制。

不受同源策略限制的

1. 页面中的链接,重定向以及表单提交是不会受到同源策略限制的。

2. 跨域资源的引入是可以的。但是js不能读写加载的内容。如嵌入到页面中的<script src="..."></script>,<img>,<link>,<iframe>等。

JSONP解决跨域问题

1、JSONP原理分析

利用 浏览器加载静态资源的时候不限制跨域

<script src=""></script>

我们使用cdn方式引用的jQuery文件也是跨域的,它就可以使用。

同样是从其他的站点拿东西,script标签就可以。那我们能不能利用这一点搞点事情呢?

<!DOCTYPE HTML>
<html>
<head><meta charset="UTF-8"><meta http-equiv="x-ua-compatible" content="IE=edge"><meta name="viewport" content="width=device-width, initial-scale=1"><title>xyz</title>
</head>
<body>
<button id="b1">点我</button>
<script src="https://cdn.bootcss.com/jquery/3.3.1/jquery.js"></script>
<script>function rion() {console.log("选我不后悔!");}
</script>
<script src="http://127.0.0.1:8002/abc/"></script>
</body>
</html>

后端返回响应

def abc(request):return HttpResponse("rion()")

刷新页面,可以看到下面的结果。

这样就利用了浏览器加载静态资源的时候不限制跨域的特性,实现了跨域请求拿数据。

2.jQuery中的getJSON方法

jQuery中封装了专门的方法实现jsonp。

示例:

点击b1按钮发送jsonp请求到后端,然后后端返回数据。

html :

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Title</title>
</head>
<body>
<button id="b1">点我发送请求</button><script src="jquery.min.js"></script>
<script>// 点击b1按钮发送jsonp请求
    $('#b1').click(function () {// 使用jquery提供的getJSON方法请求获取数据,// callback=? 是固定格式,会创建一个随机的字符串作为callback的value。
        $.getJSON('http://127.0.0.1:8000/index/?callback=?',function (data) {console.log(data)})})
</script>
</body>
</html>

后端项目函数:

def index(request):data = {"name": "zwq", "age": 18}func_name = request.GET.get('callback')print(func_name) # jQuery3310589826002995957_1547112594072return HttpResponse('{}({})'.format(func_name,json.dumps(data)))

但JSONP有一定缺陷:

1.前后端都要支持

2.只能发GET请求

 CORS解决跨域问题

CORS是一个W3C标准,全称是"跨域资源共享"(Cross-origin resource sharing)。它允许浏览器向跨源服务器发出XMLHttpRequest请求,从而解决AJAX只能同源使用的限制。

CORS需要浏览器和服务器同时支持。目前基本上主流的浏览器都支持CORS。所以只要后端服务支持CORS,就能够实现跨域。

1.简单请求和非简单请求介绍

浏览器将CORS请求分成两类:简单请求(simple request)和非简单请求(not-so-simple request)。

一个请求需要同时满足以下两大条件才属于简单请求。

(1) 请求方法是以下三种方法之一:HEADGETPOST(2)HTTP的头信息不超出以下几种字段:AcceptAccept-LanguageContent-LanguageLast-Event-IDContent-Type:只限于三个值application/x-www-form-urlencoded、multipart/form-data、text/plain

2.简单请求的处理方式

在跨域场景下,当浏览器发送简单请求时,浏览器会自动在请求头中添加表明请求来源的 Origin 字段。

 

我们的后端程序只需要在返回的响应头中加上 Access-Control-Allow-Origin 字段,并且把该字段的值设置为 跨域请求的来源地址或简单的设置为 * 就可以了。

 例如:我们可以在Django中间件中的process_response方法来给相应对象添加该字段。

from django.utils.deprecation import MiddlewareMixinclass CORSMiddleware(MiddlewareMixin):# 处理简单请求的跨域请求def process_response(self, request, response):# 告诉浏览器来自这个源的请求是我允许的跨域请求# response['Access-Control-Allow-Origin'] = 'http://localhost:63342'# 给响应头加上 Access-Control-Allow-Origin 字段 并简单的设置为 *,表示所有跨域简单请求都放行response['Access-Control-Allow-Origin'] = '*'return response

非简单请求的处理方式

我们开发中常用到的那些请求方法是PUT或DELETE,或者Content-Type字段的类型是application/json的都是非简单请求。

对于非简单请求,浏览器通常都会在请求之前发送一次 OPTIONS 预检 请求。该请求会像后端服务询问是否允许从当前源发送请求并且询问允许的 请求方法 和 请求头字段

举个例子:

 我们前端使用axios向后端发送PUT请求,结果:

 

看看发送的具体请求:

 

解决办法也很简单,我们可以在后端简单的给响应对象添加上 常用请求方法(PUT、DELETE)的支持就可以了。

在上面Django的中间件中添加如下代码:

class CORSMiddleware(MiddlewareMixin):"""对所有跨域请求做放行处理"""def process_response(self, request, response):# 所有跨域简单请求都放行response['Access-Control-Allow-Origin'] = '*'if request.method == 'OPTIONS':# 告诉浏览器你发的非简单请求(修改了Content-type)我允许了response['Access-Control-Allow-Headers'] = 'Content-type'# 告诉浏览器 你发送PUT请求我也支持response['Access-Control-Allow-Methods'] = 'PUT, DELETE'return response

使用django-cors-headers

我们这个中间件确实能解决目前的CORS跨域问题,但是我们的方法肯定是不够严谨的,django有一个第三方包django-cors-headers。

安装:

pip install django-cors-headers

注册APP:

INSTALLED_APPS = [...'app01.apps.App01Config','corsheaders',  # 将 corsheaders 这个APP注册
]

添加中间件:

必须放在最前面,因为要先解决跨域的问题。只有允许跨域请求,后续的中间件才会正常执行。

MIDDLEWARE = ['corsheaders.middleware.CorsMiddleware',  # 添加中间件'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',
]

配置

可以选择不限制跨域访问

CORS_ORIGIN_ALLOW_ALL = True

或者可以选择设置允许访问的白名单

CORS_ORIGIN_ALLOW_ALL = False
CORS_ORIGIN_WHITELIST = (# '<YOUR_DOMAIN>[:PORT]','127.0.0.1:8080'
)

更多详细配置详细请查看django-cors-headers项目

 

转载于:https://www.cnblogs.com/zwq-/p/10252210.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/364306.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

计算机病毒及其防治评课,区初中信息技术教研活动公开课评课感想

今天上午&#xff0c;在我校成功举行了区初中信息技术教研活动&#xff0c;总共开设了三节课&#xff0c;都是由我校老师执教的。听后受益匪浅&#xff0c;感受颇深&#xff0c;以下是本人的评课感想。一、首先说一下三位老师的共同点&#xff1a;1、三位老师都用了导学案&…

Django—路由层,视图层

路由层urls 浏览器会自动给url后加一个“/” django会自动给路由的正则表达式前面加一个“/” django会给任何不带“/”结尾的url语句添加“/”&#xff08;可设置&#xff09; 短路路由规则&#xff1a;匹配到第一条就忽略后面所有&#xff01; 所以路由顺序很重要&#xff01…

分数怎么化成带分数_人教版五年级下册第4单元带分数及把假分数化成整数或带分数教学视频+知识点...

|点击题目下方蓝字一键关注 小学生知识库|【教学视频】分数的分类与互化【知识点】带分数的意义和特征&#xff1a;像…这样由整数和真分数合成的数叫做带分数。假分数化成整数或带分数的方法是什么&#xff1f;①当假分数的分子是分母的倍数时&#xff0c;这个假分数可以化成整…

Java 8功能教程– ULTIMATE指南(PDF下载)

编者注&#xff1a;在本文中&#xff0c;我们提供了全面的Java 8功能教程。 自Java 8公开发布以来已经有一段时间了&#xff0c;所有迹象都表明这是一个非常重要的版本。 我们在Java Code Geeks处提供了大量教程&#xff0c;例如“ 玩Java 8 – Lambda和并发” &#xff0c;“…

盆景

dvbbs收藏本页联系我们论坛帮助dvbbs恢复默认设置登录注册 搜索风格论坛状态论坛展区道具中心我能做什么 >> 优秀作品欣赏、个人作品展示。(The excellent work enjoys, personal work demonstration) 搜一搜相关精彩主题 盆景艺术在线论坛 → 盆景论坛(penjing Forum) →…

小程序左右标签滑块排行榜

小程序左右标签滑块排行榜 效果: <view class"menu"><view class"{{currentTab0?select:default}}" data-current"0" bindtap"switchNav">成绩</view><view class"{{currentTab1?select:default}}" …

微软Visual Studio2005开发工具路线图详解

微软Visual Studio2005开发工具路线图详解 随着企业需要的不断演变&#xff0c;Microsoft 依旧致力于提供创新的开发人员工具来满足这些不断变化的需求&#xff0c;从而确保客户的成功。为帮助组织规划未来的软件开发工作&#xff0c;Microsoft 提供了一个开发人员工具计划版本…

解决微信小程序的wx-charts插件tab切换时的显示会出现位置移动问题-tab切换时,图表显示错乱-实现滑动tab

解决Echarts在微信小程序tab切换时的显示会出现位置移动问题 tab切换时&#xff0c;图表显示错乱 <canvas class"kcanvas" canvas-id"ringCanvas" hidden"{{currentTab 1}}"></canvas> <view hidden"{{currentTab ! 1}}…

Java EE:基础知识

想要了解一些基本原则&#xff0c;即与Java EE相关的技术术语。 对于许多人来说&#xff0c;Java EE / J2EE仍然最多意味着Servlet&#xff0c;JSP或Struts。 没有冒犯或双关语&#xff01; 无论如何&#xff0c;这不是Java EE的“圣经”。 我没有能力写这样的东西&#xff01…

自定义鼠标样式

效果图展示&#xff1a; 代码 &#xff1a; <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><meta http-equiv&q…

微信小程序开发POST请求

微信小程序开发POST请求 wx.request( { url: "http://op.juhe.cn/onebox/weather/query", header: { "Content-Type": "application/x-www-form-urlencoded" }, method: "POST", //data: { cityname: "上海", key: &…

6.11python 作业

1.课堂例子: 01初识python #!/usr/bin/env python # -*- coding: utf-8 -*-# print(hello world!)print(hello world!) name lyj print(name)# id,type,value x 10 y 10 python小计数池(python优化机制):在变量值产生后指定的范围内&#xff0c;在内存中事先开辟一块内存空间…

linux下常用命令

创建软连接&#xff1a;ln -s b a //为b创建一个快捷方式a&#xff0c;只是一个镜像&#xff0c;不占用空间。 ln -sf b a //差不多 &#xff0c;-f强制执行 ln b a //创建硬链接&#xff0c;会占用相同的大小空间&#xff08;不允许给目录创建硬链接&#xff09; svn…

2012服务器系统关闭网络共享,提供网络服务的前提,Windows Server 2012如何更改高级共享设置...

今天介绍系统提供网络服务的前提&#xff0c;Windows Server 2012 R2操作系统如何更改高级共享设置。小伙伴们可能都听说&#xff0c;网络配置是提供各种网络服务的前提。Windows Server 2012 R2操作系统安装完成以后&#xff0c;默认为自动获取IP地址&#xff0c;自动从网络中…

Java中WeakReference,SoftReference,PhantomReference和Strong Reference之间的区别

很长一段时间以来&#xff0c;WeakReference和SoftReference都已添加到Java API中&#xff0c;但是并不是每个Java程序员都熟悉它。 这意味着在Java中使用WeakReference和SoftReference的位置和方法之间存在差距。 参考类对于垃圾收集的工作方式尤其重要。 众所周知&#xff0c…

css设置字符长度,在css中设置最大字符长度

12 个答案:答案 0 :(得分&#xff1a;199)你总是可以通过设置max-width和溢出ellipsis来使用截断方法p {white-space: nowrap;overflow: hidden;text-overflow: ellipsis;max-width: 200px;}对于多行截断&#xff0c;请查看flex解决方案。截断3行的示例。p {overflow: hidden;d…

关于html以及js相关格式验证的记录

验证的常见方式 我们在写前端的时候或多或少的会遇到一些验证格式问题&#xff0c;通常我们有三种解决办法。 第一种就是在输入完成后在输入框附近验证给出提示第二种就是在输入完成后在提交的时候排着验证提示第三张就是限制输入 前面两种我们都是非常的熟悉以及想到的&…

mysql重做日志_MySQL-重做日志 redo log -原理

【redo log buffer】【redo log file】-原理目录&#xff1a;1.重做日志写入过程图2.相关知识点汇总图3.redo_log_buffer 原理4.redo_log_file 原理1. 重做日志写入过程&#xff1a;2. 相关知识点汇总&#xff1a;3. redo log buffer 原理重做日志缓冲(redo log buffer)是Innod…

Java 8 Friday:使用Streams API时的10个细微错误

在Data Geekery &#xff0c;我们喜欢Java。 而且&#xff0c;由于我们真的很喜欢jOOQ的流畅的API和查询DSL &#xff0c;我们对Java 8将为我们的生态系统带来什么感到非常兴奋。 Java 8星期五 每个星期五&#xff0c;我们都会向您展示一些不错的教程风格的Java 8新功能&#…

mysql集群重启offline_mysql集群搭建问题及解决方法集锦

在上一篇博客中写了如何搭建mysql集群&#xff0c;之所以遇到这些问题&#xff0c;是因为刚开始弄mysql集群的时候不熟悉&#xff0c;正是因为这些问题&#xff0c;让我对mysql集群的了解渐渐深入&#xff0c;下面介绍在搭建mysql集群的时候我遇到了一些问题。1、mysql集群安装…