如何搭建 AWS 系统
刚才我们已经简单使用了一下 aws ,现在开始一些准备
获取证书
从首页进入安全证书
AWS 有很多种安全方法,我们选择第三个访问密钥
然后你可以看到你现有的安全凭证
选择生成一个安全证书,妥善的保管它!
注意!
安全证书很重要 很重要。网上有无数人因为证书泄漏,被人恶意的挖矿,爬虫,攻击等等,白白花费了 aws 的费用,。所以一定要保管好,要保管好,要保管好! 重要的事情说 3 遍。
如果发现证书丢失,赶紧上网注销证书!
申请一个密钥对
点击 EC2 面板,选择密钥对
生成一个密钥,给它取一个名字
下载密钥
这个名字很重要,编码的时候会用到
用 linux 主机转换这个密钥 可以参考 http://blog.csdn.net/iamshaofa/article/details/7878346
用 SecureCRT 登录, 需要根据 xxx.pem 生成一个公钥文件 xxx.pem.pub 。不过生成*.pub 还是需要 linux 下进行:
$ chmod 700 xxx.pem
$ ssh-keygen -y -f xxx.pem >xxx.pem.pub
就是说,先改一下*.pem 的权限,然后再用 ssh-keygen 制作 pub 文件
证书和密钥的区别:
证书可以访问你的服务,权利非常大, API 开发需要利用证书,对你的请求进行签名。是你用户身份的标识 密钥对是弹性云计算中主机访问使用时候使用的密钥,没有它你无法连接上新创建的主机。
测试过程
一个分布式系统,从 0 开始构建,我是按照下面的步骤进行
- 搭建主机资源,为主机安装基本的操作系统,以及基本的网络设置如 IP,路由
- 配置基本的网络资源,划分子网,带宽,网络端口开放
- 主机上安装基本的软件,打开防火墙端口,修改内核参数
- 编译所有需要用的软件,准备所需要的软件包,也包括依赖的软件包
- 为所有的主机准备启动,停止,监控所需要的配置文件,脚本
- 为所有的主机部署所需要的各种软件,保证安装正确,所有的配置文件和脚本安装正确
- 将预制数据准备进系统
- 启动监控系统,
- 开启压力测试程序,在监控系统对进度做监控
- 压力测试完成后,停止所有服务
- 检测压力测试的数据结果,看结果是否符合要求
- 销毁所有主机和网络资源
- 检测压力测试中的系统记录数据,画出对应的状态变化曲线。
如果是网站测试的话,我认为可以把软件安装这部分 改为为安装 http 服务器, tomcat ,数据库, Php/Java 程序,准备 Memcached/redis, LVS 代理 这样的业务。实质只是运行的软件不一样,但是流程上大同小异。
实现的过程
1.搭建主机:
我们可以在网页里一步步的点,如果是这样做,云计算就完全没有存在的必要,所以我们需要使用 AWS 提供的 API 接口,创建我们的主机, VPC 网络,最后利用 API 销毁这些主机。
2.编译所有的软件包:
一般公司使用 jenkins 对软件包进行编译,打包,单元测试这些过程。如果是持续开发的环境,这样的系统是必备的。目前从 0 开始,我把过程简化成为一个 shell 脚本,编译完成所有的软件。
3.为所有的主机准备脚本:
写了一个简单的脚本,可以为系统准备随机数据,为每台服务器准备它们需要的启动脚本,停止脚本, redis 启动,清空等一系列脚本。
4.为所有的主机安装软件和脚本:
很明显我们需要一个开源自动化配置管理工具,选择非常多 Saltstack, cfeng, puppet 以及 ansible. 在不考虑语言本身的差异,这几个软件差异并不大,考虑到目前的实际情况,我认为在这个项目中 ansible 有一个比较好的优势:使用 ssh 无需为每台服务器安装相应的客户端,这非常方便。并且执行的批处理也很简单。所以我选择 ansible 作为部署软件。
5.启动和停止服务:
用 ansible 批处理的形式完成
6.监控:
需要一个监控的服务,可以对测试的情况做及时的捕捉,掌握状态。已经提供了部分 zabbix 系统的脚本,但是完整实现还需一些代码,所以目前写了直接写屏软件,用它记录各个服务器压力测试的状态,类似股票市场的监控图。因为服务器的各个时间点状态,都有记录所以可以在后期做测试。
它看上去是这样的

