一、为什么需要注册中心
在以前的单体服务中,我们是不需要这个组件的,因为业务之间的调用都是本地调用,不涉及到网络通信。
但是现在通常采用微服务分布式架构,即一个大单体服务拆分为多个微服务,一个微服务又存在多个实例,并且许多的服务节点通常是运行在k8s中的,节点随时启动、随时杀掉,ip经常变化,所以服务之间的调用不大可能是事先配置好的,而是动态变化的,这个时候就需要一个组件来解决微服务之间通信地址随时变化的问题。
这就是注册中心存在的意义。
二、注册中心的原理
服务发现,归根到底其实很简单,我们分为三种角色:1、服务提供者,2、服务消费者、3、注册中心。服务提供者在服务启动的时候将服务的ip + port以及其他的信息注册到注册中心中,然后服务消费者通过读取注册中心已经注册的信息来获取远程通信的方式。
但是因为这是一个关键的组件,我们所有的微服务之间的调用关系都依赖它,所以需要高可用,那么高可用就会涉及到一个数据一致性的问题,nacos支持同时支持AP和CP两种方式来用满足户对于数据一致性的要求。
三、注册中心的四个核心要点
- 1、Service provider把自己的服务地址注册到注册中心
- 2、Service consumer需要从注册中心上去查询Service provider的地址(根据服务名称)
- 3、注册中心需要感知到Service provider的上下线的变化
- 4、Service consumer需要”动态感知“到注册中心端服务地址的变化
四、Eureka目前存在的问题?
- Eureka1.0 现在已经不维护了
- 出现高位漏洞时,解决会相当麻烦
- 不健康的节点下线时间过长,导致流量进入不健康节点
五、什么是nacos?
Nacos致力于帮助您发现、配置和管理微服务。Nacos提供了一组简单易用的特性集,帮助您快速实现动态服务发现、服务配置、服务元数据及流量管理。
从上边的描述我们就可以看出nacos其实集成了服务发现、服务配置、服务管理的三个功能,但是我们这里调研它主要是用做注册中心。
六、nacos架构及概念
七、单节点部署并集成到spring cloud
实现步骤
一、启动nacos server
1、下载最新的稳定版本
首先需要下载最新的稳定版本,因为稳定版本经过大量的测试以及生产应用,且到目前为止没有出现大量的bug。
因为当前最新的稳定版本是:1.4.2,所以我们这里采用它来作为测试目标 地址:nacos-server-1.4.2.zip75.4 MB
2、解压并配置
在nacos中需要依赖使用到mysql作为存储,当然它默认有一个嵌入的数据库——derby,但我们查看数据就不太方便了,所以我们先解压进入到conf目录,打开application.properties文件,编辑如下的内容:
db.num=1
db.url.0=jdbc:mysql://127.0.0.1:3306/nacos_config?characterEncoding=utf8&connectTimeout=1000&socketTimeout=3000&autoReconnect=true&useUnicode=true&useSSL=false&serverTimezone=UTC
db.user.0=root
db.password.0=xxxxxxx
然后将目录中的nacos-mysql.sql文件执行了。
问题
如果不使用nacos的配置中心,是否还需要配置数据库? 答案:必须使用数据库,因为我们使用nacos虽然不是用来当做配置中心,但是nacos仍然有权限、用户管理等等功能需要使用到数据库。
3、启动服务
进入到bin目录,执行:
> sh startup.sh -m standalone
因为我们在本地测试,所以这里是采用单点模式,若是在生产,则去掉后边的-m standalone进入集群模式,并且在./conf/cluster.conf中配置集群节点的地址。
4、访问web管理界面
- 控制界面目录:http://127.0.0.1:8848/nacos/index.html
- 用户名和密码默认均为:nacos
二、和spring boot、spring cloud集成
1、添加依赖
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
<version>1.5.1.RELEASE</version>
</dependency>
因为我们使用的spring boot 1.5.4,所以需要使用spring-cloud-starter-alibaba-nacos-discovery 1.5.x
2、配置nacos server的地址
我们需要在各个微服务配置中添加nacos server的地址,类似于使用eureka时配置的eureka.client.serviceUrl.defaultZone。
// 配置nacos server的地址
spring.cloud.nacos.discovery.server-addr=127.0.0.1:8848
// 开启nacos作为微服务的注册中心,false则关闭
spring.cloud.nacos.discovery.enabled=true
// 服务分组-设置服务所处的分组
spring.cloud.nacos.discovery.group=DEFAULT_GROUP
.....
还要一些其他的配置,具体参考官方文档:Nacos discovery
3、开启服务发现功能
这一点和使用eureka基本一致,只需要在启动类中添加注解即可(添加@EnableDiscoveryClient注解),我们在使用Feign来作为远程调用的时候负载均衡的默认策略是轮询
八、部署类型
Nacos定义为一个IDC内部应用组件,并非面向公网环境的产品,建议在内部隔离网络环境中部署,强烈不建议部署在公共网络环境。
Nacos支持三种部署模式
- 单机模式 - 用于测试和单机试用。
- 集群模式 - 用于生产环境,确保高可用。
- 多集群模式 - 用于多数据中心场景。
九、碰到的问题
1、在mac系统中启动nacos的时候失败,报错:nohup: /Library/Internet: No such file or directory
原因:这是因为macBig Sur系统中自带java虚拟机,而且目录中还存在空格,导致nacos无法解析而出现失败
解决方法:将JAVA_HOME指定为自己安装的JDK目录,并且source 参考 : #4227
十、nacos一些功能的源码实现
1、nacos是如何实现健康检查的?
健康检查在nacos中分为两种类型:
- 临时实例:采用客户端主动上报心跳,默认发送心跳是5秒钟一次,Nacos服务端会在15秒没收到心跳后将实例设置为不健康,在30秒没收到心跳时将这个临时实例摘除。
- 持久实例:持久实例则是
nacos server主动发起心跳检测,最常用的是TCP端口探测和HTTP接口返回码探测,这两种类型的探测能够满足绝大部分的情况了,但是有一些情况时不能通过这两种方式来解决的,例如关于数据库可用性的探测,可能就需要执行一个sql才能判定。
tcp检查
具体类和方法:TcpSuperSenseProcessor -> TaskProcessor -> call()
通过ip和端口发起tcp连接,
http检查
位置:HttpHealthCheckProcessor -> process()
发起一个http请求,并且设置回调处理的类
回调处理
检查这个http请求的响应码是否为200,否则之后在尝试。
mysql检查
类:MysqlHealthCheckProcessor -> MysqlCheckTask -> run()
通过创建一个连接来执行SQL,若是成功则说明节点正常,否则节点不健康。这里的sql执行就很有讲究,到底是执行select 1还是查询,抑或是执行插入等等,要确保数据库能够健康我们需要小心的设计执行的sql,一般来说在数据库中执行插入、更新会更有效地保证数据库的健康,而不是查询。
2、客户端注册及数据结构?
3、nacos一致性协议
在注册中心的几个开源实现中比较有代表性的就是Zookeeper、Eureka,他们的共识协议分别是CP和AP,在Zookeeper中采用paxos协议实现强一致性,而Eureka则采用自己定制的renew协议,实现保证最终一致性。
下图则是nacos所支持的两种一致性协议。
总结
这篇短文先介绍了注册中心出现的内在原因,以及注册中心需要解决的四个主要问题,Eureka目前存在的一些缺点。之后还记录了nacos的单节点部署以及和spring cloud集成,最后简单展示了Nacos实现心跳、客户端发起注册功能的源码,希望对你有所帮助。