跨域1-CORS跨域
1.跨域:
请求的资源和当前网站的,协议/域名/端口 不一样,会发起跨域HTTP请求
2.为什么会跨域
出于安全原因,浏览器限制从脚本内发起的跨源HTTP请求。 例如,XMLHttpRequest和Fetch API遵循同源策略。
只能从同一个域中请求HTTP资源,除非使用CORS头文件。
3.如何跨域:
CORS(cross origin resource share),跨域(源)资源共享
a. CORS 需要客户端和服务器同时支持。目前,所有浏览器都支持该机制。
4.CORS跨域:
a.概述
跨域资源共享标准新增了一组 HTTP 首部字段,允许服务器声明哪些源站有权限访问哪些资源。另外,规范要求,对那些可能对服务器数据产生副作用的 HTTP 请求方法(特别是 GET 以外的 HTTP 请求,或者搭配某些 MIME 类型的 POST 请求),浏览器必须首先使用 OPTIONS 方法发起一个预检请求(preflight request),从而获知服务端是否允许该跨域请求。服务器确认允许之后,才发起实际的 HTTP 请求。在预检请求的返回中,服务器端也可以通知客户端,是否需要携带身份凭证(包括 Cookies 和 HTTP 认证相关数据)
b.简单请求:某些请求不会触发 CORS 预检请求。本文称这样的请求为“简单请求”
简单请求条件:
使用方法:GET/POST/OPTION 使用的首部字段集合:
Accept
Accept-Language
Content-Language
Content-Type (需要注意额外的限制)
DPR
Downlink
Save-Data
Viewport-Width
Width Content-Type的值仅限于:
text/plain
multipart/form-data
application/x-www-form-urlencoded
sample:
站点http://a.example 的网页应用想访问http://b.example 的资源,
http://a.example 的网页中包含的代码: var request = new XMLHttpRequest();
var url = 'http://b.example/resources/public-data/'; function callOtherDomain() {
if(request) {
request.open('GET', url, true);
request.onreadystatechange = handler;
request.send();
}
}
使用 Origin 和 Access-Control-Allow-Origin 就能完成最简单的访问控制。本例中,服务端返回的 Access-Control-Allow-Origin: * 表明,该资源可以被任意外域访问。如果服务端仅允许来自 http://a.example 的访问,该首部字段的内容如下: Access-Control-Allow-Origin: http://a.example
c. 预检请求
“需预检的请求”要求必须首先使用 OPTIONS 方法发起一个预检请求到服务器,以获知服务器是否允许该实际请求。"预检请求“的使用,可以避免跨域请求对服务器的用户数据产生未预期的影响。
当请求满足下述任一条件时,即应首先发送预检请求:
使用了下面任一 HTTP 方法:
PUT
DELETE
CONNECT
OPTIONS
TRACE
PATCH 人为设置了对 CORS 安全的首部字段集合之外的其他首部字段。该集合为:
Accept
Accept-Language
Content-Language
Content-Type (but note the additional requirements below)
DPR
Downlink
Save-Data
Viewport-Width
Width Content-Type 的值不属于下列之一:
application/x-www-form-urlencoded
multipart/form-data
text/plain
sample
var invocation = new XMLHttpRequest();
var url = 'http://bar.other/resources/post-here/';
var body = '<?xml version="1.0"?><person><name>Arun</name></person>'; function callOtherDomain(){
if(invocation)
{
invocation.open('POST', url, true);
invocation.setRequestHeader('X-PINGOTHER', 'pingpong');
invocation.setRequestHeader('Content-Type', 'application/xml');
invocation.onreadystatechange = handler;
invocation.send(body);
}
}
1.首先使用OPTIONS发起预检请求,预检请求中同时携带了下面两个首部字段:
Origin: http://foo.example
Access-Control-Request-Method: POST
Access-Control-Request-Headers: X-PINGOTHER
首部字段 Access-Control-Request-Method 告知服务器,实际请求将使用 POST 方法。首部字段 Access-Control-Request-Headers 告知服务器,实际请求将携带两个自定义请求首部字段:X-PINGOTHER 与 Content-Type。服务器据此决定,该实际请求是否被允许。
2.服务器响应预检请求
Access-Control-Allow-Origin: http://foo.example
Access-Control-Allow-Methods: POST, GET, OPTIONS
Access-Control-Allow-Headers: X-PINGOTHER, Content-Type
Access-Control-Max-Age: 86400
首部字段 Access-Control-Allow-Methods 表明服务器允许客户端使用 POST, GET 和 OPTIONS 方法发起请求。
首部字段 Access-Control-Allow-Headers 表明服务器允许请求中携带字段 X-PINGOTHER 与 Content-Type。
最后,首部字段 Access-Control-Max-Age 表明该响应的有效时间为 86400 秒,也就是 24 小时。在有效时间内,浏览器无须为同一请求再次发起预检请求。浏览器自身维护了一个最大有效时间,如果该首部字段的值超过了最大有效时间,将不会生效。
3.附带身份凭证的请求
对于跨域 XMLHttpRequest 或 Fetch 请求,浏览器不会发送身份凭证信息。如果要发送凭证信息,需要设置 XMLHttpRequest 的某个特殊标志位
sample
本例中,http://foo.example 的某脚本向 http://bar.other 发起一个GET 请求,并设置 Cookies:
var request = new XMLHttpRequest();
var url = 'http://bar.other/resources/credentialed-content/';
function callOtherDomain(){
if(request) {
request.open('GET', url, true);
request.withCredentials = true;
request.onreadystatechange = handler;
request.send();
}
}
XMLHttpRequest 的 withCredentials 标志设置为 true,从而向服务器发送 Cookies。如果服务器端的响应需要携带 Access-Control-Allow-Credentials: true ,浏览器将把响应内容返回给请求的发送者。
注意:
对于附带身份凭证的请求,服务器不得设置 Access-Control-Allow-Origin 的值为“*”,请求中的origin
d.HTTP 响应首部字段
Access-Control-Allow-Origin:
Access-Control-Allow-Origin: <origin> | *
origin 参数的值指定了允许访问该资源的外域 URI
Access-Control-Expose-Headers
跨域访问时,XMLHttpRequest对象的getResponseHeader()方法只能拿到一些最基本的响应头,Cache-Control、Content-Language、Content-Type、Expires、Last-Modified、Pragma,如果要访问其他头,则需要服务器设置本响应头
Access-Control-Max-Age
指定了preflight请求的结果能够被缓存多久
Access-Control-Allow-Credentials
指定了当浏览器的credentials设置为true时是否允许浏览器读取response的内容。
Access-Control-Allow-Methods
首部字段用于预检请求的响应。其指明了实际请求所允许使用的 HTTP 方法。
Access-Control-Allow-Headers
首部字段用于预检请求的响应。其指明了实际请求中允许携带的首部字段。
e.HTTP 请求首部字段
Origin 首部字段表明预检请求或实际请求的源站。
origin 参数的值为源站 URI。它不包含任何路径信息,只是服务器名称。
注意,不管是否为跨域请求,ORIGIN 字段总是被发送。
Access-Control-Request-Method
Access-Control-Request-Method 首部字段用于预检请求。其作用是,将实际请求所使用的 HTTP 方法告诉服务器。
Access-Control-Request-Headers
首部字段用于预检请求。其作用是,将实际请求所携带的首部字段告诉服务器。
跨域1-CORS跨域的更多相关文章
- JSONP跨域和CORS跨域
什么是跨域? 跨域:指的是浏览器不能执行其它网站的脚本,它是由浏览器的同源策略造成的,是浏览器的安全限制! 同源策略 同源策略:域名.协议.端口均相同. 浏览器执行JavaScript脚本时,会检查这 ...
- JSONP跨域和CORS跨域的区别
跨域: 由于浏览器中的javascript的同源策略,同源策略会阻止一个域的JavaScript脚本和另一个域的内容进行交互. 同源:协议,域名,端口,三者有一个不同即为跨域. 解决跨域有以下多种方法 ...
- 什么是同源策略,什么是跨域,如何跨域,Jsonp/CORS跨域
同源策略 同源策略(Same origin policy)是一种约定,它是浏览器最核心也最基本的安全功能,如果缺少了同源策略,则浏览器的正常功能可能都会受到影响. 可以说Web是构建在同源策略基础之上 ...
- ajax跨域通过 Cors跨域资源共享 进行GetPost请求
using System; using System.Collections.Generic; using System.Linq; using System.Net; using System.Ne ...
- 配置tomcat允许跨域访问,cors跨域资源共享
1.导入cors-filter-1.7.jar,java-property-utils-1.9.jar两个jar包 2.在web.xml里配上: <filter> <filter-n ...
- Web APi之手动实现JSONP或安装配置Cors跨域(七)
前言 照理来说本节也应该讲Web API原理,目前已经探讨完了比较底层的Web API消息处理管道以及Web Host寄宿管道,接下来应该要触及控制器.Action方法,以及过滤器.模型绑定等等,想想 ...
- Web API 实现JSONP或者安装配置Cors跨域
前言 照理来说本节也应该讲Web API原理,目前已经探讨完了比较底层的Web API消息处理管道以及Web Host寄宿管道,接下来应该要触及控制器.Action方法,以及过滤器.模型绑定等等,想想 ...
- Asp.Net WebApi 启用CORS跨域访问指定多个域名
1.后台action指定 EnableCors指定可访问的域名多个,使用逗号隔开 //支持客户端凭据提交,指定多个域名,使用逗号隔开 [EnableCors("http://localhos ...
- django上课笔记7-jQuery Ajax 和 原生Ajax-伪造的Ajax-三种Ajax上传文件方法-JSONP和CORS跨域资源共享
一.jQuery Ajax 和 原生Ajax from django.conf.urls import url from django.contrib import admin from app01 ...
- Django框架12 /同源、跨域、CORS
Django框架12 /同源.跨域.CORS 目录 Django框架12 /同源.跨域.CORS 1. 同源策略 2. 跨域 3. 解决跨域:CORS/跨域资源共享 1. 同源策略 同源策略(Same ...
随机推荐
- js判断字段是否为空 isNull
js判断字段是否为空 isNull //在js中if条件为null/undefined/0/NaN/""表达式时,统统被解释为false,此外均为true .//为空判断函数f ...
- 关于使用 myeclipse连接MySql的问题
配置Hibernate.cfg.xml测试连接Mysql数据库时老是报错,如下图: 想想这样配置也没有错啊,可是一直测试连接不上.后面上查了一下,需要在连接字符串后面加上?serverTimezone ...
- ansible常用模块用法
ansible常用模块用法 2015-07-21 10:25 24458人阅读 评论(1) 收藏 举报 分类: Linux(44) ansible 版权声明:本文为博主原创文章,未经博主允许不得 ...
- 用http请求一直失败,用https开头就ok了
今天晚上在调试新浪的程序,发现之前一直可以用的接口,有时候就会失败, 各项参数全部仔细核对,都没有发现任何不同之处,真是奇了怪了. 后来一看,post 的部分,之前是用 http:// 开头的,但是此 ...
- C#中简单操作SQLserver数据库(ADO.NET的简单应用)
本篇文章以 ADO.NET 访问SQL SERVER 数据库为例, 其中需用System.Data.SqlClient; 数据库连接字符串写法为:server=数据源(服务器名称);uid=用户名;p ...
- 学习笔记:spark Streaming的入门
spark Streaming的入门 1.概述 spark streaming 是spark core api的一个扩展,可实现实时数据的可扩展,高吞吐量,容错流处理. 从上图可以看出,数据可以有很多 ...
- SSM面试题
一.Spring面试题 1.Spring 在ssm中起什么作用? Spring:轻量级框架 作用:Bean工厂,用来管理Bean的生命周期和框架集成. 两大核心: 1.IOC/DI(控制反转/依赖注入 ...
- 关于mdb数据库在插入过程中报错->Syntax error in INSERT INTO statement.(sql语句没问题)
今天,在做mdb数据库的增删改查的时候,代码报错插入语句有问题,但是在数据库中正常执行,苦苦探索了多次,终于找到了问题所在. 结果如图: 上面是报错 下面是解决方案 解决方案:主要原因是offic ...
- 关于E-R图
E-R图 简介: E-R图也称实体-联系图(Entity Relationship Diagram),提供了表示实体类型.属性和联系的方法.用来描述现实世界的概念模型.它是描述现实世界概念结构模型的有 ...
- java的几种模式以及如何实现的
创建Bean实例的方式: 1) 通过构造器(有参或无参) 方式: <bean id="" class=""/> 2) 通过静态工厂方法 方式: &l ...