前言
在这个快速上手教程中,您将学会如何使用 Amazon CloudFront 对网站进行内容分发,实现对静态内容和动态内容的加速,最终降低终端用户访问您的网站或 Web 应用的延迟。Amazon CloudFront 是一项内容分发网络(CDN)服务,它利用 AWS 全球骨干网络和边缘站点,能够将您的 Web 内容包括图片、视频、API 等以低延迟和高可用性分发至世界各地。
教程将分为 5 个步骤,首先,您将创建一个由 Amazon S3 存储桶和 Amazon EC2 实例构成的网站,您将在 Amazon S3 存储桶中上传静态网站文件作为静态资源,以及使用 Amazon EC2 实例提供 API 服务作为动态内容。然后,您将创建 Amazon CloudFront 分配,分别添加 S3 源站和 EC2 源站,并为动静态内容配置相应的缓存行为。最终您将验证 Amazon CloudFront 对网站加速的效果,如下图所示。此外,您可参考可选步骤 6 Amazon CloudFront 分配添加自定义域名及 SSL 证书。
关于本教程 | |
预计部署时间 | 快速上手教程 30 分钟 |
费用 | 免费套餐 |
受众 | 运维工程师 |
级别 | 初级 |
相关产品 | Amazon CloudFront, Amazon S3, Amazon EC2, AWS Certificate Manager, Amazon Route53 |
相关行业 | 通用 |
上次更新日期 | 2023 年 5 月 |
教程说明
本教程以一个动静分离的源站为例,静态资源存储于 S3(Amazon S3 是一种对象存储服务,可以存储网站静态资源,CloudFront 可以使用 Amazon S3 存储桶作为源为您分发几乎任何类型的文件),动态资源来自于 ALB 后端的 EC2。
教程将分为 3 个步骤:
首先,您将创建 Amazon CloudFront 分配,添加自定义源站为默认回源地址;
其次,您将添加 S3 为静态内容回源源站;
最后,您将创建域名解析,使得您可以使用您的域名通过 CloudFront 进行加速访问。
首先简单介绍下 CloudFront 的常见术语:
- Distribution:分配,是 CloudFront 的基本单元,每个分配有唯一的 ID 以及CloudFront 为其分配的域名(类似 abcdefg13456789.cloudfront.net)。
- Origin:源站,顾名思义,是需要被加速的站点,可以是 S3 存储桶,可以是 ELB/EC2,可以是 Elemental MediaStore/MediaPackage,或者是用户自定义的站点(如第三方 IDC 中的 HTTP Web 服务器)。一个分配中可以有多个源站。
- Behaviors:行为,CloudFront 通过路径匹配和优先级决定执行哪一个缓存行为,一个分配中可以有多个行为,并且每个行为对应一个源站。在行为中可以设置缓存 TTL 时间,允许的 HTTP 行为(GET,PUT,POST 等)等等。
本节将涉及如下内容:
- 创建一个分配;
- 该分配有两个源站,其中一个是创建时添加的动态资源,源站使用自定义域名,该域名已指向 Elastic Load Balancing,主要提供 API 服务作为动态内容,另一个是后添加的静态资源,源站为 S3 存储桶;
- 两个行为,一个是默认行为对应回源自定义域,一个是新加的行为并对应源站 S3 存储桶;
- 使用 Elastic Load Balancing 创建自定义域,以及使用自定义域名解析到 Elastic Load Balancing、S3 源站创建等过程不做介绍。
第一步:创建 Amazon S3 存储桶作为静态资源源站
-
在这个步骤中,您将创建一个 Amazon S3 存储桶并上传静态网站文件作为 Amazon CloudFront 的 S3 源站。
a. 单击此处,进入 Amazon S3。点击创建存储桶按钮开始创建 S3 存储桶,在存储桶名称处为存储桶命名(存储桶名称需全局唯一),AWS 区域处选择美国东部(弗吉尼亚北部)us-east-1。其他设置保持默认,点击创建存储桶按钮完成 S3 存储桶创建。
b. 下载静态主页文件 hello-world-html.zip (该文件来自 AWS-文档-Amazon CloudFront-开发人员指南),在本地电脑解压 zip 后将所有文件上传至S3存储桶中。S3 存储桶中将包含一个 index.html 文件,一个 css 文件夹(其中包含 style.css 文件)。
第二步:创建 Amazon EC2 实例作为 Web 源站
-
在这个步骤中,您将创建一个 Amazon EC2 实例作为 Web 服务器提供 API 服务,它将作为 Amazon CloudFront 的 Web 源站。
a. 点击此处,进入 Amazon EC2 管理控制台,请确保右上角 AWS 区域处为弗吉尼亚北 (us-east-1)。点击启动实例按钮。
b. 在名称和标签处,为实例命名为 cloudfront-getting-started。在应用程序和操作系统映像处,选择 Amazon Linux 2 AMI。
c. 在实例类型处,保持默认的 t2.micro 实例类型设置。在密钥对处,选择您已有的密钥对,或点击创建新密钥对以创建新的密钥,请务必下载保存该密钥。
d. 在网络设置处,保持默认的网络选项。在防火墙(安全组),保持默认的创建新安全组设置,勾选允许来自互联网的 HTTP 流量。
e. 展开高级详细信息菜单,在用户数据处复制如下代码,该代码将部署一个 Node.js 应用,会监听针对 EC2 80 端口的 HTTP 请求。当收到请求时,该应用会发回一个 JSON 格式的响应,包含请求中的 HTTP Header 信息。它也会解析查询字符串的信息,并从 Web 服务器返回查询数据。请点击启动实例按钮开始创建 EC2 实例。
#!/bin/bash yum update -y curl -sL https://rpm.nodesource.com/setup_14.x | sudo bash - yum install -y nodejs npm install pm2@latest -g npm install express --save cat <<'EOF' >> app.js let express = require('express'); let app = express(); app.get('/api', (req, res) => { console.log(JSON.stringify(req.headers)); let message = { timestamp: new Date().toISOString(), headers: req.headers, }; res.json(message); }); app.listen(80, () => { console.log('api is up!'); }); EOF sudo pm2 start ./app.js sudo pm2 startup systemd sudo pm2 save systemctl enable --now pm2-root.service
f. 等待 EC2 实例创建成功,您可以在浏览器中访问 http://{EC2-IP}/api 或 http://{EC2-DNS-NAME}/api 确保 Web 应用正常工作,您将看到类似下图的响应。
第三步:创建 Amazon CloudFront 分配并添加 S3 源站
-
您已通过步骤 1 和步骤 2 完成 S3 源站和 EC2 源站的创建,接下来您将创建 Amazon CloudFront 分配并添加步骤 1 中创建的 S3 存储桶作为 S3 静态资源源站,并使用来源访问控制功能(Origin Access Control,OAC)安全地通过 CloudFront 访问和分发私有 S3 存储桶中的内容。
a. 点击此处,进入 Amazon CloudFront 控制台,点击创建分配按钮。
b. 在源设置中,在源域处点击输入框,选择步骤 1 中创建的 S3 存储桶。在名称处,将 S3 源命名为 s3-origin-cloudfront-getting-started。
c. 在源设置,来源访问处,选择来源访问控制设置(推荐),点击创建控制设置。
d. 保持控制设置的默认设置,点击创建按钮。您将看到来源访问控制处的配置已更新。
e. 在默认缓存行为设置处,将查看器 - 查看器协议策略勾选位 Redirect HTTP to HTTPS。
f. 在缓存键和源请求处,保持默认的 CachingOptimized 缓存策略。
g. 在 Web 应用程序防火墙(WAF)处,勾选不要启用安全保护。
h. 其余设置保持默认,在下方设置 - 默认根对象处,填入 index.html。点击创建分配按钮,完成 CloudFront 分配创建和 S3 源站的添加。
i. 您将看到 CloudFront 分配正在创建,请点击蓝色提示符的复制策略按钮,并点击转到 S3 存储桶权限以更新策略按钮,打开 S3 控制台
j. 在存储桶策略处点击编辑。
k. 在策略编辑器中粘贴刚刚复制的策略,点击保存更改按钮。该策略将保护您的存储桶在不被公开访问的情况下由 CloudFront 安全地分发存储桶内容。
第四步:为 Amazon CloudFront 分配添加 EC2 源站
-
通过步骤 3,您已创建一个 Amazon CloudFront 分配并添加 S3 源站。接下来您将为该分配继续添加步骤 2 中创建的 EC2 源站以实现对 API 服务的动态加速。
a. 进入步骤 3 中创建的 CloudFront 分配,在源标签中,点击创建源。
b. 在源域处,填入 EC2 公有 IPv4 地址,您可以通过在 EC2 控制台 - 实例详细中找到该地址,如下图所示。协议保持默认的仅 HTTP,名称处填入 ec2-origin-cloudfront-getting-started,其余设置保持默认,点击创建源。
您将看到该 CloudFront 分配除 S3 源站外已添加 EC2 源站。
c. 进入 CloudFront 分配,在行为处,点击创建行为,为 EC2 源站创建缓存行为。
d. 在路径模式中键入 /api,源和源组下拉框中选择上一步创建的 EC2 源站,查看器协议策略处勾选 Redirect HTTP to HTTPS。
e. 在缓存键和源请求处,缓存策略下拉框中选择 CachingDisabled 策略,源请求策略下拉框中选择 AllViewer 策略。其余设置保持默认,点击创建分配按钮。
f. 为了保护 EC2 源站,使 HTTP 流量仅从 CloudFront 进入 EC2,接下来您将修改 EC2 实例所关联的安全组规则。回到 EC2 控制台,选中 Web 源站 EC2 实例,选中安全标签,点击 EC2 所关联的安全组资源。
g. 进入 EC2 安全组的详情页面,点击编辑入站规则按钮。
h. 首先,删除规则类型为 HTTP,源为 0.0.0.0/0 的入站规则。随后,点击添加规则按钮,添加一条新的入站规则,规则类型为 HTTP,在源处键入 pl-,您将在选项框中看到多个 VPC 托管前缀。选中带有 com.amazonaws.global 字段且 pl - 后字符位数较短的托管前缀,点击保存规则。修改完成后的安全组规则如下图所示。
i. 在修改 EC2 安全组规则后,当您再次访问该 EC2 实例的 IPv4 DNS 地址时将发生超时,这是因为您使用 VPC 托管前缀保护 EC2 仅允许来自 CloudFront 的流量进入。接下来您将验证通过 CloudFront 加速访问 S3 静态资源和 EC2 API 服务的过程。
第五步:验证 CloudFront 分配
-
通过步骤 1~4,您已成功创建 CloudFront 分配,添加 S3 源站和 EC2 源站,并配置了相应的缓存策略实现静态内容缓存、动态 API 加速。接下来您将访问该 CloudFront 分配,验证 CDN 分发效果。
a. 进入 CloudFront 控制台,选中刚刚创建的分配,复制分配域名至浏览器。
b. 在分配域名的首页,您将看到 Hello world 首页,即步骤 1 中上传至 S3 存储桶的 index.html。您可以打开一个浏览器的无痕窗口,再次访问该分配域名,在浏览器的开发者工具中将看到 Response Headers 中的 x-cache 状态为 Hit from cloudfront,表示静态文件已被缓存在 CloudFront 边缘站点中。
c. 访问分配域名的 /api 路径,如下图所示,您将看到与步骤 2 中访问 EC2 DNS IPv4 地址类似的输出,并展示了 CloudFront 转发和增加的其他 HTTP header。通过多次刷新页面,您将在浏览器开发者工具的 Response Headers 中看到 x-cache 始终为 Miss from cloudfront,表示对 /api 路径的请求始终不进行缓存、需要通过 CloudFront 回源至 EC2 源站,达到了动态加速效果。
第六步:(可选)为 CloudFront 分配添加自定义域名并配置 SSL 证书
-
通过步骤 1~5,您已成功使用 Amazon CloudFront 为网站进行加速,实现了静态内容缓存分发、动态 API 请求加速的效果。在步骤 5 中,您使用了 CloudFront 提供的分配域名对网站进行访问,如果您具备自定义域名,请按照以下步骤添加。
a. 进入 CloudFront 分配控制台,在常规标签中,点击编辑按钮。
b. 在设置中,点击自定义 SSL 证书下方的请求证书链接。
c. 您将在新标签页中进入 AWS Certificate Manager(ACM)控制台,请确保右上角区域为弗吉尼亚北部(us-east-1),点击下一步按钮。
d. 在请求公有证书的完全限定域名处依次添加您将使用的域名,如 www.example.com, *.example.com, example.com。验证方式选择默认的 DNS 验证。点击确定。
e. 进入上一步所申请的证书详情,该证书在完成 DNS 验证之前将处于等待验证状态。如果您使用 Amazon Route53 托管您的域名,请点击在 Route53 中创建记录按钮。如果您使用其他 DNS 服务商,请将域中所显示的 CNMAE 记录添加至您的 DNS 解析中。
f. 等待 DNS 解析生效,您将看到证书状态变为已颁发。
g. 回到 CloudFront 分配设置页面,请点击自定义 SSL 证书右侧的刷新按钮,并在下拉菜单中选中刚刚由 ACM 创建的域名证书。在备用域名 (CNAME) 处,添加您将使用的自定义域名如 www.example.com (自定义域名需要为 ACM 证书中添加的域名)。点击保存。
h. 来到您的域名 DNS 解析服务处,如果您的域名托管在 Route53,请按下图所示添加记录并创建别名记录将自定义域名的流量解析至 CloudFront 分配。如果您使用其他 DNS 服务商,请为域名创建 CNAME 记录解析至 CloudFront 分配域名。
i. 等待 DNS 解析生效,在浏览器中输入您的自定义域名,您将看到网站使用 HTTPS 协议进行访问并由 CloudFront 交付内容。
第七步:终止资源
-
在这个步骤中,您将终止本实验创建的资源。
a. 清空 S3 存储桶:打开 Amazon S3 控制台,进入步骤 1 中创建的 S3 存储桶,勾选步骤 1 中上传的文件,点击删除按钮。在是否永久删除对象的文本框中输入永久删除以确认。
b. 删除 S3 存储桶:打开 Amazon S3 控制台,选中步骤 1 中创建的 S3 存储桶,点击删除按钮,在是否删除存储桶的文本框中按提示键入存储桶名称以确认删除。
c. 终止 EC2 实例:打开 Amazon EC2 控制台,选中步骤 2 中创建的 EC2 实例,点击实例状态 - 终止实例,这将完全终止您的实例。
d. 禁用 CloudFront 分配:打开 Amazon CloudFront 控制台,在分配列表中选中步骤 3 创建的 CloudFront 分配,点击禁用按钮,在弹窗中确认禁用。
e. 删除 CloudFront 分配:等待 CloudFront 分配的禁用状态修改完毕,点击删除按钮,在弹窗中确认删除。
小结
通过本教程,您已成功完成 Amazon CloudFront 的创建并对网站中静态内容和动态内容进行了分发,实现全站加速。Amazon CloudFront 是在 Web 应用系统前端作为 CDN 实现内容分发的首选,它亦可与 AWS 多种产品集成,如 DDoS 缓解 Amazon Shield,应用程序防火墙 Amazon WAF,边缘计算 Lambda@Edge、CloudFront Functions,进一步提升您的 Web 应用程序的安全性、可用性与性能。