【SpringCloud】OpenFeign服务接口调用

提示:本文在已搭建好Eureka集群和服务提供者集群的条件下测试,OpenFeign用于服务消费端,至于怎样搭建好Eureka集群和服务提供者集群参考博客【SpringCloud】服务注册中心Eureka


什么是Feign

  1. 官网解释:https://cloud.spring.io/spring-cloud-static/Hoxton.SR1/reference/htmlsingle/#spring-cloud-openfeign

Feign is a declarative web service client. It makes writing web service clients easier. To use Feign create an interface and annotate it. It has pluggable annotation support including Feign annotations and JAX-RS annotations. Feign also supports pluggable encoders and decoders. Spring Cloud adds support for Spring MVC annotations and for using the same HttpMessageConverters used by default in Spring Web. Spring Cloud integrates Ribbon and Eureka, as well as Spring Cloud LoadBalancer to provide a load-balanced http client when using Feign.

Feign是一个声明式web服务客户机。它使编写web服务客户机变得更容易。 它的使用方法是定义一个服务接口然后在上面添加注解。 它具有可插入的注释支持,包括伪注释和JAX-RS注释。Feign还支持可插拔的编码器和解码器。springcloud增加了对springmvc注释的支持,并支持使用springweb中默认使用的httpmessageconverter。springcloud集成了Ribbon和Eureka,以及springcloudloadbalancer,以便在使用Feign时提供一个负载平衡的http客户端。

Feign能干什么

  1. Feign旨在使编写Java Http客户端变得更容易。
  2. 前面在使用Ribbon+RestTemplate时,利用RestTemplate对http请求的封装处理,形成了一套模版化的调用方法。但是在实际开发中,由于对服务依赖的调用可能不止一处,往往一个接口会被多处调用,所以通常都会针对每个微服务自行封装一些客户端类来包装这些依赖服务的调用。所以,Feign在此基础上做了进一步封装,由他来帮助我们定义和实现依赖服务接口的定义。在Feign的实现下,我们只需创建一个接口并使用注解的方式来配置它(以前是Dao接口上面标注Mapper注解,现在是一个微服务接口上面标注一个Feign注解即可),即可完成对服务提供方的接口绑定,简化了使用Spring cloud Ribbon时,自动封装服务调用客户端的开发量。
  3. Feign集成了Ribbon:利用Ribbon维护了Payment的服务列表信息,并且通过轮询实现了客户端的负载均衡。而与Ribbon不同的是,通过feign只需要定义服务绑定接口且以声明式的方法,优雅而简单的实现了服务调用。

Feign和OpenFeign两者区别

FeignOpenFeign
Feign是Spring Cloud组件中的一个轻量级RESTful的HTTP服务客户端Feign内置了Ribbon,用来做客户端负载均衡,去调用服务注册中心的服务。Feign的使用方式是:使用Feign的注解定义接口,调用这个接口,就可以调用服务注册中心的服务OpenFeign是Spring Cloud在Feign的基础上支持了SpringMVC的注解,如@RequesMapping等等。OpenFeign的@FeignClient可以解析SpringMVC的@RequestMapping注解下的接口,并通过动态代理的方式产生实现类,实现类中做负载均衡并调用其他服务。

Feign:

<dependency>
  <groupId>org.springframework.cloud</groupId>
  <artifactId>spring-cloud-starter-feign</artifactId>
</dependency>

OpenFeign :

<dependency>
  <groupId>org.springframework.cloud</groupId>
  <artifactId>spring-cloud-starter-openfeign</artifactId>
</dependency>

OpenFeign的使用

  1. 在原来的SpringCloud项目中新建一个Module为普通的Maven项目,名cloud-consumer-feign-order80【注意:我们OpenFeign是在消费端使用
  2. pom.xml
<?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>SpringcloudTest</artifactId>
        <groupId>org.example</groupId>
        <version>1.0-SNAPSHOT</version>
    </parent>
    <modelVersion>4.0.0</modelVersion>

    <artifactId>cloud-consumer-feign-order80</artifactId>


    <!--openfeign-->
    <dependencies>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-openfeign</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
        </dependency>
        <dependency>
            <groupId>org.example</groupId>
            <artifactId>cloud-api-commons</artifactId>
            <version>1.0-SNAPSHOT</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.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>
  1. 配置文件application.yml
server:
  port: 80
eureka:
  client:
    register-with-eureka: false
    service-url:
      defaultZone: http://eureka7001.com:7001/eureka, http://eureka7002.com:7002/eureka
 

  1. 主启动类:新注解@EnableFeignClients
