Alibaba微服务组件Nacos注册中心

1. 什么是 Nacos
        官方:一个更易于构建云原生应用的动态 服务发现( Nacos Discovery ) 服务配置( Nacos Config ) 和服务管理平台。
集 注册中心+配置中心+服务管理 平台
        Nacos 的关键特性包括:
        服务发现和服务健康监测
        动态配置服务
        动态 DNS 服务
        服务及其元数据管理
2. Nacos 注册中心
管理所有微服务、解决微服务之间调用关系错综复杂、难以维护的问题;
        2.1 注册中心演变及其设计思想

1. 最初的单体应用时代, 如果我一个服务是产品服务,一个试订单服务. 产品服务想要去访问订单服务, 我们都是怎么做的呢?

Alibaba微服务组件Nacos注册中心_第1张图片

 也就是说: 商品服务调用订单服务, 通过的是http远程调用的方式实现的, 这样的问题是什么呢?

  • 如果订单服务宕机了, 商品服务还能调通么?
  • 如果订单服务的ip地址更改了, 商品服务的远程调用地址是不是也要一起发生变化?
  • 如果订单服务一台服务器不够用了,  需要增加一台服务器, 商品服务就要自己维护一个订单服务的ip列表. 并按照一定规则访问

这就是单体服务的问题, 因为ip是写死在商品服务里面的, 所以, 一旦发生变化, 不能自动感知, 必须手动修改. 

2. 订单服务流量增多, 变成了多个订单服务

Alibaba微服务组件Nacos注册中心_第2张图片

这个时候, 我们怎么做的呢? 我们要满足实际业务的需求, 订单量太大了, 单台服务器经常支撑不了了, 于是就想到, 部署多台服务来分担压力.

就出现了上面的模型, 可是, 这个模型存在什么样的问题呢?

  • 程序员自己维护的ip列表, 如果订单服务某一台挂了怎么办, 那就请求不通了
  • 如果订单服服务依然不能满足需求, 还要继续扩容, 程序员又要重新维护一份订单服务的ip列表. 

手动维护ip列表肯定不好, 一方面一旦有任何变动, 就需要进行维护; 另一方面, 从效率上来讲, 也不高. 还容易出错. 于是慢慢有就有了nginx

3. 使用nginx来维护订单服务的ip列表

Alibaba微服务组件Nacos注册中心_第3张图片

 商品服务的所有请求过来了, 不要直接去请求订单服务. 通过nginx去请求订单服务. 在nginx中维护了订单服务的ip列表. 并且可以指定负载均衡策略.

嗯, 这个选择好像还不错, 不用程序员经常改商品服务代码了, 也不用程序员自己写如何分配请求的流量了. 那么他就满足我们所有的需求么?当然也不是

  • 虽然程序员不用在代码中维护ip列表了, 但是在nginx中依然要维护. 如果订单服务有很多很多, 怎么办? 我们知道在nginx上是通过upstream来维护ip的, 如果有成百上千的服务, 那么我们要维护成百上千个ip么?
  • 如果订单服务扩缩容了, 是不是一样要修改nginx的配置文件呢?

于是我们就想,有没有一种办法, 能够让微服务自动的就被注册上呢?这个需求迫在眉睫

4. 于是, 就有了注册中心的概念. 最初, 我们的想法也很简单

Alibaba微服务组件Nacos注册中心_第4张图片

首先有一个数据库表来维护所有的服务, 并标记这些服务的启动状态

然后, 每当有一个服务启动, 那么都调用注册接口, 其实注册接口就是一个insert服务器信息到数据库的过程

第三, 每次商品服务要调用订单服务了, 先去数据库里面查询可用的订单服务列表. 然后根据策略选择服务ip, 

第四, 根据ip发送请求. 

这里面也会有一些问题

  • 服务宕机了怎么办? 还来不及发出通知
  • 每次商品服务调用订单服务, 都要去数据库查询可用的服务列表, 这样当流量大了, 就会给数据库造成很大的压力, 而且, 每次都查数据库, 效率也不高. 
  • 注册中心宕机 了怎么办?

于是, 想到将我们的注册中心进行改造. 改造的更加完美一些

5. 改造后的注册中心

Alibaba微服务组件Nacos注册中心_第5张图片

 这个就是在上面的基础上改造过来的

1. 增加了一个last_heartTime, 记录心跳时间.

2. 当商品服务和订单服务启动的时候, 需要调用注册接口, 告诉注册中心, 我上线了, 实质上这是一个insert记录的过程

3. 商品服务和订单服务有一个定时任务timetask1, 定期发送心跳. 然后注册中心就会修改这个心跳时间. 通常是30秒发送一次. 

4. 商品服务有一个定时任务timerTask2, 定期去任务中心拉取服务列表, 并将其保存在客户端缓存中, 当请求过来的时候, 通过ribbon拉取客户端缓存的ip, 按照负载均衡策略, 选择指定的订单服务发送远程调用, 

5. 在注册中心有一个定时任务timerTask3,  如果注册中心在规定的时间内, 没有收到微服务的心跳, 那么就认为服务挂了, 将其状态设置为down, 下次拉取的时候, 这台服务器不会被拉取过去. 其实,这是一个状态修改的过程

6. 当服务停止的时候, 会调用服务注销接口, 通知注册中心,服务停止, 注册中心就是将其从注册表中删除. 其实这就是一个delete记录的过程

