同源政策是在客户端网络应用(比如网络浏览器)上实施的安全政策,用于防止来自不同来源的资源之间发生交互。虽然这种安全措施可用于防止恶意行为,但也可能会阻止已知来源之间开展的合法交互。例如,example.appspot.com
上托管的页面中的脚本可能需要使用 Cloud Storage 存储桶(网址为 example.storage.googleapis.com
)中存储的资源。但是,由于浏览器会将它们视为两个不同的来源,因此不允许来自 example.appspot.com
的脚本从 example.storage.googleapis.com
提取资源。
跨域资源共享 (CORS) 规范是由万维网联盟 (W3C) 制定的,该规范旨在克服这一限制。Cloud Storage 支持此规范,这意味着,它允许您将存储桶配置为支持 CORS。在之前的示例中,您可以配置 example.storage.googleapis.com
存储桶,以便浏览器与来自 example.appspot.com
的脚本共享该存储桶的资源。
如需详细了解 CORS 配置组件,请参阅设置存储桶 CORS。
CORS 的工作原理
CORS 请求分为两种类型:简单请求和预检请求。简单请求可以直接发出。预检请求必须先向服务器发送初步“预检”请求以获得许可,然后才可以继续发出主请求。如果满足以下任何一种情况,系统将对请求执行预检:
- 请求使用的是
GET
、HEAD
或POST
以外的方法。 - 请求使用
POST
方法且Content-Type
不是text/plain
、application/x-www-form-urlencoded
或multipart/form-data
。 - 请求设置了自定义标头,例如
X-PINGOTHER
。
当浏览器向 Cloud Storage 发出简单请求时,会发生以下过程:
浏览器将
Origin
标头添加到请求中。Origin
标头包含相应资源(该资源在寻求共享 Cloud Storage 存储桶的资源)的来源,例如Origin:https://www.example.appspot.com
。Cloud Storage 将请求的 HTTP 方法以及
Origin
标头的值与目标存储桶的 CORS 配置中的方法和来源信息进行比较,以查看是否存在匹配项。如果存在匹配项,Cloud Storage 将在响应中包含Access-Control-Allow-Origin
标头。Access-Control-Allow-Origin
标头包含初始请求的Origin
标头的值。浏览器接收响应并检查
Access-Control-Allow-Origin
值是否与原始请求中指定的网域匹配。如果它们匹配,则请求成功。如果它们不匹配,或者响应中不存在Access-Control-Allow-Origin
标头,则请求失败。
预检请求首先执行以下步骤。如果成功,则它将执行与简单请求相同的过程:
浏览器发送一个
OPTIONS
请求(包含主请求的Requested Method
和Requested Headers
)。Cloud Storage 使用目标资源允许的 HTTP 方法和标头的值进行响应。如果预检请求中的任何方法或标头值未包含在目标资源允许的方法和标头集合中,请求将失败,并且不会发送主请求。
上文是对 CORS 进行的精简介绍。如需查看更完整的说明,请参阅提取规范。
Cloud Storage CORS 支持
Cloud Storage 仅允许您在存储桶级层设置 CORS 配置。您可以使用各种工具为存储桶设置 CORS 配置;但是,不同的 Cloud Storage 端点以不同的方式处理 CORS 请求:
无论存储桶上设置的配置如何,JSON API 端点始终允许 CORS 请求并返回 CORS 响应标头中的默认值。
XML API 端点只会根据存储桶上的配置允许 CORS 请求,并返回特定 CORS 标头值来响应该配置。
基于身份验证的浏览器下载端点
storage.cloud.google.com
不允许 CORS 请求。请注意,Google Cloud 控制台会为每个对象的公开网址链接提供此端点。
您可以使用以下任一 XML API 请求网址,从 Cloud Storage 获取包含 CORS 标头的响应:
storage.googleapis.com/BUCKET_NAME
BUCKET_NAME.storage.googleapis.com
如需了解 XML API 请求网址,请参阅请求端点。
CORS 配置的组件
使用 XML API 时,您为存储桶的 CORS 配置设置的值决定了 Cloud Storage 在 HTTP 响应中返回的 CORS 标头。使用 JSON API 时,Cloud Storage 不会评估存储桶的配置,而是返回默认标头值。
下表介绍了 CORS 配置中的字段以及 XML 和 JSON API 的响应行为。如需了解如何使用这些字段,请参阅 CORS 配置示例。
字段1 | 说明 | XML API 响应行为 | JSON API 响应行为 |
---|---|---|---|
origin |
指定您要允许与此 Cloud Storage 存储桶进行跨域资源共享的来源。例如 https://origin1.example.com 。 |
如果浏览器请求中的来源与 CORS 配置中的来源匹配,则 Cloud Storage 会向浏览器返回 Access-Control-Allow-Origin 。如果没有匹配项,则 Cloud Storage 不会在响应中包含 Access-Control-Allow-Origin 。您可以提供一个通配符值,以向所有来源授予访问权限:<Origin>*</Origin> 。 |
Cloud Storage 会返回 Access-Control-Allow-Origin 标头并将其设置为请求的来源。 |
method |
指定要允许与此 Cloud Storage 存储桶进行跨域资源共享的 HTTP 方法。该值会在 由于 |
Cloud Storage 支持以下方法: Cloud Storage 会根据存储桶的 CORS 配置检查 |
Cloud Storage 会返回 Access-Control-Allow-Methods 标头并将其设置为以下方法:DELETE 、GET 、HEAD 、PATCH 、POST 、PUT 。
|
responseHeader |
指定要允许与此 Cloud Storage 存储桶进行跨域资源共享的标头。该值会在 Access-Control-Allow-Headers 标头中返回,以响应成功的预检请求。 |
对于预检请求,Cloud Storage 会根据存储桶的 CORS 配置检查 Access-Control-Request-Headers 标头中从浏览器发送的标头。如果没有匹配项,Cloud Storage 不会返回 CORS 响应标头。 |
Cloud Storage 会返回 Access-Control-Allow-Headers 标头并将其设置为与 Access-Control-Request-Headers 标头指定的值相同。 |
maxAgeSeconds (可选) |
指定浏览器在发出请求多少秒后必须重复预检请求。这也称为缓存过期时间。该值会在 Access-Control-Max-Age 标头中返回,以响应预检请求。例如,3600 将缓存过期时间设置为 1 小时。 |
Cloud Storage 会返回 Access-Control-Max-Age 标头并将其设置为指定的缓存过期时间。如果省略此字段,Cloud Storage 将返回默认值 3600 。 |
Cloud Storage 会返回 Access-Control-Max-Age 标头,其默认值为 3600 。 |
1 “字段”列中记录的名称特定于 JSON API。使用 XML API 设置 CORS 配置时,请使用 XML 专用格式。
指定多个来源、方法或标头
如需了解如何在 CORS 配置中设置多个来源、方法或标头,请参阅以下列表:
使用 JSON API 时,您可以使用英文逗号分隔数组指定多个来源、方法或标头。例如
"method": ["GET", "PUT"]
。使用 XML API 时,您可以使用单独的元素指定多个来源、方法或标头。例如:
<Methods> <Method>PUT</Method> <Method>GET</Method> </Methods>
如需允许从任何来源发出请求,请将来源设置为
*
。例如,在 JSON API 中为"origin": ["*"]
,或在 XML API 中为<Origin>*</Origin>
。虽然此来源有助于测试配置,但在大多数情况下,您需要限制请求来源,以防止在没有必要的情况下使用资源。
其他注意事项
下表介绍了使用凭据或访问权限控制标头发出请求时的注意事项:
属性或标头 | 说明 | XML API 响应行为 | JSON API 响应行为 |
---|---|---|---|
凭据 | Cookie、授权标头或 TLS 客户端证书。 | Cloud Storage 绝不会返回 Access-Control-Allow-Credentials 标头。XML API 不支持 CORS 凭据。 |
对于简单请求,如果 CORS 请求获得批准, 对于预检请求,如果 |
公开的标头 | 对于预检请求,Access-Control-Request-Headers 请求标头会指明未来 CORS 请求可能包含哪些标头。Access-Control-Expose-Headers 响应标头包含在服务器响应中,并指示客户端可以公开哪些标头。 |
对于简单请求,Access-Control-Expose-Headers 会列出 CORS 配置中的响应标头值。 |
对于简单请求,如果常见 HTTP 标头列表中包含 Access-Control-Request-Headers 中指定的值,则 Access-Control-Expose-Headers 会返回这些值。 |
允许存储桶访问外部资源
有时,您可能希望允许 Cloud Storage 中托管的脚本访问 Cloud Storage 外部的网站上托管的静态资源。在此场景中,该外部网站会传送 CORS 标头,以允许 storage.googleapis.com
上的内容进行访问。
最佳实践是为此类数据访问提供专属的特定存储桶。这种做法可防止您的网站在不经意间将静态资源过度公开给所有 storage.googleapis.com
。例如,如果您希望为数据访问提供专属的存储桶 mybucket
,则应让网站传送 CORS 标头 Access-Control-Allow-Origin: https://mybucket.storage.googleapis.com
(而不是 Access-Control-Allow-Origin: https://storage.googleapis.com
)。
客户端 CORS 支持
大多数浏览器都使用 XMLHttpRequest
对象来发出跨域请求。
XMLHttpRequest
负责插入正确的标头以及处理与服务器进行的 CORS 交互。您不必添加任何新代码即可在 Cloud Storage 存储桶上支持配置 CORS。
后续步骤
- 了解如何为存储桶启用 CORS。
- 探索 CORS 配置示例,包括用于移除存储桶的 CORS 配置的示例。