聊聊云原生

什么是云原生

基本概念

云原生是一系列技术的集合,利用这一系列技术,企业和组织可以快速高效的在云上构建弹性、可扩展、更加可靠的应用。这些核心技术包括(来自CNCF定义):

  • 容器(container)
  • 服务网格(service mesh)
  • 微服务(micro service)
  • 不可变基础设施(immutable infrastructure)
  • 声明式API(declarative APIs)

思想

云原生的核心思想主要是:

  • 分而治之:无论是微服务还是容器化都体现在分而治之这个理念中。通过合理的拆分,解决一体化应用部署、运维、开发的问题。
  • 基础技术下沉与自动化:得益于云原生技术提供的底层抽象能力,很多层次的能力和技术得以下层和标准化,开发人员只需要关注业务开发本身。整个基础设施的标准化和统一抽象,使得基础设施层的管理、运维以及应用的部署、更新都可以更好的自动化。敏捷开发、devops的执行理念、CI/CD工具的运行在云原生的环境下可以更加高效的工作发挥更大的价值。

云原生应用

云原生中的云不仅仅指的是公有云,这点容易被误解。通过网络连接的服务器以及这些服务器上的软件和数据库构成了一个云,他可以是私有云、公有云、混合云。
image.png

云原生技术

容器(虚拟化)

容器技术是云原生技术最重要的构成部分了。实施云原生技术的关键在于拆分更细粒度的执行单元,打破原有单体应用的架构。容器技术从其本身领域来讲属于虚拟化技术,在不同层次上虚拟化我们会得到不同的虚拟化技术。
image.png

  • 物理机:没采用任何虚拟化技术,软件和硬件都在一个物理实体上。
  • 虚拟机:可以在一个物理机上划分多个VM,采用Hypervisor技术,对物理机虚拟化。
  • 容器:在vm基础上,对操作系统虚拟化,核心技术是cgroup做资源控制、namespace完成资源隔离等。
  • webassembly: 在容器化基础上,对进程进一步做虚拟化

image.png
随着虚拟化程度的提升,执行单元粒度更加细致、启动更快、更少内存占用和耦合。这也充分迎合了云原生时代的诉求。执行单元足够轻量才能更快启动与调度从而有更好的弹性。

此外,容器技术也催生了一系列配套的软件,例如容器编排(k8s)、

Tips: 2023年是webassembly的重要一年,如果wsam能够真正突围到云原生体系中,而不是仅仅给人留下只能在浏览器中运行的狭隘印象,相信会有更大的发展

数据库是否适合容器化的争论

记得多年前对于数据库是否容器化是一个争论不休的话题。多年过去了,时间给出了答案,云原生趋势不可逆。像TIDB这样的分布式数据库也已经全面对接云原生。以前反对数据库容器化更多是在那时候有太多问题待解决,随着云原生基础设施的完善,这些已不再是问题。

微服务

SOA是面向VM的,而微服务则是面向容器的。将特定职责的应用拆分成服务,在容器上运行,这就是微服务了。微服务可以是一个鉴权服务、订单服务等等。微服务本身的概念并不复杂,但是何时使用微服务以及如何使用微服务是一个比较有挑战的问题。

何时使用微服务

关于何时使用微服务个人看法是当你不知道要不要用时,那就别用。公司团队的成熟度没到一定程度的时候,单体应用一定是利大于弊的,专注在业务上、赢得客户赚到钱才是最重要的。拆分微服务会引入额外的复杂度,在小团队和企业中这个是弊大于利的。

微服务的架构发展

微服务的架构经历了如下几个阶段,每一次进步都会将更多能力做技术下沉,进行统一抽象。本质也是体现着分而治之和技术下沉的理念。下面两幅图可以展示这种架构性的变化:
image.png

多运行时架构

继bibryam提出mecha多运行时理念后,这几年多运行时算云原生中其中的一个热点了。mecha是机甲的意思,灵感来自于阿凡达人类穿不同的mecha机甲就拥有不同的能力,十分顾名思义。核心理念是为构建一个无状态、可伸缩、弹性的分布式应用提供一个通用运行时,这样业务开发人员就可以专注于业务逻辑的开发,下沉的能力由分布式运行时给你自动化按照最佳实践来处理。可以下沉的内容主要如下所示:

image.png
dapr的一个值得注意的优势是其也可以在k8s体系外应用,因为本质是一个分布式运行时,这对很多中小企业和团队是一个好事情。
从当前来看,多运行时是代表着未来的。不过新技术的发展仍然需要解决诸多问题例如不断分而治之带来的复杂度提升问题等等。但至少现在来看,云原生已经比过去成熟太多了。

关于dapr的核心应用场景,可以参考bilgin lbryam的twitter:

  • 和应用本身交互:利用dapr提供的基础设施构建最佳实践的分布式应用。另外提供的语言无关能力对于企业多语言开发也有利
  • 和外部资源交互:比如访问数据库、存储、MQ等等
  • 多云迁移:dapr给了应用很强的可移植性,是个中立、无供应商锁定标准的平台。实践案例可以看参考资料dapr在阿里实践的文章

image.png

多运行时架构的现状也并发完美,其中一个典型问题就是multi runtime是个单体运行时。很多功能整合在一起,像宏内核,一旦臃肿起来又会再暴露单体的一些问题,比如牵一发而动全身影响整个sidecar。如何找到最合适的度,权衡拆与合是multi runtime后续要考虑的问题。

