猪齿鱼的微服务之路(一):如何迈出关键的第一步

在猪齿鱼Choerodon设想之初,我们希望基于容器技术,整合DevOps工具链、微服务应用框架,开发一个企业级的PaaS平台,来帮助企业实现敏捷化的应用交付和自动化的运营管理。同时,也确定了技术堆栈的要求,即充分地使用主流成熟的组件,利用工具的扩展机制来构建平台,打造一个开放的技术平台和体系,让企业享受到社区的成果。

当然,罗马不是一天建造起来的。从初期确定技术栈到现在,猪齿鱼除Choerodon平台具体应用的实践与迭代,平台的技术栈也在不断进行着迭代。在社区中解决一个相同问题的有很多,而如何验证甄别哪些既能够满足现在的系统需求,在未来又有比较好的适应性,就给广大的架构师和软件设计师提出了挑战。根据Choerodon猪齿鱼实践经验,在使用时,可以从如下几个方面来进行考虑:

  • 语言 - 选择一个非常核心的考量是尽量使用应用比较广泛的开发技术,避免涉及相对来说的新技术、开发语言,这样可以进一步研发降低成本。例如Java的使用非常广泛。

  • 成熟度 - 的版本是否已经发布稳定版本或者更高版本是其成熟的重要标志,例如Istio在8月发布1.0版本,促使了很过公司和产品跟进使用;如果产品仍处于孕育阶段,则其技术变更的风险就比较大,例如 Apache 的 incubating 、 0.XXX版本或者beta版本等都有可能有各种技术缺陷或者没有经过较好的实际检验。

  • 社区 - 社区的活跃度在一定程度上反映了整个技术的生命力,例如是否有大量相关社区存在,K8s在国内就有Kubernetes中文社区,K8s中文社区等,以及定期还有各种关于K8s的Meetup或者论坛等;当然GitHub 上的 stars 的数量是一个参考指标,以及贡献者数量、代码更新频率等。

  • 生态圈 - 围绕是否有活跃健康的生态圈,是否有比较多的用户在使用,尤其是一些大公司,以及围绕产品是否有较多的文章、知识分享,或者围绕产品的某一块功能第三方增强工具,例如围绕Hadoop有Sqoop、Hbase、Hive等。

  • 文档 - 完备并及时更新的文档,非常有利于用户了解产品的设计思路、安装、使用等,方便产品在用户这边落地实践。想想 sourceforge.net 上如今已是代码的坟墓,没有文档的代码生命周期通常都不长。

  • 资源 - 如果在业界比较高的人气,应该有比较多的使用者,市场上相关人员资源也非常丰富,比较有利于团队技术人员的补充。

到目前为止,Choerodon猪齿鱼经过不断地迭代,逐渐形成了以 Spring Cloud + Kubernetes 为主体的微服务技术体系。

什么是微服务架构

在开始介绍之前,首先需要了解什么是微服务架构? 2014年初(该年可以称之为微服务的元年),微服务之父 Martin Fowler 在其博客上发表了”Microservices” 一文,文中正式提出了微服务架构风格,并指出了微服务架构的一些特点。

简单地说,微服务是系统架构上的一种设计风格,它的主旨是将一个原本独立的系统拆分成多个小型服务,这些小型服务都在各自独立的进程中运行,服务之间通过基于HTTP的RESTful API进行通信协作。被拆分的每一个小型服务都围绕着系统中的某一项或一些耦合度较高的业务功能进行构建,并且每个服务都维护着自身的数据存储、业务开发、自动化测试案例以及独立部署机制。由于有了轻量级的通信协作基础,所以这些微服务可以使用不同的语言来编写。

– 作者 James Lewis and Martin Fowler, 翻译自《Spring Cloud微服务实战》