7.事后分析:
已经有专门的脚本支持
整个系统的数据准备,软件编译,分发,部署,测试命令分发,我都在一台主机 10.0.1.11 上完成,这是唯一可以连接 internet 的服务器。这样其他所有的主机都无需连接 Internet ,可以节省网络费用。 fakewechat 使用是 Go 语言编写,所以不存在第三方库依赖问题,非常适合快速部署。
题外话:
从发布测试成熟度来看,我认为可以分为几个阶段, 第一个阶段就是茹毛饮血 hardcode 的脚本时代(就像我目前做的),第二个就是 自动脚本时代, 第三代 就是 service 时代,第四代则是智能管理时代。我觉得,在云时代,企业产品云化需要这样的服务。
构建虚拟机环境
脚本是一年多以前写的,语言 python, 类库 boto2 , 目前 boto 版本是 3.
位置: https://github.com/xiaojiaqi/fakewechat/blob/master/aws/create_vpc.py
只需要用修改几个参数就可以完成
脚本很简单,它大概做了一下几件事情
- 创建一个 VPC
- 创建一个 Internet 的网关
- 将创建的网关加入 VPC
- 创建为网关创建一个路由
- 创建 4 个子网分别是 10.0.1.0/24,10.0.2.0/24,10.0.3.0/24,10.0.4.0/24
- 创建安全组,让所有的主机可以通信
- 创建一台主机 10.0.1.11
- 创建多台主机 IP 从 10.0.2.20 开始
运行文件即可,大概 1 , 2 分钟。几十台服务器就已经安装,配置完成。 IP 网关也配置完成。 步骤 1 , 2 完成
构建软件 安装
现在使用 SecureCRT 连接服务器
SecureCRT 的配置过程是这样的
创建一个连接
将主机的 IP 设置进去,(服务器 IP 可以从控制台获得,也可以用 DNS 管理)
如果是 RHEL 则默认登录用户是 ec2-user, 大部分 Linux 是 root
设置公钥文件,选择 刚才转换好的文件
接受密钥,完成连接
实践过程
我们假设最先登录的主机为 10.0.1.11,它有外部 IP. 但是我们简称它为 10.0.1.11 主机,下面的操作都是在这台主机上完成的
系统部署
- 首先安装 git 工具

- 在当前目录创建 gopath/src/github.com, 进入$HOME/gopath/src/github.com/ 克隆整个项目

- 进入$HOME/gopath/src/github.com/fakewechat/package 运行 install.sh 脚本,脚本主要做了几件事情
- 利用 yum 安装了所需要的 gcc 等工具
- 下载 golang 的安装包,解压,并设置环境
- 编译项目,生成所有的可执行文件
- 编译 redis 服务器,生成需要使用的 redis-server 和 redis-cli 可执行文件
- 导入 RPM-GPG-KEY-EPEL-7, 并安装 ansible 包
- 修改 /etc/ansible/ansible.cfg 文件 大概 38 行左右,去掉这个注释。 这样 ansible 连上新的主机,就不需要确认了。
做到这一步就完成了大部分的准备工作 (默认的配置是 4 个 rg, 每个 rg 是 1000 位用户,在运行前,修改脚本 num_rg 代表 rg 的数目 rg_size 代表这个 rg 里的用户数目 如果是 100 万用户,可以采用 40 台主机,每台主机 2.5 万个用户的配置)
系统测试
- 重新建立一个连接,通过 10.0.1.11 主机,跳转进入 10.0.2.20 主机,运行 monitorclient . 这样我们就可以
- 在 10.0.1.11 主机上利用 screen 启动所有的压力测试客户端 运行一下命令启动测试客户端 screen ansible all -f 40 -a "$HOME/bin/client.sh" 使用 screen 的原因是,我们可以将它切入后台。当我们和 10.0.1.11 的网络断开的时候,不会意外打断我们的测试。 因为测试可能要运行几个小时。
- 观察状态变化。当所有的客户端显示完成的时候,表示成功。

