微服务学习一
最早写接口服务是在2012年至2014年,我在商旅服务行业,大量写Web Service,主要为CRM和移动端提供接口服务。
当时接口输入/输出都是XML,后期使用Google Protocol Buffer封装原Web Service接口方法,即输入/输出改成传递二进制数据,这样接口传输内容比xml减少,提高了响应速度。
Protobuf先写.proto 文件,再用 Protobuf 编译器生成目标语言所需要的源代码文件,再将这些生成的代码和应用程序一起编译。参考:https://www.cnblogs.com/logo-fox/p/8205116.html
2014年至2017年,我在金融行业,大量写Web Api接口,主要为网站提供接口服务。
2017年至2019年,我在在线阅读业务,大量写Web Api接口,主要是为移动设备提供接口服务。
2019年至今,我在金融行业,大量写WCF服务,为相关应用提供信用查询接口服务。
有了以上经历,我想再学习下微服务,虽然微服务这个词出来很久,虽然我的年龄也大了,在软件开发行业竞争力下降,比不得年轻人,但还是的学习。
微服务的六大好处,被调查者发现,他们已经通过微服务获得了很多的好处,位居前六的是:
持续集成(CI)/持续部署(CD)
敏捷性
提高可伸缩性
更快的交付时间
提高开发人员的生产效率
更容易调试和维护
微服务所承诺的弹性、高可用、低耦合、敏捷,以及能够解决单体架构带来的问题,这些都是它流行的主要原因。
微服务是一种应用于组件设计(服务如何分组)和部署架构(服务如何部署和通信)的模式。
微服务适用于创建具有“一定功能复杂性”的分布式应用程序。
各个服务必须小。
各个服务按功能划分,实现关注点分离。
各个服务保持自治和相互解耦,可以独立进行部署、版本控制和伸缩。
各个服务之间通过轻量级 API 和异步通道相结合的方式进行通信。
各个服务拥有独立的状态,并且只能通过服务本身来对其进行访问。
在微服务中,服务之间的通讯有俩种主要形式:
RESTful,也就是传输Json格式数,.net中就是对应的webapi技术
二进制RPC,二进制传输协议,技术有Thrift、gRPC等
微服务现在可以说是软件研发领域无人不提的话题,然而业界流行的对比多数都是所谓的Monolithic(单体应用),而大量的系统在十几年前都已经是以SOA(面向服务架构)为基础的分布式系统了,那么微服务作为新的架构标准与SOA有什么差异点呢?其本质区别在于设计原理,微服务是去中心化设计,SOA是「集成」形成中心设计;
微服务和SOA的区别点:
- CI/CD:持续集成、持续部署本身与敏捷、DevOps是交织在一起的,CI\CD更倾向于软件工程的领域,与微服务无关;
- 基于容器还是虚拟机:Docker、虚拟机、物理机等是物理介质的一种实现方式,与微服务无关;
- 微服务周边生态:比如日志平台、调用链系统?更多的是研发本身对于效率提高的自驱力,而与使用何种架构方式无关;
- 通讯协议:微服务的推荐通讯协议是RESTful,而传统的SOA是SOAP。不过基于轻量级的RPC框架Dubbo、Thrift、gRPC来实现微服务也很多;在Spring Cloud中也有Feign框架将标准RESTful转为代码的API这种仿RPC的行为,这些通讯协议不是区分微服务架构和SOA架构的核心差别;
在实际微服务的落地过程中证明,如果切分是错误的,你得不到微服务承诺的「低耦合、自治、易维护」之类的优势,并且还会比单体架构拥有更多的麻烦。那么如何切分呢?其实并不是一些新的方法论,而是都提出很多年的架构设计方法,也称它们为微服务设计基础或架构模型:领域驱动设计和立方体模型。
DDD(Domain Driven Design,领域驱动设计),2004年Eric Evans 发表。领域驱动设计已经问世十几年,从Eric Evans出版的著作「领域驱动设计」一书中对领域驱动做了开创性的理论阐述,在软件设计领域中,DDD可以称得上是步入暮年时期了。遗憾的是,国外软件圈享有盛誉并行之有效的设计方法学,国内大多数的技术人员却并不了解,也未曾运用到项目实践中。直到行业内吹起微服务的热风,人们似乎才重新发现了领域驱动设计的价值,并不是微服务拯救了领域驱动设计,是因为领域驱动设计一直在顽强的成长,其设计开放的设计方法体系,虽然从来不曾在国内大行其道,但却发挥着巨大的价值。表面上看确实是因为微服务,领域驱动设计才又开始出现在大众视野里。
领域驱动设计的意义
一套完整的模型驱动的软件设计方法,用于简化软件项目的复杂度,它能带给你从战略设计到战术设计的规范过程,使得你的设计思路能够更加清晰,设计过程更加规范;
一种思维方式和概念,可以应用在处理复杂业务的软件项目中,加快项目的交付速度;
一组提炼出来的原则和模式,可以帮助开发者开发优雅的软件系统、促进开发者对架构与模型的精心打磨,尤其善于处理系统架构的演进设计、有助于提高团队成员的面向对象设计能力与架构设计能力;
领域驱动设计与微服务架构天生匹配,无论是在新项目中设计微服务架构,还是将系统从单体架构演进到微服务设计,都可以遵循领域驱动设计的架构原则。
当然,领域驱动能给我们带来很多收获,但如果你是属于以下几种情况的某种,那么你确实不需要学习领域驱动设计了:
如果你是独当一面的架构师,并能设计出优雅的软件架构
如果你是高效编码的程序员,并只想踏踏实实的写代码
如果你是前端的设计人员,并奉行「用户体验至上」的理念
如果你负责的软件系统并不复杂,二三人便可轻松维护
DDD的分层架构
User Interface:用户界面层/展示层,负责与用户交互。包含显示信息、解释用户命令等;
Application:应用层,用来协调用户与各应用以及各应用之间的交互。不包含业务逻辑、不保存业务对象的状态;
Domain:领域层/模型层,负责表达业务概念,业务状态信息以及业务规则。包含领域模型、领域信息、业务对象的状态。领域层是业务软件的核心;
Infrastructure:基础设施层,为其他各层提供技术能力。包括为应用层传递消息、为领域层提供持久化机制、为用户界面层绘制屏幕组件等等。基础设施层还能够通过架构框架来支持四个层次间的交互模式。
六边形架构
随着后续的演进,出现了一种改进分层架构的方法,即Robert C. Martin提出的依赖倒置原则(Dependency Inversion Principle,DIP)。它通过改变不同层之间的依赖关系达到改进目的。
高层模块不应该依赖于底层模块,两者都应该依赖于抽象
抽象不应该依赖于细节,细节应该依赖于抽象
根据该原则的定义,DDD分层架构中的低层组件应该依赖于高层组件提供的接口,即无论高层还是低层都依赖于抽象,整个分层架构好像被推平了,再向其中加入了一些对称性,就出现了一种具有对称性特征的六边形架构风格。六边形架构是Alistair Cockburn在2005年提出的,其本质是倡导不同的客户通过「平等」的方式与系统交互,通过不断的扩展适配器转化成系统API所理解的参数来达到每种特定的输出,而每种特定的输出都有适配器完成相应的转化功能。
- 聚合:
- 一组具有内聚关系的相关对象的集合;
- – 是一个修改数据的最小原子单元;
- – 聚合通常使用id访问;
- 实体(Entity):表示具有生命周期并且会在其生命周期中发生改变的东西。含有VO、具有identity的特性,通常具有生命周期的概念 JPA tag @Entity;
- 值对象(Value Object):表示起描述性作用的并且可以相互替换的概念。类似于pojo,不可变immutable,可在不同模型中传递,Spring tag @value;
- 领域事件(Domain Event):所有的领域对象的跨聚合变更需要以事件方式进行通知和记录,聚合内的酌情考虑;
- 工厂(Factory):负责所有对象的生成和组装;
- 领域服务(Domain Service):纯技术层面的服务,例如日志,或者是跨聚合的编排服务,通常是Spring Component;
- 资源层(Repository):类似于DAO层,Spring JPA, Hibernate之类 @CRUDRepository;
- 防腐层:并非是系统间的消息传递机制,它的职责更具体的是指将某个模型或者契约中的概念对象及其行为转换到另一个模型或者契约中;