在传统的单体应用系统架构中,一般分为三个部分,即数据库、服务应用端和前端展现,在业务发展初期,由于所有的业务逻辑在一个应用中,开发、测试、部署都比较容易。但是,随着业务的发展,系统为了应对不同的业务需求会不断为单体应用增加不同的业务模块。久而久之,不断扩充的业务需求导致单体应用的系统越来越庞大臃肿。此时,单体应用的问题也逐渐显现出来,由于单体应用是一个“整体”,往往修改一个小的功能,为了部署上线就会影响到其他功能的运行。而且,对于业务而言,往往不同模块对系统资源的要求不也尽相同,而单体应用各个功能模块因为无法分割,也就无法细化对系统资源的需求。所以,单体应用在初期是比较方便快捷,但是随着业务的发展,维护成本会越来越大,且难以控制。

Martin Fowler 认为微服务架构与单体应用最大的区别在于,微服务架构将一个完整的单体应用拆分成多个有着独立部署能力的业务服务,每个服务可以使用不同的编程语言,不同的存储介质,来保持低限度的集中式管理。下面这张图,很好的说明了单体架构和微服务架构的区别。

猪齿鱼的微服务之路(一):如何迈出关键的第一步

根据猪齿鱼Choerodon 的开发实践和产品化经验,在互联网+、云计算和大数据、人工智能等的大背景下,构建软件系统产品,首先要把系统的基础框架搭好,方便后续的扩展。而微服务架的独立部署、松耦合等特点,与Choerodon猪齿鱼的想法和设计理念不谋而合, 所以 Choerodon 最终选择了微服务架构作为基础架构。

而在微服务基础框架中,有两个不得不提的微服务架构,分别是阿里巴巴的 Dubbo 和 Pivotal 公司开源的 Spring Cloud 。

Dubbo的诞生背景

Dubbo 是一个高性能、基于JAVA 的开源RPC 框架。阿里巴巴开源的 Dubbo 致力于提供高性能和透明化的RPC 远程服务调用方案,以及SOA 服务治理方案,使得应用可通过高性能RPC 实现服务的输出和输入功能,和 Spring 框架可以无缝集成。本质上而言,是一个服务框架。根据Dubbo 的官方 Roadmap 可以看到,Dubbo 的发展经历了如下几个过程:

  • 数据访问框架(ORM):早期的主流开发方式是面向对象的开发方式。只需一个应用,将所有功能都部署在一起,以减少部署节点和成本。关系数据库是企业级应用环境中永久存放数据的主流数据存储系统,简化了增删改查工作量。

  • Web框架(MVC):随着访问量逐渐增大,单一应用已经无法满足业务需求,将应用拆分成互不相干的几个应用,分离视图层和业务逻辑层以提升效率。

  • 分布式服务框架(RPC):当垂直应用越来越多,应用之间交互不可避免,将业务抽取出来,作为独立的服务,逐渐形成稳定的分布式服务架构。

  • 面向服务的架构(SOA):当服务越来越多,业务和环境的变化越来越快时,对于资源的控制,性能的要求也就越发重要。SOA 将一个应用程序的业务逻辑或某些单独的功能模块化并作为服务呈现给消费者或客户端,使得业务IT 系统变得更加灵活。

猪齿鱼的微服务之路(一):如何迈出关键的第一步

Dubbo 按照分层来规划我们的系统,包含远程通讯、集群容错和自动发现三个核心部分。提供透明化的远程方法调用,使各个服务之间解耦合,并通过RPC的调用来实现服务的调用。

Dubbo 由于自身的设计使得服务之间的调用更加透明,网络消耗小,同时借助类似zookeeper 等分布式协调服务实现了服务注册。但是Dubbo 的缺点也是显而易见的,比如:

  • 只支持JAVA 使得Dubbo 在开发语言上受到了限制
  • 虽然RPC 相对于HTTP 而言性能更高,但是在网络通用性上却有着局限性
  • 而且对于一个微服务架构而言,包括服务网关,配置中心等很多东西都是缺失的,需要自己实现
  • 虽然Dubbo 很早就进行了开源,但是在很长一段时间官方都没有对开源版本进行维护

