likes
comments
collection
share

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

作者站长头像
站长
· 阅读数 18

本文主要有以下内容:

  • 创建 Maven 工程进行项目依赖同一管理
  • 使用 Nacos 组件进行服务注册和发现
  • 使用 OpenFeign + LoadBalance 组件进行远程服务调用和负载均衡

搭建Maven父工程进行项目依赖管理

  1. 使 idea 工具创建 maven工程,取名为 misco-service-simple

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

  1. 创建完成后,修改pom.xml文件,打包方式为 pom 则说明此工程只管理 Maven 依赖
<!--指定springboot版本 -->
<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>2.4.2</version>
</parent>
<dependencyManagement>
    <dependencies>
         <!-- Spring Cloud依赖-->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-dependencies</artifactId>
            <version>2020.0.1</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
         <!-- Spring Cloud Alibaba依赖-->
        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-alibaba-dependencies</artifactId>
            <version>2021.1</version>
            <type>pom</type>
            <scope>import</scope>
        </dependency>
    </dependencies>
</dependencyManagement>

其中需要注意的是如果 maven 父工程中使用的是 dependencies 标签,则子工程中可以直接使用父工程的引用。如果父工程中使用的是 dependencyManagement 则子工程中不能直接使用父工程引入的依赖,需要在自己的 pom 文件中引入,此时只需要添加坐标即可,不需要添加版本号。因为 dependencyManagement 对依赖进行了统一的版本管理。

用一个不恰当的例子说明:dependencyManagement就相当于餐馆的老板,老板把菜、调味品等所需要的东西备好了,厨师 子工程 只负责使用老板已备好的东西进行出菜即可。

  1. 依次创建 consumer-serviceproduce-service 项目,具体步骤如下

    1. 选中 misco-service-simple文件夹
    2. 右键 new module 选择Maven
    3. 输入项目名
  2. 创建完成后项目文件结构如下图

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

  1. 分别在两个子工程的 pom.xml 文件中引入如下依赖

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    

引入上述依赖之后,我们就可以在相应的工程中使用 @SpringBootApplication、@RestController、@RequestMapping 等注解。

  1. consumer-server 子工程中添加如下文件和代码,文件结构如下图所示:

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

其中 ConsumerController 的代码如下所示,在 application.yml中指定端口号 10001

  @RestController
  @RequestMapping("consume/")
  public class ConsumerController {
      @GetMapping("string")
      public String consumer(){
          return "consumer user";
      }
  }

ConsumerApplication 的代码如下所示

  @SpringBootApplication
  public class ConsumerApplication {
      public static void main(String[] args) {
          SpringApplication.run(ConsumerApplication.class);
      }
  }

按照相同的方法在 produce-service 子工程中创建如下的文件和代码

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

ProduceDataServiceProduceDataController 的代码如下所示

public interface ProduceDataService {
    Map<String,String> getData();
}
​
@Service
public class ProduceDataServiceImpl implements ProduceDataService{
    @Override
    public Map<String, String> getData() {
​
        Map<String,String> result = new HashMap<>();
        result.put("produce","produce a map");
        return result;
    }
}
@RestController
@RequestMapping("produce/")
public class ProduceDataController {
​
    @Resource
    ProduceDataService dataService;
​
    @GetMapping("get")
    public Map<String,String> getData(){
        return dataService.getData();
    }
}

最后在 application.yml 中指定和 consumer-serviceapplication.yml 文件中不同的端口号,避免端口冲突。

上面的所以步骤都是在做一些准备工作,此时可以分别启动这两个服务,通过 postman都能够正确运行。

Nacos 注册中心

在使用 postman工具进行测试的时候,我们通常会输入 ip:port/path1/subpath 等信息;调用后端接口,获取后端的数据,当接口不多的时候,可能觉得没什么问题。但是当接口很多且应用端口号发生变化时,我们需要维护的接口就让人头疼,尤其是在前后端分离开发的情况下,前后端同事们在对接接口这件事上,总是让人打脑壳。

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

图片来源于:juejin.cn/pin/7041953…