serveless

在微服务发展的架构里面其实没把serveless列进去。因为其本质更多是一种利用云原生技术产生的使用形式上的变化,而且大部分都是在公有云上应用。serveless宣传的优势很多来自于微服务架构本身带来的弹性、可伸缩。在商业场景上或者需要内部结算的场景中按需使用、按量计费会带来很多额外的好处。对于客户来说可以按需使用省钱,对于内部开发人员来说按需使用可以避免浪费。

微服务的一些思考

微服务的架构也是分而治之技术下沉的过程。这个过程中各个解耦的构建之间通过标准的网络协议进行交互。这让我想到了一句老话:不要通过内存共享来通信,而是应该通过通信来共享内存。云原生的发展似乎就在践行这个理念。

服务网格

基本概念

service mesh的出现是为了更好的管理大规模的微服务,作为微服务管理的基础设施。云原生模式下,单个应用可能有数百个服务,每个服务又有上千个实例。这些实例之间涉及很多交互,而service mesh可以将这些服务高效的连接起来并且提供统一的管理。

service mesh有点像微服务之间的TCP/IP协议,不过更强。除了包含服务通讯层面必须解决的丢包重传、拥塞控制、流量控制以外还包括:

  • 服务熔断
  • 服务降级
  • 负载均衡
  • 服务限流
  • 服务发现
  • 服务监控
  • 服务调用追踪
  • 故障注入

不过相比实现与内核态的TCP/IP协议,service mesh对于用户来说更加看得见摸得着。通过service mesh,用户可以直接深度的管理service之间的通信。
image.png
一般一个service mesh的架构如下,核心由数据面板和控制面板构成。

  • 数据面板:核心是个流量proxy,具备的能力可以参考现在主要作为proxy的envoy
    • 动态服务发现
    • 负载均衡
    • TLS终端
    • HTTP/2和gRPC协议代理
    • 熔断器
    • 健康检查
    • 基于百分比流量分隔的分阶段发布
    • 故障注入
    • 丰富的指标
  • 控制面板:提供proxy的配置和管理能力,以及额外的身份认证、凭证管理、流量管理API等。例如,将用户设置的高级路由规则转换为envoy特定配置,运行时传递给proxy。当前作为控制面板的主要软件是Istio,内部集成了envoy。

image.png

xDS协议

xDS是数据平面和控制平面之间通讯的协议。相关术语和工作流程参考下图:
image.png
首先上图定义了一些基本概念,包括:

  • downstream: 发送请求的通信实体
  • upstream: 接收请求并响应的主机
  • listener: 可以被downstream client连接,由envoy暴露
  • cluster: envoy连接到的逻辑上相似的一组主机
  • mesh: 提供一致网络拓扑的一组主机,envoy mesh特指一组envoy代理
  • endpoint: Envoy将“端点(Endpoint)”定义为群集(Cluster)中可用的IP和端口,可以理解成cluster的成员

envoy提供了一组discovery service的API的集合,来支持他和控制面板之间的交互。所以这个协议叫xDS,包括:

  • LDS: listener discovery service用来发现
  • RDS: route discovery service,路由发现
  • CDS:cluster discovery service,集群发现
  • EDS:endpoint discovery service,端点发现
  • SDS:secret discovery service,用于安全证书发现
  • ADS: 聚合发现服务,可以在一个gRPC连接上聚合多个xDS请求,还可以解决CDS,RDS信息更新顺序依赖的问题,避免丢弃流量的问题

WASM与扩展性

现在最新isito采用proxy-wsam来扩展proxy能力。WSAM在云原生的发展值得关注,如果WSAM能和云原生深度融合好,WSAM技术会迎来真正的春天。

开源生态

当前service mesh层主要的产品有istio、linkerd、kuma、consul、conduit等。现在主流的还是istio和linkerd。往上也有一些评测可以参考:服务网格性能评估 — Istio、Linkerd、Kuma 和 Consul

不可变基础设施

这里的基础设施指的主要是服务器(不同时代代指不一样,可以是vm或者容器等)。过去可变基础设施主要是因为虚拟化的程度只有到vm,用户手动SSH到服务器进行部署更新等都是常见的操作。随着云原生发展,服务器指的对象越来越轻量,现在主要是指容器。不可变指的是容器实例是个一次性对象,创建好后不允许直接入侵到容器内部做手动的修改。不可变基础设施不意味着我们不能做变化。如果需要做变化例如版本升级,则通过重新发布镜像、统一的配置修改等方式重建容器。

可见不可变基础设施也依赖云原生技术提供的容器技术、CI/CD能力等。

声明式API

这个其实在编程语言中听到过类似的概念了。声明式是一种理念,相比命令式注重步骤,而声明式注重一个最终状态和结果。使用声明式API主要有以下好处:

  • 易于使用:API相当于已经是一个完整的逻辑单元,用户不用关系后端如何实现,直接调用一个API即可获得一个完整逻辑功能的结果。例如有个功能是支付金币,背后可能要先查询余额再结算,但是用户使用接口是可以直接调用支付金币的API
  • 最终状态和结果具有价值:对于用户来说,最终状态和结果是有存储和复用价值的,而内部细节暴露出来的中间结果用处不大。

在K8S中,声明式API则尤为重要,因为用户提交了一个API对象声明自己想要的状态,K8S会保证整个集群资源的状态与API描述一致。这主要就是API之间面向状态的好处。

参考资料