第1章 引入
【引入部分主要内容】
1 介绍微服务中服务注册与发现、配置管理存在的问题是什么?
2 介绍nacos是什么? 能做什么 ?
问题1: 微服务中配置文件的问题 ?
每个微服务都有配置文件,用于存放一些服务运行中可能需要修改的参数,例如:环境变化需要调整的参数:服务的地址、数据库的连接信息等。配置文件就是对这些参数的统一整合管理,实现不用修改代码就能改变服务相关功能的能力。
一般的开发中,一个服务需要包含多个环境(开发、测试、生产)的配置文件,目的是实现环境的隔离,每个环境使用的配置一般是不同的,特别是数据存储的中间件:数据库、redis等,环境隔离保证互相不干扰。在一个微服务的架构中,配置文件会随着服务数量的增多而变得越来越多,这些配置文件是相对分散的。配置文件的管理和维护成为问题。
存在的问题:
- 配置文件的数量会随着服务的增加持续的递增;
- 单个配置文件无法区分多个运行环境;
- 配置文件内容无法动态更新,需要重启服务更新的配置才能生效
---> 配置中心
配置中心解决了什么?
- 统一的配置文件管理
- 提供统一标准的接口,服务根据标准接口自行的拉取配置
- 支持动态的更新配置到所有的服务
业界常见的配置中心
- Appllo
- Disconf
- SpringCloud Config
- Nacos
问题2:微服务注册与发现的问题?
- 维护服务信息困难
- 服务健康状态不可知
- 负载均衡和容错处理复杂
---> 注册中心
注册中心解决了什么?
- 动态的服务注册发现
- 服务的健康监测
- 负债均衡
业界常见的注册中心:
第2章 Nacos
简介
1 是什么?
Nacos
/nɑ:kəʊs/
是 Dynamic Naming and Configuration Service的首字母简称,一个更易于构建云原生应用的动态服务发现、配置管理和服务管理平台。Nacos 致力于帮助您发现、配置和管理微服务。Nacos 提供了一组简单易用的特性集,帮助您快速实现动态服务发现、服务配置、服务元数据及流量管理。
2 能做什么 ?
- 服务发现和服务健康监测
- 动态配置服务
- 动态 DNS 服务
- 服务及其元数据管理
概念
配置管理 (Configuration Management)
在 Nacos 中,系统中所有配置的存储、编辑、删除、灰度管理、历史版本管理、变更审计等所有与配置相关的活动统称为配置管理。
配置服务 (Configuration Service)
在服务或者应用运行过程中,提供动态配置或者元数据以及配置管理的服务提供者。
配置项(Configuration Item)
个具体的可配置的参数与其值域,通常以 param key = param value 的形式存在。例如我们常配置系统的日志输出级别(logLevel = NFO WARN ERROR) 就是 个配置项。
配置集(Configuration Set)
组相关或者不相关的配置项的集合称为配置集。在系统中, 个配置文件通常就是 个配置集,包含了系统各个方面的配置。例如, 个配置集可能包含了数据源、线程池、日志级别等配置项。
命名空间(Namespace)
用于进行租户粒度的配置隔离。不同的命名空间下,可以存在相同的 Group 或 Data D 的配置。Namespace 的常用场景之 是不同环境的配置的区分隔离,例如开发测试环境和生产环境的资源(如数据库配置、限流阈值、降级开关)隔离等。如果在没有指定 Namespace 的情况下,默认使用 public 命名空间。
配置组(Group)
Nacos 中的 组配置集,是配置的维度之 。通过 个有意义的字符串(如 ABTest 中的实验组、对照组)对配置集进行分组,从而区分 Data D 相同的配置集。当您在 Nacos 上创建 个配置时,如果未填写配置分组的名称,则配置分组的名称默认采用 DEFAULT GROUP 。配置分组的常见场景:不同的应用或组件使用了相同的配置项,如 database url 配置和 MQ Topic 配置。
配置 ID(Data ID)
Nacos 中的某个配置集的 D。配置集 D 是划分配置的维度之 。Data D 通常用于划分系统的配置集。 个系统或者应用可以包含多个配置集,每个配置集都可以被 个有意义的名称标识。DataD 尽量保障全局唯 ,可以参考 Nacos Spring Cloud 中的命名规则:
${prefix} ${spring.profiles.active} ${file extension}权重
实例级别的配置。权重为浮点数。权重越大,分配给该实例的流量越大。
健康检查
以指定方式检查服务下挂载的实例 (Instance) 的健康度,从而确认该实例 (Instance) 是否能提供服务。根据检查结果,实例 (Instance) 会被判断为健康或不健康。对服务发起解析请求时,不健康的实例 (Instance) 不会返回给客户端。
健康保护阈值
为了防止因过多实例 (Instance) 不健康导致流量全部流向健康实例 (Instance) ,继而造成流量压力把健康实例 (Instance) 压垮并形成雪崩效应,应将健康保护阈值定义为一个 0 到 1 之间的浮点数。当域名健康实例数 (Instance) 占总服务实例数 (Instance) 的比例小于该值时,无论实例 (Instance) 是否健康,都会将这个实例 (Instance) 返回给客户端。这样做虽然损失了一部分流量,但是保证了集群中剩余健康实例 (Instance) 能正常工作。
基础架构
Nacos的领域模型
-
Nacos Config数据模型
Nacos 数据模型 Key 由三元组唯一确定, Namespace默认是空串,公共命名空间(public),
分组默认是 DEFAULT_GROUP。
- NameSpace可以区分不同的环境:开发、测试、生产环境
- Group 可用于对一个环境中的配置进行分类
- DateId 具体到某一个配置文件
一般生产环境与开发测试环境是各自部署一套nacos,保证生产环境不受影响
Namespace 的设计就是用来进行资源隔离的,在进行配置资源的时候可从以下两个角度来看:
- 从单个租户的角度来看,我们要配置多套环境的配置,可以根据不同的环境来创建 Namespace 。比如开发环境、测试环境、线上环境,创建对应的 Namespace(dev、test、prod),Nacos 会自动生成对应的 Namespace Id 。如果同⼀个环境内想配置相同的配置,可以通过Group 来区分。如下图所示:
- 从多个租户的角度来看,每个租户都可以有自己的命名空间。可以为每个用户创建⼀个命名空间,并给用户分配对应的权限,比如多个租户(zhangsan、lisi、wangwu),每个租户都想有⼀套自己的多环境配置,也就是每个租户都想配置多套环境。可以给每个租户创建⼀个 Namespace (zhangsan、lisi、wangwu)。同样会生成对应的 Namespace Id。然后使用 Group 来区分不同环境的配置。如下图所示:
Nacos 存储配置有几个比较重要的表分别是:
- config_info 存储配置信息的主表,里面包含 dataId、groupId、content、tenantId、encryptedDataKey 等数据。
- config_info_beta 灰度测试的配置信息表,存储的内容和 config_info 基本相似。有⼀个 beta_ips 字段用于客户端请求配置时判断是否是灰度的 ip。
- config_tags_relation 配置的标签表,在发布配置的时候如果指定了标签,那么会把标签和配置的关联信息存储在该表中。
- his_config_info 配置的历史信息表,在配置的发布、更新、删除等操作都会记录⼀条数据,可以做多版本管理和快速回滚。
服务注册中心的领域模型
一般会在南方和北方分别部署一个数据中心,保证同一个数据中心的请求相应很快
第3章 整合使用nacos
版本选择
版本说明 · alibaba/spring-cloud-alibaba Wiki · GitHub
springboot整合nacos的代码实操
-
服务注册与发现
下单扣减存库
代码演示
-
配置中心
演示配置中心基本使用:
从配置中心获取配置,配置动态更新
演示配置中心进阶使用:
1 实现开发、测试、生产多环境配置的动态切换
2 实现同一个服务在不同环境中有相同的配置管理
配置文件的命名:
不同环境的配置文件的命名是有规范的: 服务名-环境名.yaml
通用配置命名:服务名.yaml,实现同一个服务在不同环境下的共享的配置
3 实现不同的服务有共享的配置管理
方法1:
方法2:
优先级:
[服务名]-[spring.profile.active].yaml > [服务名].yaml > nacos拓展配置 > nacos共享配置
naocs各配置文件的优先级?
《后端程序猿 · Nacos 配置优先级&动态刷新》_nacos配置文件的执行顺序-CSDN博客
第4章 nacos的模型、原理
Nacos Config动态刷新机制
一般的动态监听方式:
维护长连接耗资源和性能
实时性不好
长轮询:推拉结合
流程图
注册中心原理
为啥用UDP协议?
基于UDP协议推送更新,优点是:
1 不可靠,但是速度快;
2 不需要建立长连接,在注册中心这个场景中,服务的消费者数量肯定是要大于服务提供者的,当服务消费者数量很多时,当服务列表更新时,如果建立TCP长连接,那nacos的性能肯定是不行的
3 怎么解决不可靠的问题,第4步中会主动拉取服务列表,可解决UDP不可靠的问题;
Nacos 健康检查机制
Nacos 提供了两种服务类型供用户注册实例时选择:临时实例和永久实例。
临时实例只是临时存在于注册中心中,会在服务下线或不可用时被注册中心剔除,临时实例会与注册中心保持心跳,注册中心会在 段时间没有收到来自客户端的心跳后会将实例设置为不健康,然后在 段时间后进行剔除。
永久实例在被删除之前会永久的存在于注册中心,且有可能并不知道注册中心存在,不会主动向注册中心上报心跳,那么这个时候就需要注册中心主动进行探活。
临时实例健康检查机制:
由客户端向注册中心发送心跳,注册中心会在连接断开或是心跳过期后将不健康的实例移除
永久实例健康检查机制:
Nacos 采用的是注册中心探测机制;注册中心会在永久服务初始化时根据客户端选择的协议类型注册探活的定时任务。Nacos 现在内置提供了三种探测的协议,即Http、TCP 以及 MySQL 。
由于持久化服务的实例的在被主动删除前 直存在的特性,探活的定时任务会不断探测服务的健康状态,并且将无法探测成功的实例标记为不健康。
有这样的场景,有些服务不希望去校验其健康状态,Nacos 也是提供了对应的白名单配置,用户可以将服务配置到该白名单,那么Nacos 会放弃对其进行健康检查,实例的健康状态也始终为用户传入的健康状态。
Nacos高并发支撑异步任务与内存队列剖析
一个消息队列,服务提供者注册时将消息放入队列,有一个监听线程在监听队列的消息变化,监听到队列中对外消息变化,就会更新服务列表并发送服务的消息变更
这里的异步读写队列,监听消息变更,快速更新列表,保证了服务注册与发现的 高性能
Nacos的CP模式和AP模式
nacos支持CP模式、AP模式
CAP理论
- C:一致性
- A:可用性
- P:分区容错性
三选二特性
分布式共识算法 Raft:
- Leader(领导者)
- Follower(跟随者)
- Candidate(候选人)
选举Leader
第5章 插件
nacos支持通过SPI的方式注入相关插件,实现鉴权、配置加密、多数据源等功能。
Nacos在跨DC部署中的应用
【跨DC调用的场景】 异地多中心,服务调用延迟时间长
解决方案:将Nacos与CMDB打通,实现同城就近的服务调用,降低调用延迟
CMDB是什么
- Configuration Management Database
- 企业存放与机器设备、应用、服务等基础设施的元数据
- 机器ip、主机名、机房、应用等
- 提供给运维或者监控平台使用这些数据进行展示和运维操作
CMDB的相关概念
- Entity可以指一个IP、应用或者服务,包含很多的属性
- Entity Type不限定在IP、应用,也可以根据业务自定义
- LABEL定义为一个描述Entity属性的K-V键值对
- Entity Event当实体属性发生变化时发出的消息
Nacos与CMDB整合
【代码演示】
多数据源插件
Nacos从2.2.0版本开始,可通过SPI机制注入多数据源实现插件,并在引入对应数据源实现后,便可在Nacos启动时通过读取application.properties
配置文件中spring.datasource.platform
配置项选择加载对应多数据源插件.本文档详细介绍一个多数据源插件如何实现以及如何使其生效。
注意: 目前多数据源插件处于Beta测试阶段,其API及接口方法定义可能会在后续版本升级而有较大修改,请注意您的插件适用版本。
插件化实现
在原来的Config模块中,所有的SQL操作的执行是通过直接使用JdbcTemplate执行固定SQL语句的形式,使得SQL语句与业务逻辑高度耦合,并且只支持Derby与MySQL两种数据源,原有Config模块架构如下。
现在的多数据源插件通过SPI机制,将SQL操作按照数据表进行抽象出多个Mapper接口,Mapper接口的实现类需要按照不同的数据源编写对应的SQL方言实现; 现在插件默认提供Derby以及MySQL的Mapper实现,可直接使用;而其他的数据源则需要用户使用数据源插件进行加载,其改造后架构图如下。
如何使用
- 用户查询当前Nacos是否支持所需数据源,Nacos默认提供Derby以及MySQL的实现,若暂未支持可参考下面插件编写者如何开发步骤开发插件自己使用或贡献;
- 在
application.properties
配置文件中将spring.datasource.platform
修改为对应的数据源名称,并配置数据源相关参数; - 然后编译运行则可支持此数据源;
插件编写者如何开发
- 引入
nacos-datasource-plugin
依赖 - 实现
com.alibaba.nacos.plugin.datasource.mapper
包下数据表对应Mapper接口中的特殊SQL方法,主要是涉及分页等方言差别,可参考com.alibaba.nacos.plugin.datasource.impl
下Derby以及MySQL的实现,只需实现对应接口即可。接口与表对应关系如下:
数据库表 | Mapper |
---|---|
config_info_aggr | ConfigInfoAggrMapper |
config_info_beta | ConfigInfoBetaMapper |
config_info | ConfigInfoMapper |
config_info_tag | ConfigInfoTagMapper |
config_tags_relation | ConfigTagsRelationMapper |
his_config_info | HistoryConfigInfoMapper |
- 编写SPI配置文件,其名字为
com.alibaba.nacos.plugin.datasource.mapper.Mapper
,写入实现Mapper接口的类,可参考config模块中Derby与MySQL配置文件。 - 插件使用者则可以通过依赖此插件,达到实现对应数据源操作的效果
- 编译运行
如何编译
编译插件之前需要先编译nacos
并安装至本地仓库.
git clone git@github.com:alibaba/nacos.git
cd nacos && mvn -B clean package install -Dmaven.test.skip=true
若出现
revision
变量无法解析,请更新maven
至最新版本
- git clone #{对应数据源插件实现Git地址}
- mvn install