由于这些缺点,Choerodon 并没有选择 Dubbo 作为基础开发框架。

Spring Cloud 应运而生

在微服务架构的概念提出之后,很快 Netflix 公司将自家经过多年大规模生产验证的微服务架构,抽象落地形成 一整套开源的微服务基础组件 NetflixOSS 。2015年,Pivotal 将 NetflixOSS 开源微服务组件集成到其 Spring 体 系,并推出 Spring Cloud 微服务开发技术栈。自此,微服务技术迅猛普及,甚至 Spring Cloud一度成为了微服务的代名词。

可能更多了解微服务架构的读者都是从 Spring Cloud 入门,凭借之前 Spring Framework 的良好群众基础和Cloud 这个具有时代感的名字,Spring Cloud 的名字可以说是无人不知,无人不晓。结合Pivotal 公司的 Spring Boot,我们通过封装开源成熟的Spring Cloud 组件和一些基础的分布式基础服务,就可以简单快速的实现一个微服务框架,降低应用微服务化的门槛。

Spring Cloud 提出了一整套有关于微服务框架的解决方案。包括:

  • 服务注册发现:Spring Cloud Eureka
  • 负载均衡:Spring Cloud Netflix
  • 服务网关:Spring Cloud Zuul
  • 配置管理:Spring Cloud Config
  • 服务消费: Spring Cloud Ribbon/Feign
  • 分布式追踪:Spring Cloud Sleuth
  • 服务容错:Spring Cloud Hystrix

下图说明了借助Spring Cloud 搭建的一套简单的微服务体系。

猪齿鱼的微服务之路(一):如何迈出关键的第一步

可以看到,Spring Cloud 集成了众多组件,从技术架构上降低了对大型系统构建的要求,使架构师以非常低的成本(技术或者硬件)搭建一套高效、分布式、容错的平台。但同时,在实际开发中也发现 Spring Cloud 存在着的一些问题:

  • 技术要求高:Spring Cloud 对于配置中心、熔断降级、分布式追踪、在权限认证、分布式事物等基本的功能,并没有提供一个成熟的组件,需要结合第三方的组件或自研实现。这对整个开发团队提出了非常高的技术要求。
  • 代码侵入性强:Spring Cloud 对业务代码有一定的侵入性,技术升级替换成本高,导致实施团队配合意愿低,微服务落地困难。
  • 服务运维困难:Spring Cloud 在服务调度和部署、服务日志、服务监控等仍有缺失。当服务的规模增大,对于微服务的管理有可能会增加运维的负担。
  • 多语言支持不足:对于大型公司而言,尤其是快速发展的互联网公司,企业的性质决定了多语言的技术栈、跨语言的服务调用也是常态,跨语言调用也恰恰是微服务概念诞生之初的要实现的一个重要特性之一。

Dubbo & Spring Cloud 对比

对比Dubbo 和Spring Cloud 可以发现,Dubbo 只是实现了服务治理,而Spring Cloud 的子项目则分别覆盖了微服务架构下的众多组件,而服务治理只是其中的一个方面。

猪齿鱼的微服务之路(一):如何迈出关键的第一步

通过谷歌和百度的搜索统计可以看到,自2015年起到现在,国内对于Spring Cloud 检索指数也在逐渐赶超Dubbo。

猪齿鱼的微服务之路(一):如何迈出关键的第一步

猪齿鱼的微服务之路(一):如何迈出关键的第一步

综合而言,Dubbo专注于服务治理;Spring Cloud关注于微服务架构生态。

虽然 Spring Cloud 降低了微服务化的门槛,但是除了基础的服务发现以外,Choerodon 团队在实际开发中也遇到了诸多的挑战。例如,各个组件并非完美无缺,很多组件在实际应用中都存在诸多不足和缺陷。 Spring Cloud 并不是银弹,微服务架构解决了单体系统变得庞大臃肿之后产生的难以维护的问题,但是也因为服务的拆分引发了诸多原本在单体应用中没有的问题,比如部署困难,监控困难,运维成本大,是选择 Spring Cloud 首先要面对的问题。