2.3 核心功能
Nacos Discovery
服务注册 Nacos Client 会通过发送 REST 请求的方式向 Nacos Server 注册自己的服务,提供自身的元数据,比如 ip 地 址、端口等信息。Nacos Server 接收到注册请求后,就会把这些元数据信息存储在一个双层的内存 Map 中。
服务心跳 :在服务注册后, Nacos Client 会维护一个定时心跳来持续通知 Nacos Server ,说明服务一直处于可用状态,防 止被剔除。默认5s 发送一次心跳。
服务同步 Nacos Server 集群之间会互相同步服务实例,用来保证服务信息的一致性。 leader raft
服务发现 :服务消费者( Nacos Client )在调用服务提供者的服务时,会发送一个 REST 请求给 Nacos Server ,获取上面 注册的服务清单,并且缓存在Nacos Client 本地,同时会在 Nacos Client 本地开启一个定时任务定时拉取服务端最新的注 册表信息更新到本地缓存
服务健康检查 Nacos Server 会开启一个定时任务用来检查注册服务实例的健康情况,对于超过 15s 没有收到客户端心跳 的实例会将它的healthy 属性置为 false( 客户端服务发现时不会发现 ) ,如果某个实例超过 30 秒没有收到心跳,直接剔除该 实例( 被剔除的实例如果恢复发送心跳则会重新注册 )
主流的注册中心
CAP C 一致性 A可用性 P 分区容错性
Alibaba微服务组件Nacos注册中心_第6张图片
3 Nacos Server 部署
单机启动 nacos ,执行命令
bin/startup.sh ‐m standalone

也可以修改默认启动方式

Alibaba微服务组件Nacos注册中心_第7张图片

访问 nocas 的管理端: http://127.0.0.1:8848/nacos ,默认的用户名密码是 nocas/nocas

Alibaba微服务组件Nacos注册中心_第8张图片

搭建Nacos-client服务

父级maven



    4.0.0

    org.example
    spring-nacos
    pom
    1.0-SNAPSHOT
    
        firsrt-nacos
        two-nacos
    
    

        1.8
        2.2.5.RELEASE
        2.3.11.RELEASE
        Hoxton.SR8
    

    
        
        
        
            org.springframework.boot
            spring-boot-dependencies
            ${spring.boot.version}
            pom
            import
        
        
        
            com.alibaba.cloud
            spring-cloud-alibaba-dependencies
            ${spring.cloud.alibaba.version}
            pom
            import
        
        
        
            org.springframework.cloud
            spring-cloud-dependencies
            ${spring.cloud.version}
            pom
            import
        
        
    




firsrt-nacos 项目



    
        spring-nacos
        org.example
        1.0-SNAPSHOT
    
    4.0.0

    firsrt-nacos

    
        8
    
    
        
        
            com.alibaba.cloud
            spring-cloud-starter-alibaba-nacos-discovery
        

        
            org.springframework.boot
            spring-boot-starter-web
        
    

application.properties

server.port=8002
#微服务名称
spring.application.name=firsrt-nacos
#配置 Nacos server 的地址
spring.cloud.nacos.discovery.server‐addr=localhost:8848

TestController 

package com.yqx.controller;

import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

/**
 * @author yanqx
 * @date 2023/11/13  14:18
 */
@RestController
@RequestMapping("/order")
public class TestController {


    @Value("${server.port}")
    String port;

    @RequestMapping("/reduct")
    public String reduct() throws InterruptedException {
        System.out.println("扣减库存");
        return "扣减库存:"+port;
    }
}

启动后会发现  

Alibaba微服务组件Nacos注册中心_第9张图片

Alibaba微服务组件Nacos注册中心_第10张图片

two-nacos 项目

pom



    
        spring-nacos
        org.example
        1.0-SNAPSHOT
    
    4.0.0

    two-nacos

    
        8
    
    
        
        
            com.alibaba.cloud
            spring-cloud-starter-alibaba-nacos-discovery
        

        
            org.springframework.boot
            spring-boot-starter-web
        
    

application.properties

server.port=8003
#微服务名称
spring.application.name=two-nacos
#配置 Nacos server 的地址
spring.cloud.nacos.discovery.server‐addr=localhost:8848
Application
package com.yqx;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.loadbalancer.LoadBalanced;
import org.springframework.context.annotation.Bean;
import org.springframework.web.client.RestTemplate;

/**
 * @author yanqx
 * @date 2023/11/13  14:10
 */
@SpringBootApplication
public class TwoNacosApplication {

    @Bean
    @LoadBalanced
    public RestTemplate restTemplate() {
        return new RestTemplate();
    }

    public static void main(String[] args) {
        SpringApplication.run(TwoNacosApplication.class, args);
    }

}

调用第一个方法的controller 

package com.yqx.controller;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;

/**
 * @author yanqx
 * @date 2023/11/13  14:53
 */
@RestController
@RequestMapping("/two")
public class TwoController {


    @Autowired
    RestTemplate restTemplate;

    @RequestMapping("/add")
    public String add(){
        System.out.println("下单成功!");

        String msg = restTemplate.getForObject("http://firsrt-nacos/order/reduct", String.class);
        return "Hello World"+msg;
    }
}

 Nacos注册中心架构

Alibaba微服务组件Nacos注册中心_第11张图片

你可能感兴趣的:(微服务专题,微服务,java,架构)