同样的情况在后端也会出现。如果说 consumer-service 要调用 produce-service中的服务时,使用OkHttp3或者HttpClient等网络请求框架时,如果 produce-service的端口信息或者其他信息发生变更没有告诉开发 consumer-service 服务的开发时,难免少不了一场甩锅大战。这就是Nacos或者eureka等注册中心出现的原因。

怎么去理解注册中心呢?使用过自如或者找过链家等中介平台进行租房的朋友们就知道。通常房东把自己的房子信息交给中介平台,然后为我们询问中介平台有无合适的房源进行租房。房东就相当于上面的 produce-service ,而我们就相当于消费者服务,去消费房子。

就如同有不同的中介平台一样,注册中心也很多种,只是我这里选择了 nacos 进行服务的注册。有利就有弊,注册中心帮助我们更好的管理服务,带来的最直接的影响就是我们需要去学习怎么使用注册中心。

Nacos 安装

官方提供的下载页面选择自己需要的版本,注意是在Assets节点下,我选择的版本是 2.0.3。 以 Windows 系统为例,下载之后解压文件,解压后进入 conf 目录下,需要修改以下几项:

  1. 打开 application.properites 需要打开如下几项的注释,并添加相关配置信息,

    # 默认端口号
    server.port=8848
    # 指定Nacos持久化所需要的数据库
    spring.datasource.platform=mysql
    ### Count of DB:
    db.num=1
    ### Connect URL of DB:
    db.url.0=jdbc:mysql://127.0.0.1:3306/nacos?characterEncoding=utf8&connectTimeout=1000&socketTimeout=3000&autoReconnect=true&useUnicode=true&useSSL=false&serverTimezone=Asia/Shanghai
    db.user.0=root
    db.password.0="root password"
    
  2. 创建 nacos 数据库,sql 文件在 conf 目录下的 nacos-mysql.sql

    create schema nacos;
    -- 运行nacos-mysql.sql 中的sql语句
    
  3. 如果是单机 nacos ,则在 bin 目录下,点击 startup.cmd 启动,如果要搭建集群则,需要在 conf 目录下搭建创建 cluster.conf 文件配置集群的 ip 信息

     - ip: port 这里的ip地址不能是127.0.0.1
     - IP 应该使用你本机分配到的内网 IP 地址
     - 如果你使用的是 mac 或者 linux 系统,可以在命令行使用 ifconfig | grep “inet” 命令来获取本机 IP 地址
     - windows 使用 ipconfig来获取
    

windows 为例,在命令行输入 ipconfig 图中红色圈中的信息就是内网地址。

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

此时配置文件如下


  192.168.1.7:8848
  192.168.1.7:9848
 

注:需要复制一份解压文件,分别配置相关信息!两个服务的端口号如果连续有时候会出现问题,建议设置隔开一点。

  1. 在正确配置集群之后就可以启动 nacos 服务器,启动成功后可见到如下画面。

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

  1. 通过终端的输出就可以看到访问 127.0.0.1:8848/nacos/index.html 可以登录到控制台,默认账户密码均为 nacos ,第二个红色框框表示集群的 IP 地址,第三个红框表示正确启动 Nacos

  2. 登录 Nacos 控制台之后,在左侧侧边栏点击—命名空间—点击新建命名空间—新建 dev、pre-production、production 供我们后续使用

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

微服务改造

安装完毕后,在各自的 pom.xml添加如下依赖

<dependency>
    <groupId>com.alibaba.cloud</groupId>
    <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>

在各自的 application.yml 添加 nacos 配置信息,以 produce-service 为例

server:
  port: 20000
spring:
  application:
    name: produce-application
  cloud:
    nacos:
      discovery:
        # Nacos的服务注册地址,可以配置多个,逗号分隔
        server-addr: http://192.168.1.7:8848
        # 服务注册到Nacos上的名称,一般不用配置
        # nacos客户端向服务端发送心跳的时间间隔,时间单位其实是ms
        heart-beat-interval: 5000
        # 服务端没有接受到客户端心跳请求就将其设为不健康的时间间隔,默认为15s
        # 注:推荐值该值为15s即可,如果有的业务线希望服务下线或者出故障时希望尽快被发现,可以适当减少该值
        heart-beat-timeout: 20000
        # 元数据部分 - 可以自己随便定制
        metadata:
          mydata: abc
        naming-load-cache-at-start: false
        # 命名空间ID,Nacos通过不同的命名空间来区分不同的环境,进行数据隔离,将服务进行分组
        namespace: dev
        cluster-name: Cluster-A
        group: myGroup
        register-enabled: true