而容器化的普及,尤其是云原生技术生态的不断完善,比较好地解决了微服务架构的采用引发的诸多问题,使得微服务在普通传统企业的落地成为了可能。

Kubernetes + Docker 使微服务实施成为一种可能

当企业逐步接受微服务架构,享受着微服务带来好处的同时,也面临着微服务运维成本的增加, 环境的不一致,服务的编排、部署、迁移等诸多问题。Choerodon 平台经过不断地演进,从初期引入Docker,到Rancher + Jenkins,再到现在采用 Kubernetes 为容器编排和管理工具。

容器技术产生的主要原因,并不是因为资源浪费。主要是开发和运维人员环境不一致,导致开发效率大大降低。通过容器可以在一个完全隔离的环境中非常高效地运行代码,容器化天然适用于微服务,改善了引入Spring Cloud 微服务后开发效率大大降低的问题。但是单独使用Docker 并没有完整的解决微服务管理的痛点,服务的部署和运维仍然急需解决。

Kubernetes 是谷歌推出的容器编排引擎,是基于GoLang 实现的一个开源软件。K8s(Kubernetes)初源于谷歌内部的Borg,提供了面向应用的容器集群部署和管理系统,其目标旨在消除编排物理/虚拟计算、网络和存储基础设施的负担,并使应用程序运营商和开发人员完全将重点放在以容器为中心的原语上进行自助运营。

早期大家对于K8s 定位是容器编排引擎,同一时期流行的容器编排引擎还有MESOS、Docker Swarm 等。但是经过几年的发展,K8s 已经成为了云供应商的通用基础设施,我们熟悉的Google Cloud,AWS,Microsoft Azure,阿里云,华为云等等,都提供了对K8s 的支持。现在,K8s 已经不仅仅是一种工具,更多的是作为微服务架构的一种行业标准。

下图通过使用微服务架构的设计思想来看待K8s,并对K8s 中的一些功能进行了说明。

猪齿鱼的微服务之路(一):如何迈出关键的第一步

通过对比可以看到,在设计上,K8s本身就属于微服务架构的范畴。这里有的人可能就会有疑问,既然 K8s 功能这么强大,那么K8s 和 Spring Cloud 到底哪个更好?Choerodon 为什么不直接使用Kubernetes 作为基础的微服务架构呢?

为了区分Spring Cloud 和Kubernetes 两个项目的范围,下面这张图列出了几乎是端到端的微服务架构需求,从底层的硬件到上层的 DevOps 和自服务经验,并且列出了如何关联到Spring Cloud 和Kubernetes 平台。

猪齿鱼的微服务之路(一):如何迈出关键的第一步

可以看到:

  • Spring Cloud:自上而下,面向开发者,从应用代码到微服务架构的方方面面
  • Kubernetes:自下而上,面向基础设施,试图将微服务的问题在平台层解决,对开发者屏蔽复杂性

综上对比,K8s 遵循了微服务架构的基本核心要素,虽然在一些功能上有所欠缺,但不可否认,K8s 帮助补足了使用Spring Cloud 所缺失的一部分。

微服务“新秀”–Service Mesh

Choerodon 通过使用 Spring Cloud + Kubernetes 的模式,帮我们能够很容易的构建和部署微服务架构。但是在线上管理整个微服务体系的时候,仍然面临着一些难点。

一直以来都存在一个谬误,那就是在分布式系统中网络是可靠的。实际上网络是不可靠的,也是不安全的,微服务中大部分的故障都是出现在服务通信中。

K8s 帮我们实现了微服务的部署,但服务的网络调用、限流、熔断和监控这些问题,依旧让开发和运维人员都十分头痛。如何保证应用调用和事务的安全性与可靠性?Service Mesh 由此应运而生。