- 在 10.0.1.11 运行 命令,这个命令会让每个主机,对完成的结果校验,并将结果写入文件 运行以下命令启动校验结果 screen ansible all -a "$HOME/bin/checkdb.sh"
- 利用收集脚本将数据收集到 10.0.1.11 上面,把结果数据拖回本地
- 利用脚本,关闭所有的主机!这个每分钟都是钱 运行以下命令关闭所有的 ec2
7. 慢慢的整理结果
完毕
结果对比
数据分布
脚本总共生成了 100 万位用户,用户之间的相互关系 29741136 条,平均每位用户接近 30 条。其中每位用户在同一个 rg 的关系为 20 条,跨 rg 的关系为 10 条。每位用户向自己的好友发送 5 条消息,测试共产生了 1.4 亿条(148705680)条消息,并完全正确接受。经过验证数据的没有问题,每位用户都成功发送了消息,也成功接受了消息。 因为消息需要跨服务器进行交互,从侧面证明,系统不是单独在单机上运作,是全集群有消息交互的。
性能比较
1 台服务器 和 2 台服务器的数据可以见
4 台服务器处理 10 万用户, 40 台服务器处理 100 万用户 对比
可以看到 计数器显示,系统的吞吐数据有接近线性的增长,这表明软件原型 在 100 万级别有水平扩展的能力。
教训
仔细回想了一下,经验收获不多,但是教训有一些。列下来引以为戒吧!
1.数据注入成为瓶颈
最开始的设计,在 10.0.1.11 上将所有的数据准备好,然后导入 redis 服务器。开始一切都很好,当开始百万用户级别的时候,导入这些用户的时间就让人无法接受,每台主机需要接近 10 分钟才能导入完成。 40 台主机就是 400 分钟。这是极大的浪费。所以 流程改进为改完所有的数据文件,复制到每一台主机上,用 golang 的程序载入,基本做到了几十秒内完成。
教训: 大规模并发服务,任何地方都不能单点运行,当规模扩大了,缺陷也立刻被放大。
2.T2.Mircor 导致 CPU 挂起
一开始希望用低端的主机,实现"蚂蚁吃大象"的办法完成百万级用户测试,但是到最后的时候,因为 CPU 分数用尽,导致系统基本停止。最后只有换比较高端的主机。
教训 对系统的 CPU 使用情况没有仔细分析,对 AWS 主机分类理解不够
3.配置 bug 导致端口冲突
生成配置的脚本 bug ,导致某台主机的端口冲突,引起某个服务自动下线。最后在监控上发现服务数目不够,才查到了原因。
教训 监控需要更加智能,更细致。
4.网络不畅导致断线
连接 AWS 的网络连接并不稳定,结果某次断线,导致测试中断,最后重新测试
教训: 需要长期运行的程序 应该用 screen 这样的程序放到后台, 更好的办法是 service 化。 此外如果程序不是无状态的,就无法重试继续,需要对流程进行改进。
5.小细节导致流量暴增
本来监控程序的刷新频率,靠业务数据驱动,每次有更新就自动刷新,用户少的时候,没有问题。当 40 台服务器一起更新的时候,刷新速度就没办法看了,导致流量涨得太高。 只能改成每 3 秒刷新一下
教训 品质细节需要实践
6.进程部署是瓶颈
虽然使用了 ansible 分发程序,但是可以看得出分发过程,仍然是系统的瓶颈,同时也是个单点故障。这套部署架构并不适合更多的主机。
教训 大规模云计算系统里应该利用 p2p 进行程序部署,分发。
账单问题
AWS 的账单可以从这里看
账单的组成部分:
点击查看详单
流量部分
主机部分
价格可以从这里看
http://aws.amazon.com/cn/ec2/pricing/
总之,用完以后,立刻删除所有的资源!
最后提醒一下, AWS 的客服非常好!有任何问题都可以直接和他交流,可以很快得到解决。
如果觉得对项目有兴趣可以访问 https://github.com/xiaojiaqi/fakewechat 本文地址 https://github.com/xiaojiaqi/fakewechat/wiki/Stress-Testing-in-the-Cloud 会持续更新
如果觉得有收获,让我知道 0.01 元
支持一下你的项目 1.00 元