问题: nacos是怎么进行服务发现的?
步骤:
1、引入pom文件
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
2、查看jar包下的spring.factories文件
2.1 存在类com.alibaba.cloud.nacos.registry.NacosServiceRegistryAutoConfiguration
其中存在3个bean
NacosServiceRegistry
NacosRegistration
NacosAutoServiceRegistration
3、NacosServiceRegistryAutoConfiguration上有一个注解@AutoConfigureAfter
中有一个类AutoServiceRegistrationAutoConfiguration
其中注入一个bean AutoServiceRegistration下的AbstractAutoServiceRegistration实现了spring的ApplicationListener接口
当ServletWebServerInitializedEvent事件监听成功 调用onApplicationEvent方法
3.1、执行this.bind()方法
3.2、执行this.start()方法
3.3、执行this.register()方法
4、调用namingService.registerInstance()方法
调用NameingProxy.registerService()方法
4.1 心跳 beatReactor.addBeatInfo
4.1.1 BeatTask —> serverProxy.sendBeat() —> 调用 /instance/beat 接口
4.1.2 InstanceController.beat —> serviceManager.getInstance 获取服务
—> 如果不存在 则注册服务 serviceManager.registerInstance
—> service.processClientBeat 开启任务 维护客户端实例心跳(ClientBeatProcessor.run)
—> 15s未收到心跳 则把健康状态设置为false 30s未收到就调用deleteIps删除该节点
5、调用 /nacos/v1/ns/instance 注册
6、调用com.alibaba.nacos.naming.controllers.InstanceController#register方法
6.1、InstanceController.register —> serviceManager.registerInstance —>
6.1.1、createEmptyService 创建新的服务容器 —> putAndInitService
putService() ==> Map<namespace, Map<group::serviceName, Service>>
service.init() ==> HealthCheckReactor.scheduleCheck维护健康检查心跳 ==> 执行线程的run方法
==> distroMapper.responsible() 使用服务名hash取模, 选择集群中一台机器执行任务
==> 15s没有收到心跳 将值设置为false 30s没有收到心跳 剔除该实例 调用deleteIp
6.1.2、addInstance 将service实例写入内存注册表 ==> consistencyService.put()
根据是否是永久实例调用不同方法 ==> DistroConsistencyServiceImpl.put() ==> onPut()
notifier.addTask()放入队列