在过去几个月里,Service Mesh是行业内毋庸置疑的焦点。Service Mesh 译作“服务网格”或“服务栅格”,作为服务间通信的基础设施层。Service Mesh 是一种模式,而非技术。Buoyant 公司的 CEO Willian Morgan 在他的文章《WHAT’S A SERVICE MESH? AND WHY DO I NEED ONE?》中解释了什么是 Service Mesh。

A service mesh is a dedicated infrastructure layer for handling service-to-service communication It’s responsible for the reliable delivery of requests through the complex topology of services that comprise a modern, cloud native application. In practice, the service mesh is typically implemented as an array of lightweight network proxies that are deployed alongside application code, without the application needing to be aware.*

Service Mesh 本质上是一个轻量级的网络代理,好比应用程序或者说微服务间的 TCP/IP。

对于开发人员而言,在编写应用的时候无需关心网络这一层,使得服务回归到本质,专注于业务功能,服务中的交互则交给Service Mesh。Service Mesh 为服务提供了一个视图,提高了追踪能力,并提供了添加跟踪而不触及所有应用的能力,也就是所谓的Service Mesh 代码无侵入和透明性,能够帮助团队更好地管理服务。

Service Mesh 架构图:

猪齿鱼的微服务之路(一):如何迈出关键的第一步

可以看到,Service Mesh 通过一种Sidecar的模式。给每一个微服务实例部署一个Sidecar Proxy。该Sidecar Proxy 负责接管对应服务的入流量和出流量,并将微服务架构中的服务订阅、服务发现、熔断、限流、降级、 分布式跟踪等功能从服务中抽离到该Proxy 中。

Sidecar 以一个独立的进程启动,可以每台宿主机共用同一个Sidecar 进程,也可以每个应用独占一个Sidecar 进程。所有的服务治理功能,都由Sidecar 接管,应用的对外访问仅需要访问Sidecar 即可。当该Sidecar 在微服务中大量部署时,这些Sidecar 节点自然就形成了一个服务网格。

猪齿鱼的微服务之路(一):如何迈出关键的第一步

通过控制面组件对这些服务网格进行管理,这样也就提供了一种对于微服务进行高效而统一的管理方式。集中化的控制面板,同时仍然具有随心所欲的敏捷性和基于云的应用开发。这一特性,使得Service Mesh 成为大势所趋。

总 结

回顾微服务结构发展的这几年,微服务架构的逐渐普及,容器技术的兴起,云原生的趋势,微服务技术生态在不断地变化中,容器、Cloud Native、Serverless、Service Mesh,Knative 等新技术新理念你方唱罢我登场,使得整个以微服务为核心的生态越来越完善成熟。

像在前文中提到的Kubernetes、Service Mesh等都是解决微服务架构本身系统范围的问题,扎实可靠的基础框架,有利于后续的开发,这也是产品研发、系统实施的关键第一步。

除了系统本身的技术栈,工程落地实施是另一个要解决的问题。很多产品开始开发的时候,都不太注意规范化,待产品需求越来越复杂,人员越来越多时,整个项目会变得很难维护,甚至会影响产品的持续迭代。特别是微服务技术体系的引入,这个问题会更加明显。所以如果项目一开始,就以工程化的思想去组织代码,以规范化的流程去做构建发布,会给后续的发展打下坚实的基础。微服务的工程落地实施是Choerodon猪齿鱼一直关注和实践的方向,通过整合DevOps工具链和引入落地敏捷实施的方法论,让微服务架构的工程落地变得容易,这也成了Choerodon的PaaS平台能力,在这就不做赘述,感兴趣的读者可以到猪齿鱼Choerodon的官网了解。


本文由猪齿鱼技术团队原创,转载请注明出处

上一篇:dubbo springboot,踩到的坑,主要是版本问题,springboot的版本为2.2.5release,可以用,否则,报类找不到的错误


下一篇:Dubbo容错机制