Docker在蚂蚁金融云平台中的探索与实践
蚂蚁金融云是蚂蚁金服推出的针对金融行业的云计算服务,旨在将蚂蚁金服的大型分布式交易系统中间件技术以 PaaS 的方式提供给相应客户。在整个的 PaaS 产品中,蚂蚁金服通过基于 Docker 的 CaaS 层来为上层提供计算存储网络资源,以提高资源的利用率与交付速度,并用来隔离底层 IaaS 的不同,IaaS、CaaS 与 PaaS 三层相互借力,互相配合。为了进一步了解蚂蚁金融云的整个体系架构,InfoQ 采访了蚂蚁金服基础技术部系统组 leader 吴峥涛。
InfoQ:能否介绍下蚂蚁金服的金融云 PaaS 平台?
吴峥涛:金融云 PaaS 是从 2014 年中开始研发的,目前已经承载了网商银行以及另外两个核心业务,后续会以公有云和专有云两种模式对外提供。之所以会有金融云 PaaS 这个项目,是因为蚂蚁这些年来在大型分布式系统领域涉及的 SOA、消息通讯、水平扩展、分库切片、数据一致、监控、安全等技术方向积累了大量的中间件以及与之完整配套的监控运维研发流程体系,这一切在性能和稳定 性以及扩展性上做的都不错,能够有效的支撑蚂蚁的业务发展,并应对『双 11』这样的高负荷挑战。很多金融客户与伙伴都对此非常感兴趣,所以我们希望能够把这一整套的技术上云并产品化,以 PaaS 的方式整体对外输出,帮助金融行业的客户使用云计算技术去 IOE,帮助他们解决我们已经解决的技术问题,让他们能专注于业务逻辑。上帝的归上帝,凯撒的归凯撒。
InfoQ:蚂蚁金服想把自己的中间件技术以 PaaS 产品的形式对外输出,这中间碰到了哪些问题?为什么会想到通过 Docker 这样的技术来解决?
吴峥涛:遇到的问题有很多,最主要的问题包括:
金融云 PaaS 是承载在阿里云 IaaS 上的,最初的方案是,用户部署应用的时候,根据所属技术栈,由系统解析软件包(例如 sofa4 依赖 CloudEngine、Tengine、cronolog、JDK 等等),下载安装配置并启动。这样的资源交付、应用部署周期比较长,客户体验不太好。
蚂蚁的应用架构采用的是基于服务发现、消息总线的 SOA 方案,模块间通过服务接口调用;服务可以是本地接口也可以是远程接口,对于调用者是解耦合的。在实际部署的时候,我们会根据业务纬度切分大量的服务模块出 来,以金融云 PaaS 中枢为例,目前已经有几十种服务模块。这样的话,我们希望资源粒度越小越好,原有以 VM 为粒度的资源分配方式已经不能满足我们的需求。同时资源交付速度慢导致扩容缩容慢,影响资源利用率。
金融云 PaaS 如果对外输出,可能使用非阿里云的 IaaS,所以需要一个中间层屏蔽多种 IAAS 的区别。
镜像管理比较麻烦,无法自动化,也不是白盒。
而遇到的这些问题,都可以通过 Docker 来解决。
InfoQ:能否介绍下你们整个平台的系统架构?Docker 在整个架构中扮演怎么样的位置?
吴峥涛:我们在 PaaS 和 IaaS 之间插了一个 AntCaaS 层,这是一个基于 Docker 的管控平台,他的职责是:
- 以微容器(Docker)为载体,为用户(PaaS、SaaS)按需提供计算存储网络资源,提高资源的利用率与交付速度。
- 对 PaaS、SaaS 屏蔽 IaaS 实现细节。
- 实现容器、集群级别的标准化与可复制、可迁移。
AntCaaS 提供 container、app、cluster 三层接口,可以把他当作一个轻量级的 IaaS,区别仅仅是提供 Container 而不是 VM,然后也提供 PaaS 层的接口。
一个比较有特色的功能是,通过『镜像中心+集群 template+ 环境相关参数列表』,我们实现了集群的快速复制,目的是为了应付突发的负载高峰。
InfoQ:在 PaaS 层面,你们是如何屏蔽底层不同 IaaS 的区别的?
吴峥涛:目前 AntCaaS 可以直接运行在物理机上也可以运行在经典网络的 ECS VM 集群中,VPC、ECS 支持还在开发过程中。在 AntCaaS 中,我们采用三层架构,通过创建不同 pool 来兼容不同的 IaaS。pool 包含了:
- 多个 node(container 的载体)。
- ZK 用以监控 node 和 container。
- scheduler 调度器,负载 container 的创建调度。
- manager,对 master 提供管控的 HTTP Rest 接口。
- registry-proxy 保证网络联通性以及 cache 镜像数据,加速镜像下载。
- 在 node 内起 cadvisor 监控 container。
Docker 默认的 bridge/host 网络模式不能满足我们的需要,根据 IaaS 提供的网络功能不同,我们扩展了 vlan/vxlan 两种网络 driver,第三者 vpc driver 还在开发中。
vlan 模式,事先为 container 分配一个与 node 不一样的网段。
vxlan 模式,首先通过 ovs 实现跨 node 的私有网络,然后通过 zk 缓存同步 vpcid、vpc ip、node ip 的映射关系,极端情况下,如果一个 vpc 有 1000 个 container 分布在 1000 个 node 上,那么新建一个 container 加入这个 vpc 时,需要通知所有的 node。
另外在 VPC 内,我们提供轻量级的 DNS,用于内部域名解析;轻量级的 LB,用于内部的负载均衡。
下图是可扩展的容器创建流程。
InfoQ:容器的安全问题是怎么解决的?
吴峥涛:基于 pool-node-container 的三层解决方案。用户和 pool 是 1 对多的关系,所以 pool 的 node 必然都属于同一个用户,同一个 node 上的 container 属于同一个用户。pool 和 pool 之间根据 IaaS 不同采用不同的隔离方案,经典网络的 ECS 使用安全组隔离,vpc ecs 使用 vpc 隔离。
InfoQ:社区中有反馈说 Docker 会经常无故挂掉,你们有遇到过吗?有做过深入跟进吗?
吴峥涛:碰到过,我们的架构设计允许 Docker Daemon 和 Container 挂掉。使用了集团的一个 Docker Patch,在 Docker Daemon 挂掉后,不影响 container 运行。出现比较多的场景是 docker pull 时候。
InfoQ:你们是如何将基于 Docker 的系统与原有系统对接的?
吴峥涛:为了与现有的运维流程管控 SCM 系统对接,帮助现有系统迁移,以及帮助开发同学转换开发模式,我们做了不少妥协方案。作为 Docker fans,理想的开发模式是下面这样。
但是实际上蚂蚁目前已经有 1000 多个应用,几千的开发人员,很难让他们一下都切换到 Docker 这种以镜像为中心的研发模式上;但是如果一个团队一个团队的推广,那么耗时不可控。并且蚂蚁原有的运维、监控、SCM 等系统都是以 VM 为纬度的,基于 Docker 的运维发布系统需要与原有系统对接集成难度比较大。
所以我们的第一个策略是,首先解决线上环境的 Docker 化部署问题,开发者的本地开发环境 Docker 化问题暂且不管,希望通过线上环境 Docker 化来吸引开发人员学习使用 Docker。
接下来的问题是,谁来写 Dockerfile,首先各个研发团队的人不关心是否使用 Docker 部署,所以不可能写 Dockerfile,由 Docker 团队或者运维同学负责,没有应用代码的编辑权限,同时工作量太大并且不了解应用容易出问题。所幸蚂蚁的业务应用大多数都是基于 sofa3 或 sofa4 框架的 Java 应用,所以我们做了 sofa3/4 的基础镜像以及提供一个辅助工具,使用 sofa3/4 镜像启动一个 container,然后使用原有的发布工具将应用的 tgz 包(类似 war)发布到 container 中。这样就不需要写 Dockerfile,同时原有运维系统也能把 container 当作 VM,无缝对接。
InfoQ:聊聊你们异地多机房的统一镜像中心解决方案?
吴峥涛:关于跨机房镜像中心的解决方案要点:
- 将镜像数据存在 OSS 写三份,保证数据安全性;
- Registry 本地不保存数据,是无状态的服务,可以水平扩展;
- Registry 上跑一个 Nginx,提高镜像数据访问速度;
- 在每个 pool 中部署一套 Nginx,开启文件缓存,对常见镜像进行预热,构建缓存。