Spinnaker 是 Netflix 在2015年开源的一款持续交付平台,它继承了 Netflix 上一代集群和部署管理工具 Asgard:Web-based Cloud Management and Deployment的优点,同时根据公司业务以及技术的的发展抛弃了一些过时的设计:提高了持续交付系统的可复用性,提供了稳定可靠的API,提供了对基础设施和程序全局性的视图,配置、管理、运维都更简单,而且还完全兼容 Asgard,总之对于 Netflix 来说 Spinnaker 是更牛逼的持续交付平台。
在深入了解 Spinnaker 之前,先扯一扯 Netflix 的技术文化:这是一家全面拥抱云的公司,据报道数据中心完全部署在 AWS 上,是 AWS 的超级大客户。在上云后他们发现故障仍然避免不了,为了更加从容的应对这些故障,就搞了一个工具 Chaos Monkey 会随机停止生产环境中的虚拟机,通过观察系统在真实故障中的表现来确保程序的健壮性,也通过实战来验证各种高可用技术是否靠谱。接着冒出了 Chaos Gorilla,会停止一整个可用域中的所有机器;最后还有Chaos Kong,直接停掉一整个 Region,非常有挑战精神(丧心病狂)。
为了更好的观察系统在故障时的情况,还研发了全局可视化系统,代号 Flux,可以将整个系统的逻辑架构和各服务之间的流量可视化在大屏幕上,效果图如下:
他们每个月有一个活动:将一个 Region 里的机器全部关掉,看 Netflix 服务是否正常。有兴趣看视频的可以移步这里。
另外,Netflix 除了云服务,还有自建CDN,即 Open Connect 项目,这个项目的边缘设备是地地道道的物理设备,并且从硬件到软件全部是自己定制的。关于 Open Connect 的详细介绍,以及使用的技术栈可以看 Netflix 的分享,还有他们如何做 CDN 监控的。
主要功能
回到 Spinnaker,他主要管理 Netflix 的云服务,并不管理 OpenConnect 相关的设备和服务。Spinnaker 是基于云的 CD 平台,提供快速、可靠、稳定的软件变更服务。主要包含两类功能:集群管理(Cluster management)和部署管理(deployment management)。
1. 集群管理
集群管理主要用于管理云资源,Spinnaker 所说的“云”可以理解成 AWS,即主要是 IaaS 的资源,比如 OpenStack,Google云,微软云等,后来还支持了容器,但是管理方式还是按照管理基础设施的模式来设计的。
Spinnaker 中管理如下资源:
Server Group:最基本的逻辑资源,包括了若干使用相同配置和镜像的虚拟机,若干负载均衡(load balancer),以及安全组。
安全组规则(Security Group):就是 AWS 中的安全组,可以理解成防火墙。
负载均衡(Load Balancer):AWS 中的 ELB,也可能是安装在虚拟机中的负载均衡。
2. 部署管理
管理部署流程是 Spinnaker 的核心功能,他负责将软件包(可能是手工创建的或者 jenkins 创建的)打成一个镜像,用这个镜像生成对应的虚拟机,让服务真正运行起来:
pipeline
在 Spinnaker 中一个部署流程叫做pipeline,由若干个操作组成,每个操作又叫做一个 stage
。触发一个 pipeline 方式非常灵活,可以手动触发,也可以用 jenkins、CRON 等。同时,可以配置 pipeline 向外发送一些通知信息,比如“开始”,“结束”,“失败”等。
stage
pipeline 中的一个操作,stage 之间可以有先后顺序,也可以并行。Spinnaker 中预定义了一些 stage 的类型,这些类型的 stage 往往使用频率比较高:
- Bake:在某个 region 中制作虚拟机的镜像。Netflix 推崇不可变基础设施的理念,所以他们将软件打包进镜像的方式来部署服务。创建镜像的核心基于 Packer(Hashicorp 开源的镜像烘焙工具,Vagrant 就出自该公司 CEO 之手)。如果部署时用 docker,则打包过程就交由
docker build
完成。 - Deploy:用 Bake 中创建的镜像部署成一台虚拟机。
- Jenkins: 执行一个 Jenkins 的 job。
- Manual Judgment : 暂停,等待用户的许可后再继续。
- Pipeline : 执行另外一个 pipeline。
- Script :执行任意的脚本。
- Wait : 等待一段时间。
从 pipeline 的定义看,Spinnaker 和 Jenkins 有几分相似,不过两者的设计出发点的不同,stackoverflow上有相关的讨论。总结来看,jenkins 偏向 CI,产出物是软件包;Spinnaker 是 CD,将软件包分发到服务器/虚拟机上,保持软件正常运行,它的目标只是让“部署”的过程更容易更可扩展。有一个例子可以说明两者的关系:Netflix 内部有人不用 Spinnaker 的 pipeline,而只是将 Spinnaker 看为一个部署工具,直接在 jenkins 中调用它的 API 来部署服务。
逻辑架构
Spinnaker 自己是一个微服务架构,由若干组件组成,所有组件都开源在github上,整个逻辑架构如下图所示:
Deck:AngularJS 写的 WebUI。
Gate:提供 API 接口给外部程序,Deck 也是其中之一,Spinnaker 的大门。
Cloud Driver:对接各种云服务提供商,比如AWS, GCP, Azure 等。她负责所有对这些云服务的读写操作。
Orca :处理 pipeline 和任务编排,比如创建一个虚拟机,等待它创建完成,然后执行其他操作。
Rosco 基于 Packer 的镜像创建服务,她将一个 Debian 或者 RedHat 的包封装到虚拟机镜像中,这个过程有点像烘焙,所以也叫 image bake。
Front50 存储所有pipeline,应用,通知的原信息。
Igor 对接 Jenkins 的服务,比如 pipeline 中需要调用 jenkins,那么就依赖这个服务。
Echo 提供通知服务,对接各种各样的服务商:Slack, Hipchat, SMS (via Twilio) , Email。
Rush 脚本执行引擎。
管理方法
Spinnaker 看起来也是一个复杂的微服务架构,由不少服务组成,所以本身也遵循一些运维准则:
- 每个 Spinnaker 的服务(如 deck,gate,orca)都运行在独立的 cluster 中。
- 每个服务都将自己的运行指标推送到 Atlas 中,用于绘制仪表盘和报警。Atlas 是Netflix的一个内存时间序列数据库。
- 每个服务都将自己的日志发送到 ELK 集群中。
- 每个内部服务除了deck 和 gate 必须用 mutual TLS,并且证书和认证通过 Lemur 进行管理。不允许任何外部流量进入内部服务中。所有的 API 调用必须经过 gate。
- 每个外部服务(除了gate)都要支持 mTLS 或者 SSO。
- 如果某个服务有数据存储的需求,那么只能存在自己的数据库中,服务之间不共享数据存储。
为了保证兼容性,Spinnaker 在开发过程中还会准守一些准则:
- 保证足够的单元测试和覆盖率。
- 在 code review 的时候特别注意是否会破坏API兼容性。
- 7×24 不间断的执行集成测试。有两种集成测试,一种是一个 jenkins job,会不断调用 API 接口,确保API是按照预想的在工作,另一种是一个 Spinnaker 的 pipeline,用来执行日常任务(比如创建镜像,部署环境等)。
- 当发现未知的失败是,首先执行回滚操作,直到这个问题被修复。
总结
Netflix 是一个优秀的企业,有着自由的精神和先进的技术,崇尚 DevOps 文化。而 Spinnaker 是他们在践行 DevOps 文化时创造出的优秀工具,通过这些工具我们能窥见他们对微服务和敏捷开发的深刻理解,希望能够给国内的开发者一些启发和帮助。
文章末尾固定信息