如何使用阿里云
如何使用阿里云 前言大家好。我们是成都瑞小博科技 (www.rippletek.com)。自从去年10月在阿里云购买了第一台ECS 并部署服务后,到现在已过去了一年。在这一年间,随着业务的扩张和用户规
如何使用阿里云 前言
大家好。我们是成都瑞小博科技 (www.rippletek.com)。
自从去年10月在阿里云购买了第一台ECS 并部署服务后,到现在已过去了一年。在这一年间,随着业务的扩张和用户规模的增长。我们的ECS 数量从1台增长为20台,并开通了SLB , RDS , OSS, CDN,OCS, SLS, MQS等多项业务。在这一年中,通过工单系统得到了阿里云的技术支持团队和开发团队的大量帮助和指导。在" 应该如何使用阿里云" 这个问题上,也积累了一些心得和经验,希望和大家分享,抛砖引玉。
初探ECS
使用阿里云的第一步, 当然是购买一台ECS(后面称为ecs1) 。这台ECS 应该是什么样的配置呢?一般情况下,我们建议的最低配置是单核,2G 内存。如果只有1G 的内存,运行阿里云的一键lamp 安装脚本可能会oom 。操作系统,如果是从头开始建站,建议使用Ubuntu 14.04. 相比CentOS 6.5, Ubuntu的内核版本更高,能玩的花样也更多(比如
docker) 。带宽的话,1M 其实就够了。无论如何,不要超过5M 。根据阿里云的带宽阶梯计价公式,1M 带宽的月单价是21元,2M 比1M 多23(即44元,后面类推) ,3M 比2M 多25, 4M 比3M 多27, 5M 比4M 多29, 而一旦超过5M , 每多1M 带宽,价格就多100元! 所以,带宽越高,每M 的单价也越高。同时,对于需要高可用的服务,根本不可能通过ECS 的外网带宽开出去。所以,购买1M 带宽,获得一个外网IP ,就足够了。至于数据盘,一般情况下,你不会需要它。ECS 购买完成后,你会收到阿里云的短信通知,发给你root 密码。用那个密码登入ECS 后,应该做的第一件事是加入authorized_key并删除root 密码:
复制代码
1.
2.
3.
4.
5. mkdir .ssh chmod 700 .ssh vi .ssh/authorized_keys #加入自己的id_rsa.pub chmod 600 .ssh/authorized_keys passwd -d root
这样,可以在根本上杜绝root 密码被猜中的可能性。
初探SLB
第二步,购买一个公网的负载均衡器SLB(后面称为slb1) 。如果你的域名已申请好,可以把域名指向slb1了。为了保证服务的高可用性,服务一定要通过SLB 开出去。设想一下,如果你的服务是走单台ECS 出去,某天你需要修改一下apache 的配置,修改完毕后,service httpd restart却发现httpd 进程没有起来 (由于httpd.conf 里有个小小的笔误..) 。事实上,这个时候你就已经停服了!这也是为什么前面建议不必购买高带宽ECS 的原因。
为了避免出现上面提到的那种尴尬的情况,SLB 的后端服务器至少要有两台ECS 并配置好health check。 尽管我们现在只有ecs1,如果上面的服务环境已经部署ok, 就先把它加入到slb1的后端服务器组里,然后在浏览器里输入我们的域名开始测试吧!然后,我们还需要另一台ECS 。
再探ECS
,第三步,再购买一台ECS (后面称为ecs2)。这一次,如果我们的业务代码本身不用从internet 上获取数据的话,我们可以试试内网ECS ,即0M 带宽的机器。这样的机器没有带宽费用,会便宜一些,更重要的是,它没有公网IP ,所以也更安全。下面问题来了: ∙
∙ 它没有公网IP ,我如何ssh 上去? 它无法访问internet ,我如何使用yum, apt这类包管理器来搭建业务环境? 对于第一个问题,有两个解决办法:
1.
2.
∙
∙ 先ssh 到有公网IP 的ecs1上,然后再ssh ecs2的内网IP ,搞定 也可以通过一些配置,实现内外网无感知的直接ssh 上去,方法如下: 在ecs1上安装nc 工具,并修改/etc/hosts, 加入 ecs2
复制代码
1. [li][li][li][li][li][li][li][li][li]Host ecs2[/li][li] Proxy
Command ssh root@ecs1 exec nc h p[/li][/li][/li][/li][/li][/li][/li]
[/li][/li]
在本地终端的/etc/hosts中加入 ecs1
然后,ssh root@ecs2 即可直接登录ecs2
对于第二个问题,也有两个解决办法: ∙
1. 在ecs1上架设如privoxy 一类的http 代理,然后在ecs2的/etc/bashrc文件中加入这
行代码 export http_proxy="http://ecs1:
2. 给ecs1的系统盘做个磁盘快照,并建立一个自定义镜像,然后对ecs2使用“替换系
统盘”的操作把系统盘替换为我们刚刚创建的自定义镜像就可以立即获得和ecs1完全一样的系统环境!
我们一般是把上面两个办法结合起来使用,快速搭建环境。在ecs2环境ok 后,也将它加入slb 的后端服务器组。至此,我们消除了ecs1的单点,再也不用为重启web server这种事情纠结了。
但是ecs2并没有公网IP ,如何才能访问它以确认服务OK? 有两种办法:
1.
2. ssh tunnel. 在测试机器test 和ecs2分别建立ssh tunnel到ecs1的同一端口对接起来. 建一个测试用的公网SLB 作为代理网关,里面只放ecs2一个节点。用公网SLB 的
IP 就能访问ecs2了。显然,第2种办法要简单得多,所以我们一般用这种办法 :) 在系统设计上,方便性和安全性存在冲突,内网ECS 亦是一例。在进阶篇 中,我们会进一步讨论内网ECS 的优缺点。
分布式计算的几个基本概念
在继续我们后面的云端飞行旅程之前,我先介绍几个分布式计算的基本概念。阿里云平台提供的几个基础服务正是为了解决这几个问题才开放出来的。
1. Single Point Failure (SPF), 单点故障。在一个服务系统中,因为一个节点的故障,导
致整个系统不可用。例如上面提到的网站域名指向ecs1的IP ,但ecs1上的web server restart 失败的情形
2. Redundancy ,冗余。为了解决SPF ,在系统的关键路径上,必须存在两个或更多的
选择。即当一个节点失效后,仍有其他的节点可以继续提供服务。
,3.
4. Stateless Node,无状态节点。为了让多个计算节点具有完全一致的行为,单个节点上面一定不能有自己独有的状态信息。 Load Balance, 负载均衡。多个计算节点共同承担系统负载。
SLB 这一工具已经解决了1,2,4这三点。那么,我们如何从ECS 上抽离状态信息以实现无状态节点呢?为此,阿里云提供了另外两个工具:RDS 抽离动态数据和OSS 抽离静态数据将ECS 变为无状态的计算节点。可以把RDS 当成一个超大型的Mysql 数据库集群,OSS 当成一个超大型的文件存储集群。
RDS 和OSS
我们先讨论RDS 。虽然阿里云提供了lamp 的一键安装包sh-1.3,但事实上,本地的mysql 服务是不需要的。RDS 的可靠性,易用性和可扩展性都比自己搭建的mysql 服务器要好很多。如果你仍在使用自己的mysql 数据库,强烈建议迁移到RDS 。
再说说OSS 。ECS 的本地磁盘上只应存放业务代码和配置,20G 的系统盘完全够用,这就是为什么前面不建议购买数据盘的原因。用于下载或用户上传的数据文件都可以存到OSS 中。
对于一个基本的建站业务而言, 将动态数据存RDS ,静态文件存OSS ,就实现了ECS 的无状态。在这样的框架下,可以方便的对系统扩容:
1.
2. 当访问量变大,现有计算资源紧张时,对ECS 进行横向(增加ECS 的节点个数) 或纵向(增加单个节点的CPU 核心和内存) 扩展 如果数据库访问出现瓶颈,升级RDS 实例至更高配额
CDN 和OCS
后面,很自然的可以开通CDN 为OSS 的访问加速。这一点,从定价上不难看出OSS CDN是阿里云希望用户使用的方式。OSS 的流量是0.8元/GB,而CDN 是0.4. OSS通过CDN 出去,不仅访问速度更快,还能降低成本。
如果RDS 中有一部分数据的读取频率比更新频率高很多,可以通过将这部分数据缓存入OCS ,在提升系统响应速度的同时缓解RDS 的读取压力。RDS OCS业务代码的实现逻辑:
1.
2.
3. 如果要从RDS 的表table0中读取主键为id 的数据项,先尝试从OCS 中读取key="table0_id"的数据,如果命中,则使用从缓存中读取的数据,不用再访问RDS 如果缓存不命中,访问RDS 读出数据v ,以key="table0_id", value=v写入OCS 当table0中的id 数据项被变更或删除的同时,删除OCS 中key="table0_id"的数据
小结
综上,我们介绍了如何使用阿里云提供的ECS,SLB,RDS,OSS,CDN 和OCS 这6个业务来构建我们自己的高可用业务网站系统。它的基本结构如下图所示:
,
几点说明:
1.
2.
3.
通过外网SLB 的IP 向外提供服务,用户请求通过SLB 分发到后端的几个ECS 来计算处理 利用RDS 和OSS 来抽离状态数据,使得ECS 成为无状态的计算节点 可以利用OCS 缓存RDS 的数据, CDN 缓存OSS 的数据,提高访问速度
前情提要及概述
在基础篇中,我们介绍了如何利用阿里云的几个基础服务: ECS , SLB, RDS, OSS, CDN 和OCS 来构建一个高可用的业务网站系统。在本篇中,我们将进一步介绍上面这些基础工具,以及如何从单业务系统拓展到多业务系统,和日常开发和运维的一些常用技巧。
多业务系统之间的交互手段
我们从几个具体的case 说起吧 :)
case #1 利用消息队列实现的固件定制系统
,
如上图所示,先是由一个web 前端的表单系统将用户的输入参数组装为一条消息放入固件生成的请求队列中,后面由固件构建集群取得用户的配置参数,生成固件后存入OSS ,再将生成的结果放入结果消息对列中,前端系统获取结果后更新RDS 的状态。
我们可以利用阿里云提供的MQS 服务非常方便的在两个业务系统之间实现用消息队列异步传输小尺寸数据。如果尺寸较大,亦可以通过往RDS/OCS或OSS 中写入临时数据,用消息队列传输key 或url 来解决。
case #2 利用ODPS/RDS实现的非实时数据分析系统
,
ODPS 是一个阿里云上的接口类似Hadoop Hive的数据分析系统。我们可以部署多个数据收集节点,将数据存入ODPS 。再搭建一个数据分析集群,定期对写入ODPS 的新数据进行提取,然后将提取的结果放入RDS 。最后由一个web 前端系统读取RDS 中的数据生成报表呈现给最终用户。
这种reader/writer的模式是两个业务系统之间通信的常见方式,只要是两个系统之间可以共享的系统资源,都可以通过一端写入,另一端读出来实现通信。而在阿里云的系统设计中,同一账户下的ECS 可以共享RDS ,OCS, MQS, OSS, ODPS这些资源。我们应当针对不同的应用场景选择合适的资源类型加以利用。
case #3 利用OCS/内存数据库构建实时数据分析系统
,
web 前端系统接受用户查询请求后,先查找OCS 是否有缓存的结果,如果cache 命中则直接返回结果。如果cache 不命中,调用后端数据存储集群的web api. web api负责查询分布式内存数据库并计算分析后返回统计结果。前端系统拿到查询结果后,用查询参数hash 出一个key ,将查询结果作为value 存入OCS 中。注意:该系统的实时性在很大程度上取决于OCS 缓存的expiration. 应依据业务特点设置合适的expiration 值。如果对结果的实时性要求很高并且后端数据存储集群的计算性能有充分安全边际的情况下,也可以移除OCS ,每次都重新提取数据计算结果。
同样,web api系统也务必消除单点。在这里,我们可以使用内网SLB 解决。
再探SLB
在基础篇中我们介绍过外网SLB ,并强调一切对外服务一定要通过外网SLB 开放出去以消除单点。同样的,所有的系统内部通信web api也一定要通过内网SLB 访问。内网SLB 和外网SLB 的区别在于内网SLB 只有内网IP ,没有外网IP ,所以无法从internet 上访问到。另外,内网SLB 没有实例费和流量费,所以一定要多多的用起来!
SLB 有两种监听转发方式, TCP 和HTTP ,一般情况下,web 服务都采用http 的转发方式,使用cookie 来保持会话,这样即使在应用中使用本地文件来保存session ,也不会成为问题。唯一的例外是给网站开启CDN 时,为了消除CDN 回源的单点,自然的,我们不能用单台ECS 来回源,应考虑使用SLB ,然而,如果使用HTTP cookie保持会话,
,CDN 会由于页面带了cookie 而拒绝缓存。这种情况下,只能使用无会话保持的HTTP 转发或TCP 转发。
小结
至此我们展示了几个多业务系统的具体架构。云计算的组件组合方式可以是多种多样的。然而,在构建高可用系统这个问题上,有几个基本原则可以参考:
1.
2. 务必消除单点。(如果读到这里您仍不理解什么是单点,请再看一遍基础篇 ) 尽量使用阿里云提供的系统服务,不要自己用ECS 进行重复建设。例如,使用RDS ,
而不是自己搭建mysql 集群; 使用OCS , 而不是自己搭建memcached 集群;使用OSS , 而不是自己搭建文件服务器;使用ODPS , 而不是自己搭建Hadoop Hive; 使用MQS, 而不是自己架RabbitMQ... 一是可以大幅降低投入,二是尽可能的把高可用问题交给阿里云的运维团队,而不是自己的运维团队解决,会有更佳的效果。
3. 设计异常恢复机制。任何系统都有可能会出现各种异常,阿里云也不例外。例如: ECS
的宕机迁移会使ECS 实例重启,最好在系统启动时即自动启动服务;RDS 和SLB 都有可能出现闪断的情况,需要自动重连;甚至云服务节点间的内网通信也有可能中断,导致内网SLB 失效以及分布式数据库brain-split 这类对服务质量有很大影响的问题,所幸在这一年里我们只遇到过一次这样的故障。
4. 安全平稳的线上代码变更。不管基础系统架构多么完美稳定,如果运行在上面的业
务代码剧烈震荡,系统的可用性也还是个问题。所以在本篇的最后,我再介绍一下 RippleTek 的上线流程
我们的每一个服务都是通过至少一个外网SLB 开放出去的。在每个SLB 的后面,至少有两个主服务节点SRV1和SRV2。另外,还有一个线上引流测试节点pilot 。当需要线上代码进行变更的时候,先将pilot 下线 (使用slb api将它从slb 中移除,或者在控制台中将它的权重设为0. 这时你可能会问两个问题: 1) 把节点的权重设为0和直接将节点从slb 中移除的区别是什么? 2) 为什么不用slb api将它的权重设为0? 这两个问题的答案请见下方的Q&A),在pilot 中的代码或配置变更不会对线上服务产生影响。同时,我们有一个测试专用的SLB_TEST,后端服务器就只有一个pilot ,自己测试就用SLB_TEST的IP 来做。功能测试OK 后,把pilot 重新加入线上服务的SLB ,导入5流量,持续观察日志5分钟看是否有异常情况。如无异则一小时后再观察。如一切正常,就将变更部署到该业务的全部主服务器上。部署后密切观察线上日志和监控,如有异常,先回退变更,再结合异常日志调查原因。该流程的有效性在很大程度上依赖于pilot 的环境配置和SRV1/2的一致性,务必保证它们的环境是完全一样的!
到这里我们的旅程也暂告一段落了。稍事休息,更多精彩和乐趣将在 应该如何使用阿里云?(高级篇) 中呈现。 敬请期待。
Q&A
∙ 把节点的权重设为0和直接将节点从slb 中移除的区别是什么?
把节点A 的权重设为0可以让SLB 不再转发新的请求到A ,但已经调度到这个服务器的连接继续保持,直到这些连接全部结束。而直接将节点A 从slb 中移除会导致已经调度到这个服务器的连接中断,可能会对服务质量有细微影响。
∙ 为什么不用slb api将它的权重设为0?
目前最新的slb api v20140515 尚未提供后端分发节点的权重设置。
,