@SpringBootApplication
@EnableFeignClients
public class OrderFeignMain80 {
    public static void main(String[] args) {
        SpringApplication.run(OrderFeignMain80.class,args);
    }

}
  1. 业务类:业务逻辑接口+@FeignClient配置调用提供者服务
    (1)新建PaymentFeignService接口并新增注解@FeignClient
@Service
@FeignClient(value = "CLOUD-PROVIDER-PAYMENT")  //value为服务提供者名
public interface PaymentFeignService {

    //下面的方法来自 服务提供者的controller层的Controller类

  @GetMapping(value = "/payment/{id}")
    public CommonResult getPaymentById(@PathVariable("id") Long id);
}

(2)控制层Controller

@RestController
@Slf4j
public class OrderFeignController {

    @Autowired
    private PaymentFeignService paymentFeignService;

    @GetMapping(value = "/consumer/payment/get/{id}")
    public CommonResult<Payment> getPaymentById(@PathVariable("id") Long id){
        return paymentFeignService.getPaymentById(id);
    }
}
  1. 测试:开启7001和7002Eureka集群和8001和8002服务提供者集群,然后开启前面搭建的80消费者端
    访问:http://localhost/consumer/payment/get/1在这里插入图片描述

  2. 小结:
    (1)之前用的是Ribbon+RestTemplate实现对提供者的调用,现在使用的是OpenFeign代替,其实OpenFeign内部集成Ribbon,所以负载均衡的效果和前者一致。
    (2)OpenFeign中写的接口Service类,可以直接从服务提供者copy,去掉方法体即可。

OpenFeign超时控制

  1. 首先你需要知道OpenFeign默认等待一秒钟,超过后报错。
  2. 测试:

(1)在8001和8002提供者中的Controller类添加一个请求:等待3s

@GetMapping(value = "/payment/feign/timeout")
public String paymentFeignTimeout(){
    try { TimeUnit.SECONDS.sleep(3); }catch (Exception e) {e.printStackTrace();}
    return serverPort;
}

(2)服务消费方80添加超时方法PaymentFeignService

@Service
@FeignClient(value = "CLOUD-PROVIDER-PAYMENT")  //value为服务提供者名
public interface PaymentFeignService {

    //下面的方法来自 服务提供者的controller层的Controller类

  @GetMapping(value = "/payment/{id}")
  public CommonResult getPaymentById(@PathVariable("id") Long id);

  @GetMapping(value = "/payment/feign/timeout")
  public String paymentFeignTimeout();
}

(3)服务消费方80添加超时方法OrderFeignController

@GetMapping(value = "/consumer/payment/feign/timeout")
public String paymentFeignTimeout(){
   return paymentFeignService.paymentFeignTimeout();
}

(4)重启上面的服务,进行测试:先访问8001和8002的超时方法,确保没错,之后访问80的
http://localhost:8001/payment/feign/timeout
在这里插入图片描述
http://localhost:8002/payment/feign/timeout
在这里插入图片描述
http://localhost/consumer/payment/feign/timeout在这里插入图片描述

  1. 怎样修改默认的一秒钟:在配置文件application.yml中添加:改成5s
#设置feign客户端超时时间(OpenFeign默认支持ribbon)
ribbon:
  # 指的是建立连接后从服务器读取到可用资源所用的时间   5s
  ReadTimeout:  5000
  # 指的是建立连接所用的时间,适用于网络状况正常的情况下,两端连接所用的时间   5s
  ConnectTimeout: 5000
  1. 重启80消费端进行再次测试http://localhost/consumer/payment/feign/timeout,未报超时错误在这里插入图片描述

OpenFeign日志打印功能

Feign提供了日志打印功能,我们可以通过配置来调整日志级别,从而了解Feign中Http请求的细节,其实就是对Feign接口的调用情况进行监控和输出

  1. 日志级别:
日志级别解释
NONE默认的,不显示任何日志
BASIC仅记录请求方法、URL、 响应状态码及执行时间
HEADERS除了BASIC 中定义的信息之外,还有请求和响应的头信息
FULL除了HEADERS中定义的信息之外,还有请求和响应的正文及元数据
  1. 不使用默认的日志级别,怎样使用其他的日志级别:
    (1)配置日志bean,在com.gaolang.config下创建FeignConfig 类
@Configuration
public class FeignConfig {

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

(2)YML文件里需要开启日志的Feign客户端

logging:
  level:
    # Service类路径  
    com.gaolang.service.PaymentFeignService: debug

(3)重启80服务:访问:http://localhost/consumer/payment/get/1,看控制台:在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值