如何使用 CloudFront 为 Amazon S3 上托管的静态网站提供服务?
上次更新日期:2021 年 1 月 5 日
我想在 Amazon Simple Storage Service (Amazon S3) 存储桶中托管静态网站。然后,我想通过 Amazon CloudFront 分配为我的网站服务。该如何操作?
简短描述
要为 Amazon S3 上托管的静态网站提供服务,您可以使用以下某项配置部署 CloudFront 分配:
- 使用 REST API 终端节点作为源,通过源访问身份 (OAI) 限制访问权限
- 使用网站终端节点作为源,允许匿名(公开)访问
- 使用网站终端节点作为源,通过 Referer 标头限制访问权限
- 使用 AWS CloudFormation 将 REST API 终端节点部署为源,并通过 OAI 和指向 CloudFront 的自定义域限制访问权限
有关两个终端节点类型的更多信息,请参阅网站终端节点和 REST API 终端节点之间的主要差异。
解决方法
按照以下步骤,配置具有要用作源的 S3 终端节点类型的 CloudFront 分配:
使用 REST API 终端节点作为源,并通过 OAI 限制访问权限
- 使用 Amazon S3 控制台创建存储桶并上传网站文件。
注意:若采用此配置,则无需在存储桶上启用静态网站托管。此配置使用存储桶的 REST API 终端节点,而不是静态网站托管功能中的网站终端节点。 - 创建 CloudFront Web 分配。除了您的使用案例需要的分配设置外,另请输入以下内容:
在源域名部分,选择您创建的存储桶。
对于限制存储桶访问,请选择是。
对于源访问身份,请选择创建新身份。
备注部分可以保留默认值。您还可以为 OAI 输入自定义标签。
对于授予存储桶读取权限,请选择 Yes, Update Bucket Policy(是,更新存储桶策略)。 - 最佳做法是为您的网站使用 SSL (HTTPS)。要设置 SSL,请为 SSL 证书选择 Default CloudFront Certificate(默认的 CloudFront 证书)以使用默认的 CloudFront DNS 名称。或者,选择 Custom SSL Certificate(自定义 SSL 证书)以使用您自己的自定义域。您可以选择 Request or Import a Certificate with ACM(使用 ACM 请求或导入证书)以请求新证书。
重要提示:如果您为分配输入了备用域名 (CNAME),则 CNAME 必须与您选择的 SSL 证书匹配。要排查 SSL 证书的问题,请参阅如何排查与在我的 CloudFront 分配上使用自定义 SSL 证书有关的问题? - 选择 Create Distribution(创建分配)。
- 更新域的 DNS 记录,以便将网站的 CNAME 指向 CloudFront 分配的域名。您可以在 CloudFront 控制台中查找您的分配的域名,其格式类似于 d1234abcd.cloudfront.net。
- 等候 DNS 更改完成传播且先前的 DNS 条目过期。
注意:先前的 DNS 值过期所需的时间取决于托管区域中设置的 TTL 值,以及您的本地解析程序是否使用这些 TTL 值。
使用网站终端节点作为源,允许匿名(公开)访问
此配置允许公开读取您网站的存储桶。有关更多信息,请参阅设置网站访问权限。
注意:当您使用 Amazon S3 静态网站终端节点时,CloudFront 和 Amazon S3 之间的连接只能通过 HTTP 进行。要将 HTTPS 用于 CloudFront 和 Amazon S3 之间的连接,请为源配置 S3 REST API 终端节点。
- 使用 Amazon S3 控制台创建一个存储桶,然后为该存储桶启用静态网站托管功能。
- 在 Static website hosting(静态网站托管)对话框中,复制您的存储桶的终端节点,但不要复制先导符 http://。格式类似于 DOC-EXAMPLE-BUCKET.s3-website-region.amazonaws.com。您将后面的步骤中用到此格式的终端节点。
- 向您已创建的存储桶添加允许公开读取权限的存储桶策略。
- 创建 CloudFront Web 分配。除了您的使用案例需要的分配设置外,另请输入以下内容:
对于源域名,输入您在第 2 步复制的终端节点。 - 最佳做法是为您的网站使用 SSL (HTTPS)。要设置 SSL,请为 SSL 证书选择 Default CloudFront Certificate(默认的 CloudFront 证书)以使用默认的 CloudFront DNS 名称。或者,选择 Custom SSL Certificate(自定义 SSL 证书)以使用您自己的自定义域。您可以选择 Request or Import a Certificate with ACM(使用 ACM 请求或导入证书)以请求新证书。
重要提示:如果您为分配输入了备用域名 (CNAME),则 CNAME 必须与您选择的 SSL 证书匹配。要排查 SSL 证书的问题,请参阅如何排查与在我的 CloudFront 分配上使用自定义 SSL 证书有关的问题? - 选择 Create Distribution(创建分配)。
- 更新域的 DNS 记录,以便将网站的 CNAME 指向 CloudFront 分配的域名。您可以在 CloudFront 控制台中查找您的分配的域名,其格式类似于 d1234abcd.cloudfront.net。
- 等候 DNS 更改完成传播且先前的 DNS 条目过期。
注意:先前的 DNS 值过期所需的时间取决于托管区域中设置的 TTL 值,以及您的本地解析程序是否使用这些 TTL 值。
使用网站终端节点作为源,通过 Referer 标头限制访问权限
此配置通过以下方法限制访问权限:在分配上设置自定义 Referer 标头,然后使用存储桶策略来仅向具有自定义 Referer 标头的请求授予访问权限。请务必评估此设置允许的访问权限是否符合您的使用案例的要求。
注意:当您使用 Amazon S3 静态网站终端节点时,CloudFront 和 Amazon S3 之间的连接只能通过 HTTP 进行。要将 HTTPS 用于 CloudFront 和 Amazon S3 之间的连接,请为源配置 S3 REST API 终端节点。
- 使用 Amazon S3 控制台创建一个存储桶,然后为该存储桶启用静态网站托管功能。
- 在 Static website hosting(静态网站托管)对话框中,复制您的存储桶的终端节点,但不要复制先导符 http://。格式类似于 DOC-EXAMPLE-BUCKET.s3-website-region.amazonaws.com。您将后面的步骤中用到此格式的终端节点。
- 创建 CloudFront Web 分配。除了您的使用案例需要的分配设置外,另请输入以下内容:
对于源域名,输入您在第 2 步复制的终端节点。
在标头名称下的源自定义标头部分,输入 Referer。在值下,输入您希望转发给源(S3 存储桶)的自定义标头。要限制对源的访问,您可以输入只有您知道的随机值或密钥。 - 最佳做法是为您的网站使用 SSL (HTTPS)。要设置 SSL,请为 SSL 证书选择 Default CloudFront Certificate(默认的 CloudFront 证书)以使用默认的 CloudFront DNS 名称。或者,选择 Custom SSL Certificate(自定义 SSL 证书)以使用您自己的自定义域。您可以选择 Request or Import a Certificate with ACM(使用 ACM 请求或导入证书)以请求新证书。
重要提示:如果您为分配输入了备用域名 (CNAME),则 CNAME 必须与您选择的 SSL 证书匹配。要排查 SSL 证书的问题,请参阅如何排查与在我的 CloudFront 分配上使用自定义 SSL 证书有关的问题? - 选择 Create Distribution(创建分配)。
- 从 Amazon S3 控制台打开您网站的存储桶。然后,添加存储桶策略:在请求包含自定义 Referer 标头的情况下允许 s3:GetObject,该标头即您在第 3 步中指定的标头。
注意:要阻止不包含自定义 Referer 标头的请求的访问权限,请在存储桶策略中使用显式拒绝语句。 - 更新域的 DNS 记录,以便将网站的 CNAME 指向 CloudFront 分配的域名。您可以在 CloudFront 控制台中查找您的分配的域名,其格式类似于 d1234abcd.cloudfront.net。
- 等候 DNS 更改完成传播且先前的 DNS 条目过期。
注意:先前的 DNS 值过期所需的时间取决于托管区域中设置的 TTL 值,以及您的本地解析程序是否使用这些 TTL 值。
使用 CloudFormation 将 REST API 终端节点部署为源,并通过 OAI 和指向 CloudFront 的自定义域限制访问权限
使用此解决方案,您的网站:
- 已部署 CloudFormation
- 已在 Amazon S3 上托管
- 已由 CloudFront 分发
- 使用 AWS Certificate Manager (ACM) 颁发的 SSL/TLS 证书
- 使用 Lambda@Edge 为每个服务器响应添加安全标头
有关部署此解决方案的说明,请参阅 GitHub 网站上的 Amazon CloudFront 安全静态网站。