资讯详情

SpringCloud无介绍快使用,Ribbon负载均衡工具与OpenFeign的使用(十五)

SpringCloud无介绍快使用,Ribbon负载平衡工具和OpenFeign使用(十五)

  • 问题背景
  • Ribbon负载均衡
  • OpenFeign默认使用Ribbon做负载均衡
  • Lyric: 土耳其冰淇淋 就像女人的心

问题背景

从零开始学springcloud微服务项目 注意事项:

  • IDEA版本2021.1
  • 这个项目,我分了很多章节,每篇文章都有一个操作步骤,目的是看起来更简单清晰
  • controller调service,service调dao
  • 项目源代码及sentinel安装包

Ribbon负载均衡

1 Spring Cloud Ribbon是基于Netflix Ribbon一套客户端负载均衡的工具

2 集中式LB

  • 在服务的消费者和提供者之间使用独立的服务LB设施(如硬件)F5, 也可以是软件,比如nginx), 该设施负责通过某种策略将访问请求转发给服务提供商

3 进程内LB

  • 将LB逻辑集成到消费者身上,消费者从服务注册中心了解可用的地址,然后从这些地址中选择合适的服务器
  • Ribbon属于过程内LB,它只是一个集成在消费者过程中的类库,消费者通过它获得服务提供商的地址

4 Ribbon客户端本地负载均衡 VS Nginx负载均衡差异的服务端

  • Nginx服务器负载载的平衡,客户端的所有要求都会交客户nginx,然后由nginx转发请求的实现。即服务端实现负载平衡
  • Ribbon本地负载均衡,在调用微服务界面时,在注册中心获取注册信息服务列表后,缓存至JVM本地实现RPC远程服务调用技术

5 Ribbon工作时分为两步

  • 首先选择第一步 EurekaServer ,它优先考虑同一区域负载较少的情况server
  • 第二步是遵循用户指定的策略server选择服务注册列表中的地址。Ribbon根据响应时间提供轮询、随机、加权等多种策略
  • Ribbon事实上,它是一个软负载平衡的客户端组件,可以与其他需要的客户端结合使用eureka组合只是一个例子

6 前面几个篇章就是使用了Ribbon负载均衡,RestTemplate @LoadBalanced实现负载平衡,包括使用依赖Eureka-client中

<!--eureka-client--> <dependency>        <groupId>org.springframework.cloud</groupId>        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId> </dependency> 

OpenFeign默认使用Ribbon做负载均衡

1 OpenFeign集成了Ribbon

  • 利用Ribbon维护了Payment通过轮询实现客户端负载平衡的服务列表信息。Ribbon不同的是,通过feign服务调用只需要定义服务绑定接口并以声明的方式进行,优雅简单 2 新增module 3 选择jdk1.8 4 输入服务名:cloud-consumer-feign-order80

5 复制cloud-consumer-order80到cloud-consumer-feign-order80 更改pom依赖

<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0"          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"          xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">     <parent>         <artifactId>springcloud2022</artifactId>         <groupId>com.yg</groupId>         <version>1.0-SNAPSHOT</version>     </parent>     <modelVersion>4.0.0</modelVersion>      <artifactId>cloud-consumer-feign-order80</artifactId>      <dependencies>         <!--openfeign-->         <dependency>             <groupId>org.springframework.cloud</groupId>             <artifactId>spring-cloud-starter-openfeign</artifactId>         </dependency>         <!--eureka-client-->         <dependency>             <groupId>org.springframework.cloud</groupId>             <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>         </dependency>         <dependency><!-- 引入自定义api一般包,可用Payment支付Entity -->             <groupId>com.yg</groupId>             <artifactI>cloud-api-commons</artifactId>
            <version>${project.version}</version>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-actuator</artifactId>
        </dependency>

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-devtools</artifactId>
            <scope>runtime</scope>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <optional>true</optional>
        </dependency>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-test</artifactId>
            <scope>test</scope>
        </dependency>
    </dependencies>

</project>

更改application文件,添加超时连接控制和日志增强

server:
  port: 80


spring:
  application:
    name: cloud-consumer-order


eureka:
  client:
    #表示是否将自己注册进EurekaServer默认为true。
    register-with-eureka: true
    #是否从EurekaServer抓取已有的注册信息,默认为true。单节点无所谓,集群必须设置为true才能配合ribbon使用负载均衡
    fetchRegistry: true
    service-url:
      #defaultZone: http://localhost:7001/eureka
      defaultZone: http://eureka7001.com:7001/eureka,http://eureka7002.com:7002/eureka
  instance:
    instance-id: order80
    prefer-ip-address: true     #访问路径可以显示IP地址

