Auto Scaling Out/In 自动扩展或缩减笔记
目前为止已经完成将应用程序从传统自建机房搬到 AWS 云端的工作,这已经帮管理人员节省了要管理一大堆实体设备的问题,接下来我们就继续发挥云端的特色,云计算最为人所称道的就是它的便利性,也就是要用多少拿多少,不用就还给云端,转成专业术语就是 Auto Scaling Up/Down 自动扩展或缩减,所以接下来我们要进行的就是如何让原先的架构可以达到这个目标,如下图所示
图 1 具有自动扩展功能的应用程序架构
下图是个很常见的网页应用程序计算使用量的统计图表,所有网站拥有者都有相同的困扰,他们必须为最高计算量准备好该有的硬设备,但是当我们把整个计算量统计出来时,却发现原来闲置的计算量可能数倍于使用所需的计算量,这对经营者而言是个很大的打击,尤其是针对新创业者或是产品周期就短的业者而言,都是很不利的,这也说明了,为何现在的新创公司或是手游业者会大量采用云端技术的主要原因。
图 2 网页应用程序容量统计图
AWS 在自动扩展或缩减这个需求上提供了三个组件:
- 启动配置 Launch Configuration : 这个组件提供的是当要扩展时所要启动的 EC2 实例,所以需要提供 AMI 、实例类型、安全组、角色。
- 自动扩展组 Auto Scaling Group : 这个组件提供的是整个 EC2 实例所在的环境,包含了 VPC 和子网、负载均衡器、最少实例数、最多实例数、所需容量。
- 自动扩展策略 Auto Scaling Policy : 这个组件提供的是整个系统要如何进行扩展或缩减需求,是按特定时间就增加或减少,这个功能适合对时间敏感的组织,如证券公司开盘时就是高峰期间,零售商特卖活动等;另一种是依照目前的计算量来进行配置。所以包含了按计划/按求需、扩展策略或缩减策略等功能。
下图描述了 AWS 自动扩展或缩减架构, ELB 对外提供服务,透过 Cloud Watch 来监控 ELB 目前的状态,根据使用者是先定义好的 Auto Scaling Policy 来通知 Auto Scaling 是否要新增 EC2 实例,如果需要,则从 Launch Configuration 所定义好的 EC2 实例进行启动,并放置到 ELB 的 target group 中。
图 3 、AWS 自动扩展或缩减架构
Aoto Scaling Group 建置
从无到有建置 Aoto Scaling Group 要做的事情有
- 建置 VPC 与相关的子网 - 请参阅 Amazon VPC 实操。
- 新增 EC2 实例 - 请参阅 Amazon Elastic Compute Cloud (EC2) 笔记。
- 新增 RDS 实例 - 请参阅 EC2 连接 RDS。
- 新增 AMI - 建置一个 AMI 模板供后续的 Launch Configuration 使用
根据以上所建立的 EC2 实例,我们必须在该实例上进行一些雏型系统配置,作为将来检验之用
系统设定
# 安装套件 httpd php mysql php-mysql
sudo yum -y install httpd php mysql php-mysql
# 启动 Web Server
sudo systemctl start httpd
# 设定 Web Server 为系统服务,可在下次重开机时自动启动
sudo systemctl enable httpd
- 1
- 2
- 3
- 4
- 5
- 6
- 7
应用程序设定
首页程序 index.php,新增加可以增加主机CPU负载的链结
<center>
<p>
<a href="put-cpu-load.php" target="_blank">Increase CPU Load</a>
</p>
<table class='table table-bordered'>
<tr><th>Meta-Data</th><th>Value</th></tr>
<?php
#The URL root is the AWS meta data service URL where metadata
# requests regarding the running instance can be made
$urlRoot="http://169.254.169.254/latest/meta-data/";
$instanceId = file_get_contents($urlRoot . 'instance-id');
$availabilityZone = file_get_contents($urlRoot . 'placement/availability-zone');
# Get the instance ID from meta-data and print to the screen
echo "<tr><td>InstanceId</td><td><i>" . $instanceId . "</i></td><tr>";
# Availability Zone
echo "<tr><td>Availability Zone</td><td><i>" . $availabilityZone . "</i></td><tr>";
include("rds_write.php");
?>
</table>
</center>
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
存取 RDS 的程序 rds_write.php
<?php
//This is a simple EC2_metadata example for testing with RDS
// RDS configuration
$rdsURL = “ithomedbid.clbfxibs3qbv.ap-southeast-1.rds.amazonaws.com”;
$rdsDB = “ithomeDB”;
$rdsUser = “ithomeDbuser”;
$rdsPwd = “ithome-password”;
// Get remote IP
r
e
m
o
t
e
I
p
=
i
s
s
e
t
(
remoteIp = isset(
remoteIp=isset(_SERVER[‘REMOTE_ADDR’]) ? $_SERVER[‘REMOTE_ADDR’] : “”;
// Connect to the RDS database
m
y
s
q
l
i
=
n
e
w
m
y
s
q
l
i
(
mysqli = new mysqli(
mysqli=newmysqli(rdsURL, $rdsUser, $rdsPwd, $rdsDB);
// Set mysql connection character set
if (!$mysqli->set_charset(‘utf8’)) {
printf(“Error loading character set utf8: %s\n”, $mysqli->error);
exit;
}
// Insert data into ec2_metadata tbale in RDS
s
q
l
=
"
I
N
S
E
R
T
I
N
T
O
e
c
2
m
e
t
a
d
a
t
a
(
i
n
s
t
a
n
c
e
I
d
,
a
v
a
i
l
a
b
i
l
i
t
y
Z
o
n
e
,
r
e
m
o
t
e
I
p
)
V
A
L
U
E
S
(
′
sql = "INSERT INTO ec2_metadata (instanceId, availabilityZone, remoteIp) VALUES ('
sql="INSERTINTOec2metadata(instanceId,availabilityZone,remoteIp)VALUES(′{instanceId}’, ‘
a
v
a
i
l
a
b
i
l
i
t
y
Z
o
n
e
′
,
′
{availabilityZone}', '
availabilityZone′,′{remoteIp}’)";
if (!$mysqli->query( $sql))
echo "<div>Error: " . $sql . “<br>” . $mysqli->error . “</div>”;
$mysqli->close();
?>
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
产生 CPU 负载的程序 put-cpu-load.php
<?php
# Start PHP Session to keep track of whether or not load is getting generated
session_start();
echo “<meta http-equiv=“refresh” content=“5,URL=./put-cpu-load.php” />”;
KaTeX parse error: Can't use function '\'' in math mode at position 34: …stat 1 2 | awk \̲'̲{ for (i=1; i&l…i==“id”) { getline; getline; print $i }}’’);
if ($idleCpu > 50) {
echo exec('dd if=/dev/zero bs=100M count=500 | gzip | gzip -d > /dev/null &');
echo "Generating CPU Load! (auto refresh in 5 seconds)";
}
else {
echo “Under High CPU Load! (auto refresh in 5 seconds)”;
}
echo “<br /><p>Current CPU Load: <b>”;
echo 100-$idleCpu;
echo “%</b></p>”;
?>
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
透过浏览器确认功能无误,确认首首以及产生 CPU 负载测试页均可正常运行,如下图显示
图 4 确认 EC2 实例的功能符合要求
到 EC2 控制台,选择左边选单中的 实例,再选择刚刚建立的 EC2 实例,按鼠标右建,选择 Image > Create Image,接着输入以下内容建可以建立一个 AMI Image
Image name : ithomeAMI
Image description : ithome Web Server AMI
图 5 新增 AMI
图 6 输入 AMI 信息
- 新增 Application Load Balancer (ALB) - 原则上跟 Elastic Load Balancing (ELB) 笔记 很类似,只有第五个步骤 Register Targets,有所不同,原来的步骤是
Register Targets: 指定目标群的内容,将先前设定的两个 EC2 实例指定到上面新建立的目标群
图 7 指定负载平衡器目标群内容
但因为这次的目标群是不固定的,会在下一个步骤再设定,所以应该是不要指定,如下图
图 8 负载平衡器目标群内容不指定
- 新增 Launch Configuration - 设定目标群内的 EC2 实例的启动组态
到 EC2 控制台,选择左边选单中的 Launch Configuration,按下右边的建立启动组态按钮
图 9 建立启动组态
完成启动组态设定
名称 : ithomeLC
AMI : ithomeAMI
实例类型 : t2.micro (1 vCPU, 1 GiB, 仅 EBS)
监控 (Monitoring) : 在 CloudWatch 中启用 EC2 实例详细监控 #重要!!!启用详细监控之后,当您使用此启动组态时,Auto Scaling 群组可以具备相关扩展政策,以 1 分钟的频率在 Amazon EC2 实例指标上扩展。
指派安全群组 :
选取现有的安全群组
ithome_web_SG
密钥对选项 :
选择现有的密钥对
ithome
图 10 启动组态设定画面
- 新增 Auto Scaling Group
到 EC2 控制台,选择左边选单中的 Auto Scaling 群组,按下右边的建立 Auto Scaling 群组按钮,接下来需要完成七个步骤来完成Auto Scaling 群组的设定
步骤 1. 选择启动模板或组态
Auto Scaling 组名 : ithomeACG
启动组态 : ithomeLC (记得一定要先按下转换至启动组态,才会切换到选择启动组态)
图 11 选择启动组态
步骤 2. 进行设定
VPC : vpc-0bb7004b67556d0da (172.16.0.0/16) | ithomeVPC
子网 :
ap-southeast-1a | subnet-0f1df807467b642f6 (ithome public subnet 1)
172.16.0.0/26
ap-southeast-1b | subnet-06f56dccb2a9cfcf0 (ithome public subnet 2)
172.16.0.64/26
图 12 网络组态设定
步骤 3 (选用) 设定进阶选项
负载平衡
勾选 启用负载平衡
_Application Load Balancer _
为您的负载平衡器选择目标组 : ithomeTargetGroup
监控 : 勾选 在 CloudWatch 中启用群组指针集合
图 13 负载平衡设定
步骤 4 (选用) 设定群组大小和扩展政策
群组大小 - 选用
变更所需的容量,以指定 Auto Scaling 群组的大小。您也可以指定最小和最大容量限制。所需的容量必须在限制范围内。
所需容量 : 2 # 指的是一开始启动 Auto Scaling Group 会启动的 EC2 实例数量
容量下限 : 1 # 指的是 Auto Scaling Group 最少正在执行的 EC2 实例数量
容量上限 : 10 # 指的是 Auto Scaling Group 最多正在正常执行的 EC2 实例数量
扩展政策 - 选用
选择 目标追踪扩展政策
选择所需的结果,并将其保留至扩展政策中,视需要新增和移除容量,以实现该结果。
扩展政策名称: itHomePolicy
指标类型 : 平均 CPU 使用率
目标数值 : 50
纳入指标之前的暖机秒数 : 300
这个设定的意思是说当整个 Auto Scaling Group 的平均 CPU 使用率为 50% 的话,会扩展一台新的 EC2 实例来降低整个系统的负荷
纳入指标之前的暖机秒数这个数字是说,当新增一台新的 EC2 实例,从启动到可以被注册到目标群的时间
图 14 设定群组大小和扩展政策
步骤 5 (选用) 新增通知
没有设定
步骤 6 (选用) 新增标签
标签
密钥 : Name # 注意大小写是不同的,
数值 : itHomeWebServer
图 15 设定新启动的 EC2 实例的名称
步骤 7. 检阅
再次确认上述数据有无错误
检验 Auto Scaling Group
到 EC2 控制台,选择左边选单中的 负载平衡器,选择负载平衡器 ithomeALB,并找到 DNS name 这个字段,复制这个字段并贴到浏览器,如果成功会出现以下画面,按下 Increase CPU Load 来增加 CPU 使用率。
图 16 透过ALB浏览网页
几分钟后,到 EC2 控制台,选择左边选单中的 Target groups,选择 ithomeTargetGroup,切换到 Targets 页签,可以观察到下方的 EC2 实例的增加状况。
图 17 观察目标组实例的状态
以上是没有错误的状况,但如果一直观察不到有新的 EC2 实例生成,可以到 EC2 控制台,选择左边选单中的 Auto Scaling Groups,选择 ithomeACG,切换到活动页签,可以观察到活动的历史纪录,这是很重要的排错功能。
图 18 观察Auto Scaling Groups活动的历史纪录
此外还可以透过监控页签,选择检视所有 CloudWatch 指标,切换到CloudWatch的控制台,选择 EC2 > 依照 Auto Scaling 群组,选择观察 CPUUtilization 这个指针,就可以有图形化的方式显示出来
图 19 透过 CloudWatch 观察 CPUUtilization
再检查RDS是否正常运作
图 20 检查RDS是否正常运作
最后,当整个CPU使用率下降后,确认是否会自动缩减,一样去检查目标组(Target groups)中的实例的状态就可以知道,下图中有三个实例正在进行解注册目标组
图 21 目标组实例自动缩减