微服务的许多优点,例如缩短开发时间、小且独立发布、分散管理等引入了一系列挑战,像是版本控制,测试,部署和配置管理。本文提供了一个方法,来处理微服务复杂的构建、测试和部署程序。
问题说明
构建、测试和部署程序对于那些只有很少的微服务和普通服务的项目来说是非常简单的。通常,一个解决方案有2-3个Docker镜像,服务和UI,因此它很容易执行集成、测试,我们因此得出结论——服务与UI和其他兼容。版本控制策略也可以很简单,直接用程序文件的版本(pom, nuget或其他)。即使部署到生产环境,也可以为每个微服务手工完成
当下面的情况发生时,情况就会发生巨变:
- 解决方案被分为几个独立的“数据流”,每个“数据流”有一组微服务和UI。
- 每个微服务都有它自己的寿命和发布周期。
- 不同团队(甚至竞争关系)在同样的项目上工作。
- 微服务从一个“数据流”运行时,依赖来自另一个“数据流”的微服务。
- 微服务取决于生态系统(常用的服务,比如AAA、日志记录等等)。
当每个微服务有它自己的部署和运行配置时,情况变得更为复杂。举个例子,在一个测试环境中,一个微服务不需要安装多种实例,但却是生产所需。因此我们需要处理至少3-n维数组:
- 容器化微服务 Docker/LXC/OS镜像
- 部署配置
- 运行配置
这些还需要进行管理。
另外,项目中还可能存在一些额外的约束和需求。我们还需要考虑一些额外的要求:
- 不变的服务器范式。
- 未经测试微服务不得出现在资源中。
- 通过测试程序的每个构建是有可能交付的。
- 整个解决方案的部署/回滚程序应尽可能简单,而且避免处理不同的微服务的复杂性,它们都有不同的版本。
构建程序
微服务管道
当世界上其他国家休息时,微服务必须继续工作,所以下面的结果是正确的——首先它必须被分别构建和测试。一个微服务的管道应该与下图类似。
步骤:
- 合并代码变更到SCM中master/构建分支,将触发构建程序。
- 在构建程序期间,执行单元测试和组件测试。静态代码分析也可以执行来通过源代码质量检验关。
- 发布构建工件到临时资源库。
- 从模板中创建临时部署描述符。Velocity、Groovy或任何其他模板都可以用于Jenkins。
- 部署到开发环境,不管集成测试结果允许开发人员手动检查。
- 部署到测试环境并开始集成测试。有外部化的测试场景和程序比较好。
- 在通过案例集成测试时发布到存储库中。触发与其他微服务的集成。
端到端测试管道
在此阶段,一组微服务将与其他微服务的***稳定版本集成。
步骤:
- 下游构建发送的名称和微服务的版本,微服务已变更。
- 构建服务器加载所有现有微服务的***版本号。简单的属性文件就够了。
- 与新版本合并。版本和部署模板的集合用于创建部署描述符。
- 部署微服务使用一组变更了版本的部署描述符,并运行集成测试。
- 如果通过测试程序,构建服务器将持续一组微服务,版本设置为“集成测试前”,为了下次使用。
- 构成配置和发布。为了简化部署过程,创建一个“uber”部署描述符,它将包括所有必要的微服务、配置变量等。
集成测试前
端到端的集成测试工作拥有所有微服务的***版本,已经成功地通过了集成测试。“集成测试前”加上变更将提供必须测试的微服务版本集。
所有微服务的集成测试,可以说是通过集成测试的每一个构建都有可能交付的。
提示和陷阱
使用“***”的反面模式来部署服务并不是一个好办法,需要指定微服务的确切版本,因为不是所有的服务变更都需要重新部署。
几乎不可能为每个环境测试所有可能的微服务版本配置,在大多数情况下实际上是不需要的。
***每次都重新创建测试环境。
保持Jenkins管道作为源代码的一部分。
尽量避免使用Spring Cloud config server等外部化的运行时配置。***使用部署描述符提供配置值。