#设置feign客户端超时时间(OpenFeign默认支持ribbon)
ribbon:
  #指的是建立连接所用的时间,适用于网络状况正常的情况下,两端连接所用的时间
  ReadTimeout: 5000
  #指的是建立连接后从服务器读取到可用资源所用的时间
  ConnectTimeout: 5000

logging:
  level:
    # feign日志以什么级别监控哪个接口
    com.yg.springcloud.service.PaymentFeignService: debug

更改启动类

package com.yg.springcloud;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.cloud.openfeign.EnableFeignClients;

/** * @Author suolong * @Date 2022/6/15 15:10 * @Version 2.0 */
@EnableEurekaClient
@EnableFeignClients
@SpringBootApplication
public class FeignMainApp80 { 
        

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

}

添加openFeign的日志打印配置

package com.yg.springcloud.config;

import feign.Logger;
import org.springframework.cloud.client.loadbalancer.LoadBalanced;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.client.RestTemplate;

/** * @Author suolong * @Date 2022/6/15 20:53 * @Version 2.0 */
@Configuration
public class ApplicationContextConfig { 
        

    @Bean
    @LoadBalanced // 使用@LoadBalanced注解赋予RestTemplate负载均衡的能力
    public RestTemplate restTemplate()
    { 
        
        return new RestTemplate();
    }


    @Bean
    Logger.Level feignLoggerLevel()
    { 
        
        return Logger.Level.FULL;
    }

}

更改controller

package com.yg.springcloud.controller;

import com.yg.springcloud.entities.CommonResult;
import com.yg.springcloud.entities.Payment;
import com.yg.springcloud.service.PaymentFeignService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;

import javax.annotation.Resource;

/** * @Author suolong * @Date 2022/6/15 20:54 * @Version 2.0 */

@RestController
public class OrderController { 
        


    //public static final String PaymentSrv_URL = "http://localhost:8001";
    public static final String PaymentSrv_URL = "http://CLOUD-PAYMENT-SERVICE";


    @Autowired
    private RestTemplate restTemplate;


    @Resource
    private PaymentFeignService paymentFeignService;

    @GetMapping(value = "/consumer/feign/get/{id}")
    public CommonResult<Payment> getPaymentById(@PathVariable("id") Long id)
    { 
        
        return paymentFeignService.getPaymentById(id);
    }

    @GetMapping("/consumer/payment/create") //客户端用浏览器是get请求,但是底层实质发送post调用服务端8001
    public CommonResult create(Payment payment) { 
        
        return restTemplate.postForObject(PaymentSrv_URL + "/payment/create", payment, CommonResult.class);
    }


    @GetMapping("/consumer/payment/get/{id}")
    public CommonResult getPayment(@PathVariable Long id) { 
        
        return restTemplate.getForObject(PaymentSrv_URL + "/payment/get/" + id, CommonResult.class, id);
    }

}

添加feign调用

package com.yg.springcloud.service;

import com.yg.springcloud.entities.CommonResult;
import com.yg.springcloud.entities.Payment;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.stereotype.Component;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;

/** * @Author suolong * @Date 2022/6/19 15:06 * @Version 2.0 */
@Component
@FeignClient(value = "cloud-payment-service")
public interface PaymentFeignService { 
        

    @GetMapping(value = "/payment/get/{id}")
    CommonResult<Payment> getPaymentById(@PathVariable("id") Long id);

}

6 整体目录结构

7 postman测试:http://localhost/consumer/feign/get/1

  • 8001和8002服务器交替出现,说明openfeign自带ribbon负载均衡
  • 消费方也打印详细feign调用的日志