配置信息给出了详细的注释,就不过多介绍。在正确配置之后,启动 nacosconsumer-serviceproduce-service 打开 nacos 控制台,可以看到我们启动的服务,

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

OpenFeign + LoadBalancer 组件

在通过上面的步骤之后,我们相当于把服务注册到 nacos 上了,但是如何调用服务?答案就是使用 OpenFeign 组件,如果你使用过其他 Http库进行服务调用如RestTemplate + @LoadBalanced 注解组合通过服务名调用远程服务,或者RestTemplate 直接 ip + port 的访问方式就能够体验到 OpenFeign 带来的快感。

前面所描述的两种调用方式,不是说他们不好,只是使用 OpenFeign 让我们开发更加丝滑,如调用本地服务一样。

consumer-servicepom.xml 文件中,引入如下依赖

<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-openfeign</artifactId>
</dependency>
<!-- 负载均衡组件 -->
<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>

注意: 如果不引入 LoadBalancer 组件,使用 OpenFeign组件后,直接启动服务,会提示缺少 LoadBalancer组件。

consumer-service创建consumer.service.feign.ProduceDataInt接口, 并添加如下代码

@FeignClient(value = "produce-application",path = "produce/")
public interface ProduceDataInt {
​
    @GetMapping("get")
    Map<String,String> getData();
}

value 属性指向 produce-servicespring.application.name, path+ getMapping 指向我们要代理的方法,方法名要和我们调用的方法名一致,包括参数顺序、个数 。只是在本例子中没有使用带参数的方法。我想用最简单的方法和最少的代码来演示各个组件的使用。这也是没有创建 entity、dao等包和类的原因。

添加完上述的代码之后在启动类上添加注解@EnableFeignClients(basePackages = "consumer.service.feign"),并通过basePackages 指向我们创建ProduceDataInt的接口所在的包,这样 Spring 就可以扫描到使用 @FeignClient 的注解,生成动态代理对象,帮助我进行服务调用。

接着修改 ConsumerController的代码

@RestController
@RequestMapping("consumer/")
public class ConsumerController {
​
    @Resource
    ProduceDataInt produceDataInt;
​
    @GetMapping("string")
    public String consumer(){
        System.out.println(produceDataInt.getData().get("produce"));
        return "consumer user";
    }
​
}

再修改 ProduceDataController 的方法如下,方便我们看日志信息。

@GetMapping("get")
public Map<String,String> getData(){
    System.out.println("service1: time = " + LocalDateTime.now());
    return dataService.getData();
}

启动produce-service服务后,修改端口 20000-->20010 通过Edit configuration修改服务允许服务并行运行。

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

然后修改输出流为System.out.println("service2: time = " + LocalDateTime.now()); 在启动produce-service服务。通过 nacos 控制台观察服务

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

此时通过postman 进行服务调用 consumer/string 两次,可以看到 produce1/produce2 各输出了一次,再调用一次produce1又输出了相应的时间信息。这是因为LoadBalancer 默认情况下时采用轮询算法进行负载均衡的。LoadBalancer 默认提供了两种算法进行负载均衡,一个是轮询算法,一个是随机算法,也可以自定义负载均衡算法。

【微服务01】Nacos + OpenFeign + LoadBalancer 的入门级用法

consumer-service 获取到了所有的 produce-service 服务实例,依次进行服务调用,这是在客户端consumer-sercice进行的。

思考&说明

  1. 为什么服务注册时,需要配置 namespace 以及group ? 答案在Nacos官网。
  2. LoadBalancer组件的负载均衡算法可以改变,也可以自定义负载均衡算法,先挖坑后面再填。
  3. RestTemplate + LoadBalance实现服务名调用的demo在后面有时间也写一下。
转载自:https://juejin.cn/post/7227128420358422565
评论
请登录