原本不想起一个英文名,可是想来想去都没能想出一个简洁地表述该意思的中文释义,因此就用了一个英文名称,望见谅。html
Cloud Native是一个刚刚由VMware所提出一年左右的名词。其表示在设计并实现一个应用时,软件开发人员须要尽可能使用云所提供的一系列较为先进的特性来提升应用的开发及部署效率,并使得应用的服务质量,如高可用性等,获得显著的提高。其并无一个定量的要求,而只是一种定性的思惟方式。那么对云所提供的哪些特性的使用能够提升应用的开发及部署效率,提高服务质量呢?数据库
因为网络上已经有了不少有关建立一个Cloud Native应用所须要遵照的一系列规则的讨论,所以咱们将再也不对这些泛泛的讨论进行讲解。而在本文中,咱们将以Amazon为例,讲解如何利用其所提供的一系列功能来作到Cloud Native。因为这只是一篇相似于简介的文章,所以我会控制在10页Word之内。缓存
云所带来的不一样安全
我相信的一点是,不管您是否开发过云应用,您对云至少会有多多少少的了解。本节将只对将会涉及到的云的特性进行简单地介绍。服务器
云所提供的是一系列虚拟化的资源,而这些虚拟化的资源则实际运行在一系列物理资源之上。相较于直接使用物理资源,云使用了额外的一层虚拟化层:网络
咱们都知道,额外的组成会带来额外的风险。这个多出的虚拟化层也同样。在使用物理资源时,操做系统直接运行在物理资源上。此时咱们所面临的风险有:物理资源的失效,以及在其上所运行的软件的失效。而在添加了额外的一层虚拟化层以后,咱们一样须要面对物理资源失效这一问题。并且因为虚拟化层所使用的操做系统或多或少都与原版系统有一些不一样,所以这些操做系统也经常具备较大的出错几率。除此以外,虚拟化层自身也有可能出现问题,例如虚拟化层管理软件失效等。所以运行在一个虚拟化环境中的独立组成经常会拥有更大的失效几率。架构
那运行在云之上的应用岂不是会有更多的宕机时间?答案是:这取决于应用究竟是如何设计的。若是一个部署在云上的应用和运行在物理资源上的应用的设计思路没有什么不一样,那么这个应用的确拥有更高的宕机几率。可是若是咱们能充分利用云所提供的一系列功能来完成应用的灾难恢复以及高可用性设计,那么该应用反而会提供更高的可用性。除此以外,咱们还能够在扩展性(Scalability,国内译法有歧义,没法与Extensibility区分),灾难恢复等一系列非功能性需求上获得显著地提高。框架
那这句“充分利用云所提供的一系列功能”该如何理解呢?运维
首先就是,在云上建立一台虚拟机每每比向咱们本身的服务集群添加一台物理机容易得多,也快速得多。在添加一台物理机时,咱们须要完成物理机的安装,布线,添加电力管理等一系列操做。甚至在手头上没有现成物理机的时候经由采购购买新的机器。所以从有了需求直到全部的环境准备完毕至少须要几个小时,甚至可能须要数个月的时间。若是物理机发生了损坏,如断电后没法成功启动,那么分析并解决问题也经常须要数个小时的时间。相比较下,在云上申请一台新的虚拟机则每每只须要几分钟。在须要一个新的虚拟机实例时,咱们只须要简单地向云服务提供商发送一个请求并等待几分钟就能够获得该实例。而在一个虚拟机发生了故障时,咱们也能够直接经过请求一台虚拟机来替换原有虚拟机的方式继续提供服务。而全部这一切经常只须要几分钟。tcp
除此以外,云平台所提供的自动化支持也经常是一个巨大的优点。试想一下,若是监控系统发现了应用中的某台虚机已经没法正常工做,那么它彻底能够向处理该状况的组成发送一个通知。接收到该通知的组成将向云平台从新申请一台虚拟机,并销毁原有的虚拟机。在自动化支持的帮助下,这一切彻底能够在数分钟内完成。因此基于云的服务经常拥有一系列脚本,以可以自动地进行灾难恢复,容量扩展等一系列本来很是耗时的操做。
而在这两点之上,云服务经常会提供一系列对服务开发人员进行支持的工具。最为常见的例子就是在云上部署用于开发及测试的环境。在云所提供的快速部署虚拟机以及自动化脚本的帮助下,软件开发及测试人员经常能够经过一键点击的方式来完成对特定版本应用的部署,进而在其上完成对新功能的开发及测试。而在再也不须要这些部署出的应用时,咱们也只须要一次点击就对这些应用所占用的资源进行回收。
除此以外,云还能帮助企业节省大量的资金。在自行搭建应用所运行的硬件平台的状况下,咱们首先要考虑的就是如何定义应用所须要的容量。若是容量过小,那么应用的负载将很容易地超过硬件容量,形成应用所提供的服务质量降低,甚至产生临时的没法提供服务的状况;若是容量太大,那么将有大量的处理能力将被闲置,从而形成资源的利用率很是低。而在云上的应用则不一样了。当应用负载处于波谷时,咱们能够缩减应用所使用资源的规模,以减小资源占用,提升资源的利用率,下降成本;而当应用的负载到达某个阈值时,咱们能够向云申请更多的资源。因为这些资源都是按实际的使用状况计费的,所以一个设计良好的Cloud Native应用将为咱们节省大量的资金。
固然,咱们只是列出了最为基本的几条。而在真正开发一个Cloud Native应用时,咱们不只仅须要了解这些基础的思路,更重要的是对云所提供的功能有所了解。只有充分地利用了云平台所提供的便捷功能,才能最大限度地保证云上应用的高质量运行。
另外须要插一句的是,Cloud Native无助于解决云所具备的Vendor lock-in问题,甚至是对该问题的解决有必定的影响。这是由于每种云都有一系列自身所特有的功能,而对特有功能的使用则会致使应用在云之间迁移变得较为困难。
基础设计
在设计时,一个Cloud Native应用就须要考虑如何使用云平台所提供的各类特性。这其中的不少特性其实是和运维有关的。一个最多见的例子就是如何对应用进行扩容。在以往的应用中,运维人员须要根据当前服务的负载来判断是否应用的现有容量可以应对全部的负载。若是现有容量只能勉强处理负载的峰值,那么他就须要开始着手准备对应用进行扩容了。可是在云上,咱们彻底能够将这些自动化:当当前服务的某个组成达到非安全负载时,监控系统会向服务发送一条通知,而通知的响应逻辑会与云进行通信以获得更多的容量。这一切功能都须要软件开发人员在应用设计时就将这些机制考虑进去,而再也不是交由运维人员负责。
软件开发人员在设计一个Cloud Native应用时所遇到的最大困难莫过于如何定义一系列合适的运维准则。这一方面和软件开发人员并不熟悉运维知识有关,并且就算知道了这些运维知识,也会由于传统运维经验和基于云的运维之间的差距而致使做为运维行为发生标准的各个阈值与最佳数值之间存在着较大的误差。
所以若是软件开发人员但愿可以开发出较为出色的Cloud Native应用,那么他必需要学习一系列和运维相关的知识。除此以外,他还须要将这些阈值设计为一系列能够被更改的配置文件,并经过一系列版本管理工具来记录这些修改。这样才可以较为容易地根据应用的实际运行对整个服务进行逐步调优。
而接下来的事情就是对整个产品进行架构设计了。鉴于Cloud Native应用对于高可用性以及扩展性(Scalability)的要求,一种常见的组织应用组织方式就是Micro-service。Micro-service中的最基本组成是各个子服务。这些子服务能够很容易地经过添加结点进行扩容,所以其对服务的扩展性支持得很好。同时经过向服务中添加冗余结点,咱们能够很容易地经过这些冗余结点构建具备高可用性的解决方案。有关扩展性以及Micro-service的讲解请看个人另两篇博客《服务的扩展性》以及《Microservice简介》。在这里咱们再也不赘述。
接下来,咱们就能够开始着手开发应用中的各个子服务了。首先要考虑的是,这些子服务在运行时的负载究竟是什么样的?那如今就让咱们以一个股票交易系统为例,讲解到底应该如何对应用所具备的负载进行处理。一般状况下,股票交易系统会在开市前的集合竞价阶段以及刚刚开市时的交投活跃阶段接收到大量交易委托;而在其它交易时间段,交易量将大幅降低;而在当日休市后,股票交易系统将只负责对一系列基本信息的读取操做。也就是说,该系统的负载是在不断变化并具备必定的时间规律的:
若是咱们自行搭建服务运行所须要的物理环境,那么咱们就须要保证该物理环境的容量大于可能产生的特殊状况下的峰值负载。而该值将远大于一般状况下的峰值负载:
能够看到,这种方法要求咱们将服务所提供的容量定义得远远超出实际需求,而仅仅是为了可以在服务迎来超级峰值时能为用户提供优质的服务。也就是说,咱们须要为了发生几率很是小的事件提供了远超过实际需求的容量。
而大多数云所能提供的快速增长/减小容量的功能则最适合用来处理这种容量变化的状况。就让咱们以一个负载波峰为例展现云是如何根据自身负载来对容量进行控制的:
上图中展现了一个基于云的应用所须要的容量随着负载发生变化的状况。能够看到,若是当前系统的负载达到了系统当前容量的扩容阈值,那就表示系统的当前负载已经接近当前的容量极限。为了不因为系统的负载超过系统容量而致使没法为某些用户提供服务,软件将向云发送扩容通知,并在几分钟后得到云平台所提供的新增长的容量。而在负载降低时,系统的负载将可能触及缩容阈值。此时软件将要求云平台对其部分容量进行回收,从而减小对资源的占用,以下降应用的运营成本。
总的来讲,基于云的应用在运行时将根据实际负载来决定自身的容量,而云自身将只对应用所消耗的容量进行计费。所以其实际上大大地下降了运行该应用的实际成本。
而Amazon所提供的一系列虚拟机实例购买方式则可让应用的运营成本进一步下降。其所提供的虚拟机购买方式以下所示:
那么对于上图所示的具备周期性负载的服务,咱们就能够经过一系列购买组合来减小咱们运行服务所须要的成本:
从上图中能够看出,对于一个负载具备周期性变化的资源,其中用来提供服务的虚拟机实例经常是由经过不一样方式购买的虚拟机实例共同组成的:Reserved实例所具备的容量只略大于用来处理负载波谷时期的能力,而且全天都处于服务状态下;而Scheduled实例将在特定时间内提供服务,是处理高峰负载的主力。可是有些时候,服务所接受到的瞬间负载经常会超过这两种资源所拥有的容量。此时用来提供服务的即是On-Demand实例。
固然,服务是不断发展的。当服务得到了愈来愈多的用户,其所对应的峰值负载等都会有相应的增长。此时咱们就须要根据实际状况更改每种购买方式的购买量。
因为不一样的云所提供的虚拟机实例购买方式并不相同,所以在建立您本身的Cloud Native应用时,您须要根据该云平台所实际提供的虚拟机销售方式设计一套方案,以获取相对较低的运行成本。
如今咱们有了用于运行应用所须要的各个虚拟机,下一步就是设计到底应该如何将它们组织在一块儿以提供服务了。一个传统的Web应用所常具备的结构以下所示:
上图展现了一个传统的Web应用所具备的最基本架构。其主要由Web Server,App Server以及数据库组成。Web Server主要用来处理HTTP请求,App Server则用来完成应用在提供服务时所须要处理的操做,而数据库则用来存储数据。
而在Amazon上定义的应用所具备的基本架构则会有一点不一样:
能够看到,基于Amazon的应用对虚拟机实例的组织方式与传统的Web应用的物理机组织方式基本相同。惟一不一样的是,防火墙的位置是在Elastic Load Balancer以后了。这是由于在Amazon中,防火墙的功能主要是经过Security Group完成的。
固然,除了这些功能以外,您还可使用如下一些功能来提升应用的性能:
提升了应用的性能便可以减小系统运行所须要的资源,从而下降了应用的开销。
Day 2 Operation的支持
在这一节中,咱们会介绍与云应用维护相关的一系列相关功能。这些功能会自动地被触发,并自动地对脚本进行执行,从而使得运维变得简单高效。
这一切的核心主要是CloudWatch。在运行时,每种AWS资源都会将一系列运行指标定时地保存在一个被称为Repository的数据容器中。除此以外,用户还能够在这些Repository中保存一系列自定义的指标。在用户须要的时候,软件开发人员能够经过特定的API调用读取这些指标。若是软件开发人员但愿可以在某个指标到达某种状态时自动执行某些运行逻辑,那么他就须要使用CloudWatch的Alarm功能。这些Alarm会监听指定的指标,并在指标到达特定条件时发送一个通知到Amazon SNS或一个Auto Scaling Policy之上,进而执行相应的处理逻辑:
如上图所示,有了监控,咱们就能够根据系统状态探测并解决系统出现的问题了。这些问题可能包含有系统过载,虚拟机实例失效等。一旦CloudWatch发现了问题,它就能够经过Amazon SNS发送通知消息的方式来促使相应的组成来执行用来解决这些问题的脚本。
而对于一些经常使用的解决方案,如虚拟机实例的横向扩展以及灾难恢复,Amazon则提供了一系列解决方案。例如在须要对容量进行扩展时,最“Cloud Native”的方法就是Auto Scaling Group了。能够说,这是Amazon所具备的特有功能(Openstack如今有一个Proposal)。在建立一个Auto Scaling Group时,软件开发人员能够标示其所管理的实例类型,每一个实例所使用的AMI,以及其能够包含的实例个数的最大值,最小值以及默认值。固然了,对于这样一组实例,其天然须要一个负载平衡服务器来完成对请求的分发。为此,软件开发人员只须要在配置中设置好须要使用的负载平衡服务器实例便可。而在服务运行过程当中,若是负责监控的CloudWatch发现Auto Scaling Group中的某些实例负载太重,那么其将能够发送一个Alarm并由Auto Scaling Group执行对它的响应:
除此以外,Auto Scaling Group还能够帮助咱们实现N+1冗余,以帮助咱们的应用实现高可用性。简单地说,就是N个可以正常工做并处理现有负载的实例由N+1个实例所共同负担。在一个处于Auto Scaling Group中的实例失效时,其它N个可以正常工做的实例仍可以向用户提供正常的服务。因为Auto Scaling Group会自动探测失效的实例并将从新启动一个实例来替换失效的实例,所以在数分钟以后,Auto Scaling Group将会从新拥有N+1个可以正常工做的实例。
而Amazon所提供的另外两个功能,存储在S3上的AMI以及EBS存储则能够帮助咱们进一步加快这个实例替换的过程。试想一下一个全新的物理机要达到工做状态须要作什么样的工做:首先要将物理机设置完毕并启动,而后安装并配置操做系统,最后安装并配置其所须要的软件,甚至还须要经过数据库日志或运行脚本等一系列方式进行预热。这一切都须要不少时间不是么?可是在AMI以及EBS存储的帮助下,这一切将会缩短到几分钟:
上图中展现了一个Auto Scaling Group中的一个实例出现故障时是如何对其进行恢复的。在一个虚拟机实例出现故障时,其将首先被从Auto Scaling Group移出,而且与之关联的EBS存储也将与之解除关联。该存储上可能记录了日志等一系列有关运行的数据。接下来,Amazon将经过预先配置好的AMI从新请求一台虚拟机。该AMI不只仅包含了该虚拟机运行时所须要的操做系统,更包含了虚拟机运行时所须要的一系列配置好的组成,如其运行时所须要使用的Servlet Container以及运行于其上的Source Bundle(WAR包等)。这样一旦建立完毕,虚拟机中的大部分软件就已经被部署好了。这大大地减小了从新建立一台虚拟机所须要的时间。接下来,Amazon将会把刚刚从损坏的虚拟机上解除关联的EBS存储与新建立的虚拟机相关联,并将其添加到Auto Scaling Group中。这样Auto Scaling Group就拥有了原有数量的虚拟机。全部这一切都将在虚拟机发生故障后的几分钟内完成。
固然,一个AMI中到底包含了多少预约义信息也会影响虚拟机的启动速度。例如对于一个包含了操做系统,Servlet Container以及应用代码的AMI,Amazon只须要经过该AMI建立一个虚拟机并启动它便可。而对于只包含了操做系统的AMI,其启动以后还须要安装运行子服务所须要的一系列软件,从而可能须要较长的时间。反过来,一个包含了操做系统,Servlet Container以及应用代码的AMI经常须要更多的维护工做。所以到底如何制做并维护AMI也是一个蛮有意思的话题。只是因为该话题离Cloud Native较远,所以咱们在这里将再也不详述。若是您对此感兴趣,请参考Amazon论文《Managing your AWS Infrastructure at Scale》中的“Provision New EC2 Instances”一节。
反过来,让咱们回想一下基于物理机的灾难恢复解决方案:在一个基于物理机的系统中,若是其中一台物理机再也不正常工做,咱们经常须要访问这台物理机,并尝试找到发生异常的缘由。有时候咱们还须要经过尝试从新启动系统等一系列操做来尝试恢复其工做。若是实在不行,那么咱们就须要从新在该物理机上安装软件。之因此这么作,是由于咱们只有有限的物理机,而且从新在物理机上建立系统是一个很是麻烦的事情。可是在云的帮助下,这个问题的解决方案就将变成“丢掉之前的,几分钟以内就能建立个新的”这种简单的逻辑。
也就是说,云的某些特性将显著地更改一系列解决方案的解决思路。Cloud Native应用须要充分地利用云所提供的这些功能,以提升效率。那这些物理机中所没有的特性有哪些呢?虚拟机的快速建立,更多更强的内置管理工具以及对自动化脚本的更好的支持。
这些特性会进一步发展为更高一层次的优势。就以虚拟机的建立为例:因为咱们能够在云上快速地建立一台虚拟机,并且在再也不须要时直接丢弃该虚拟机,而不像物理机时代须要几个小时甚至几天才能设置好。所以基于云的应用经常具备“灵活性”这一特征:虚拟机想要就请求,不要的时候就删除。
这些特性更能够进一步发展,从而推出一系列云所特有的解决方案。上面所介绍的基于Auto Scaling Group的吞吐量管理以及灾难恢复就是其中一个实例。
开发Cloud Native应用
在有了合适的设计以后,咱们就能够开始计划开发您的Cloud Native应用了。此时咱们能够从云平台上获得的好处有:原生云管理软件的支持,DevOps支持,甚至一些Cloud Native Framework等。
Amazon为咱们提供了一系列用来对资源及应用进行管理的组件。迄今为止,这些组件有:CloudFormation,Beanstalk以及OpsWorks。三者的定位各有不一样。
CloudFormation用来对云上的资源进行管理。首先,用户须要经过一个模板来描述所须要的全部种类的AWS资源以及这些资源之间的关系。一个简单的CloudFormation模板以下所示(自Amazon CloudFormation官方文档):
1 { 2 "Parameters" : { 3 "KeyName" : { 4 "Description" : "The EC2 Key Pair to allow SSH access to the instance", 5 "Type" : "AWS::EC2::KeyPair::KeyName" 6 } 7 }, 8 "Resources" : { 9 "Ec2Instance" : { 10 "Type" : "AWS::EC2::Instance", 11 "Properties" : { 12 "SecurityGroups" : [ { "Ref" : "InstanceSecurityGroup" }, "MyExistingSecurityGroup" ], 13 "KeyName" : { "Ref" : "KeyName"}, 14 "ImageId" : "ami-7a11e213" 15 } 16 }, 17 18 "InstanceSecurityGroup" : { 19 "Type" : "AWS::EC2::SecurityGroup", 20 "Properties" : { 21 "GroupDescription" : "Enable SSH access via port 22", 22 "SecurityGroupIngress" : [ { 23 "IpProtocol" : "tcp", 24 "FromPort" : "22", 25 "ToPort" : "22", 26 "CidrIp" : "0.0.0.0/0" 27 } ] 28 } 29 } 30 } 31 }
能够看到,上面的模板将用来建立一个EC2实例以及一个Security Group,并将其添加到刚刚建立的Security Group中。在使用该模板的时候,软件开发人员能够经过KeyName参数传入建立虚拟机时所使用的KeyPair。
在用户经过该模板建立资源时,CloudFormation会分析该模板中所记录的信息,并据此来分配并配置资源。若是软件开发人员对该模板进行了修改并提交,CloudFormation会根据用户所修改的配置对已经部署好的资源进行更新。一样地,咱们也能够经过CloudFormation删除已经部署好的资源,那么这些以前分配好的资源都将被删除。
而Beanstalk则主要用来完成简单应用的部署。在使用Beanstalk在云上部署应用时,咱们只须要上传该应用的Source Bundle,如WAR包,并提供一系列部署的信息,就能完成对应用的部署。此时用户并不须要关心资源分配,负载平衡,应用的容量扩展以及应用的监控等一系列问题。若是须要对应用进行更新,咱们只须要上传新版本的Source Bundle并指定新的配置便可。在部署完成之后,咱们就能够经过一系列管理工具,如AWS Management Console,对这些部署好的应用进行管理。
OpsWorks则是最为强大也是最为复杂的应用管理工具。软件开发人员能够为须要部署的应用定义一系列Layer,每一个Layer表示一系列用于特定用途的EC2实例,如数据库实例。每一个Layer中能够包含一系列Chef recipe,以用来在特定生命周期,如Setup,Configure,Deploy,Undeploy以及Shutdown等事件发生时执行特定任务,从而容许软件开发人员指定在这些生命周期执行的自定义逻辑。由于它是如此经常使用,所以我在想是否是有机会专门为该工具写一篇介绍的博客。
而这一系列部署工具一样也构成了基于AWS的DevOps的基础。再加上一系列其它代码管理工具如CodeCommit以及CodeDeploy等将能够构成完整的DevOps解决方案。由于我对CodeCommit以及CodeDeploy等产品了解并很少,所以在这里不加以详细介绍。若是但愿对基于AWS的DevOps有更深刻的了解,请看Amazon的一篇文章《Introduction to DevOps on AWS》。
除了这些以外,最近兴起的一个有关Cloud Native的话题就是Cloud Native Framework。如Airavata等。这些框架经常将一系列云所提供的功能包装起来。这样软件开发人员就能够将精力集中于业务逻辑的开发,而再也不须要过多地关心如何正确地使用云这一类问题。有兴趣的读者能够持续地关注这一方面,毕竟是一个新兴起的符合大趋势的方向。
更多资源:
Cloud Native Blog@vmware: http://blogs.vmware.com/cloudnative/
Cloud Native Computing Foundation:https://cncf.io/
转载请注明原文地址并标明转载:http://www.cnblogs.com/loveis715/p/5185367.html
商业转载请事先与我联系:silverfox715@sina.com
公众号必定帮忙别标成原创,由于协调起来太麻烦了。。。