2022-06-19 15:25:02.356 DEBUG 34144 --- [p-nio-80-exec-2] c.y.s.service.PaymentFeignService        : [PaymentFeignService#getPaymentById] ---> GET http://cloud-payment-service/payment/get/1 HTTP/1.1
2022-06-19 15:25:02.356 DEBUG 34144 --- [p-nio-80-exec-2] c.y.s.service.PaymentFeignService        : [PaymentFeignService#getPaymentById] ---> END HTTP (0-byte body)
2022-06-19 15:25:02.469  INFO 34144 --- [p-nio-80-exec-2] c.netflix.config.ChainedDynamicProperty  : Flipping property: cloud-payment-service.ribbon.ActiveConnectionsLimit to use NEXT property: niws.loadbalancer.availabilityFilteringRule.activeConnectionsLimit = 2147483647
2022-06-19 15:25:02.496  INFO 34144 --- [p-nio-80-exec-2] c.n.u.concurrent.ShutdownEnabledTimer    : Shutdown hook installed for: NFLoadBalancer-PingTimer-cloud-payment-service
2022-06-19 15:25:02.496  INFO 34144 --- [p-nio-80-exec-2] c.netflix.loadbalancer.BaseLoadBalancer  : Client: cloud-payment-service instantiated a LoadBalancer: DynamicServerListLoadBalancer:{ 
        NFLoadBalancer:name=cloud-payment-service,current list of Servers=[],Load balancer stats=Zone stats: { 
        },Server stats: []}ServerList:null
2022-06-19 15:25:02.501  INFO 34144 --- [p-nio-80-exec-2] c.n.l.DynamicServerListLoadBalancer      : Using serverListUpdater PollingServerListUpdater
2022-06-19 15:25:02.518  INFO 34144 --- [p-nio-80-exec-2] c.netflix.config.ChainedDynamicProperty  : Flipping property: cloud-payment-service.ribbon.ActiveConnectionsLimit to use NEXT property: niws.loadbalancer.availabilityFilteringRule.activeConnectionsLimit = 2147483647
2022-06-19 15:25:02.518  INFO 34144 --- [p-nio-80-exec-2] c.n.l.DynamicServerListLoadBalancer      : DynamicServerListLoadBalancer for client cloud-payment-service initialized: DynamicServerListLoadBalancer:{ 
        NFLoadBalancer:name=cloud-payment-service,current list of Servers=[10.2.0.85:8001, 10.2.0.85:8002],Load balancer stats=Zone stats: { 
        defaultzone=[Zone:defaultzone;	Instance count:2;	Active connections count: 0;	Circuit breaker tripped count: 0;	Active connections per server: 0.0;]
},Server stats: [[Server:10.2.0.85:8002;	Zone:defaultZone;	Total Requests:0;	Successive connection failure:0;	Total blackout seconds:0;	Last connection made:Thu Jan 01 08:00:00 CST 1970;	First connection made: Thu Jan 01 08:00:00 CST 1970;	Active Connections:0;	total failure count in last (1000) msecs:0;	average resp time:0.0;	90 percentile resp time:0.0;	95 percentile resp time:0.0;	min resp time:0.0;	max resp time:0.0;	stddev resp time:0.0]
, [Server:10.2.0.85:8001;	Zone:defaultZone;	Total Requests:0;	Successive connection failure:0;	Total blackout seconds:0;	Last connection made:Thu Jan 01 08:00:00 CST 1970;	First connection made: Thu Jan 01 08:00:00 CST 1970;	Active Connections:0;	total failure count in last (1000) msecs:0;	average resp time:0.0;	90 percentile resp time:0.0;	95 percentile resp time:0.0;	min resp time:0.0;	max resp time:0.0;	stddev resp time:0.0]
]}ServerList:org.springframework.cloud.netflix.ribbon.eureka.DomainExtractingServerList@27468f17
2022-06-19 15:25:02.575 DEBUG 34144 --- [p-nio-80-exec-2] c.y.s.service.PaymentFeignService        : [PaymentFeignService#getPaymentById] <--- HTTP/1.1 200 (219ms)
2022-06-19 15:25:02.575 DEBUG 34144 --- [p-nio-80-exec-2] c.y.s.service.PaymentFeignService        : [PaymentFeignService#getPaymentById] connection: keep-alive
2022-06-19 15:25:02.575 DEBUG 34144 --- [p-nio-80-exec-2] c.y.s.service.PaymentFeignService        : [PaymentFeignService#getPaymentById] content-type: application/json
2022-06-19 15:25:02.575 DEBUG 34144 --- [p-nio-80-exec-2] c.y.s.service.PaymentFeignService        : [PaymentFeignService#getPaymentById] date: Sun, 19 Jun 2022 07:25:02 GMT
2022-06-19 15:25:02.575 DEBUG 34144 --- [p-nio-80-exec-2] c.y.s.service.PaymentFeignService        : [PaymentFeignService#getPaymentById] keep-alive: timeout=60
2022-06-19 15:25:02.576 DEBUG 34144 --- [p-nio-80-exec-2] c.y.s.service.PaymentFeignService        : [PaymentFeignService#getPaymentById] transfer-encoding: chunked
2022-06-19 15:25:02.576 DEBUG 34144 --- [p-nio-80-exec-2] c.y
        标签: 贴片二极管丝印f17

锐单商城拥有海量元器件数据手册IC替代型号,打造 电子元器件IC百科大全!

锐单商城 - 一站式电子元器件采购平台