阮一峰:浏览器同源政策及其规避方法
同源政策:同协议、同域名、同端口
阮一峰:ajax教程
ajax用XMLHttpRequest向后端发送请求,但是AJAX无法跨源
json语法;通过JSON.parse(string)将后端返回的字符串转换成JS对象
jsonp动态添加script标签实现跨域请求,但jsonp只能发送GET请求
CORS跨域,支持所有请求
json
JSON 指的是 JavaScript 对象表示法(JavaScript Object Notation)
JSON 使用 Javascript语法来描述数据对象
- JS 是一门语言,JSON 是另一门语言
- json这门语言是道格拉斯抄袭js的语言
- JSON 使用 Javascript语法来描述数据对象
- 道格拉斯还写了本《javascript语言精粹》,俗称蝴蝶书,来吐槽js中垃圾的地方
json铁轨图
json语法
{"a":1,"name":"stage","age":24}
json里的【字符串】必须用双引号,不能用单引号!!
json没有undefined
和function
| js数据 | json数据 |
| :—-: |:———:|
| 123| 123 |
| ‘stage’| “stage” |
| true| true |
| [‘a’, ‘b’] | [“a”, “b”] |
| {name: ‘stage’} | {“name”: “stage”} |
| null | null |
| undefined| json没有undefined |
| function fn(){}| json没有function |
浏览器同源策略
- 同协议
- 同域名
- 同端口
举例来说,http://www.example.com/d/page.html
这个网址,
协议是http://
,
域名是www.example.com
,
端口是80
(http默认端口80,https默认端口443)。
不刷新页面,使用xhr发送请求局部更新数据:AJAX
AJAX - 异步的 JavaScript 和 XML
AJAX就是使用XMLHttpRequest技术向服务端发送请求
AJAX 是一种在无需重新加载整个网页的情况下,能够更新部分网页的技术。
AJAX 最大的优点是在不重新加载整个页面的情况下,可以与服务器交换数据并更新部分网页内容。
- 使用
XMLHttpRequest
发请求 - 服务器返回
JSON
格式的字符串(后来人们不用XML,改用JSON了) - JS 解析
JSON
(通过JSON.parse(字符串) 将JSON格式的字符串转成JS对象),并更新局部页面1234567891011121314var xhr = new XMLHttpRequest();xhr.open('GET', '/', true);xhr.onreadystatechange = function() {if (this.readyState == 4) {if (this.status >= 200 && this.status < 400) {// 成功!var string = this.responseText;var obj = JSON.parse(string);} else {// 失败 _(:з」∠)_}}};xhr.send();
AJAX无法跨域
同源政策规定,AJAX请求只能发给同源的网址,否则就报错。
只有 协议 + 域名 + 端口 完全一模一样才能发AJAX请求
如何解决AJAX无法跨域的问题?↓↓↓
跨域方法:jsonp
由于同源策略,我们无法从别的域名(网站)那获取数据,用jsonp可以解决这个问题。
JsonP(JSON with Padding) 是 json 的一种”使用模式”,可以让网页从别的域名(网站)那获取数据,即跨域读取数据。
它的基本思想是,网页通过动态添加<script>
标签,<script>
标签的src
向跨域服务器请求JSON数据,同时传一个查询参数callback=随机名&时间戳
,这种做法不受同源政策限制;服务器收到请求后,将数据放在一个指定名字的回调函数里传回来。
上面代码通过动态添加<script>
标签,向服务器example.com
发出请求。注意,该请求的查询字符串有一个callback参数,用来指定回调函数的名字(一般用随机数),这对于JSONP是必需的。此外还需要加一个时间戳,防止浏览器的缓存。
由于<script>
标签请求的脚本会直接作为代码运行。这时,只要浏览器定义了名字为随机数的函数,该函数就会立即调用。于是请求方就能获得他要的数据。
jsonp面试题
- 什么是jsonp
JSONP(JSON with Padding) 是 json 的一种”使用模式”,可以让网页从别的域名(网站)那获取数据,即跨域读取数据。
它的基本思想是:
- 网页通过动态添加
<script>
标签,<script>
标签的src
向服务器请求数据,同时传一个查询参数callback=随机名&时间戳
给服务器,这种做法不受同源政策限制
- 服务器收到请求后,将数据放在一个指定名字的回调函数里传回来。
- 由于
<script>
标签请求的脚本会直接作为代码运行。这时,只要浏览器定义了对应名字的函数,该函数就会立即调用。 - 于是请求方就能获得他要的数据。
- jsonp为什么不支持post方法
因为jsonp是通过动态创建<script>
标签实现的,而script只能通过GET请求数据,不能POST
由于jsonp只能发GET请求,于是又有了CORS跨域
↓↓↓
CORS跨源AJAX请求
当使用ajax访问远程服务器时,请求失败,浏览器报No 'Access-Control-Allow-Origin' header
解决方案:后端程序员添加response.setHeader("Access-Control-Allow-Origin", "*");
CORS是跨源资源分享(Cross-Origin Resource Sharing)的缩写。它是W3C标准,是跨域AJAX请求的根本解决方法。
CORS允许浏览器向跨源服务器,发出XMLHttpRequest
请求,从而克服了AJAX只能同源使用的限制。
相比JSONP只能发GET
请求,CORS允许任何类型的请求。
|
|
或者前端程序员设置将ajax请求中的dataType属性设置为“jsonp”,jsonp是专门用来解决跨域访问而诞生的。
chrome调试
在用submit提交数据时,页面会刷新,因此:chrome开发者工具 → Network → Network → 点击preserve log(页面刷新时不清楚日志)