1. Feign 介绍

RestTemplate方式调用存在的问题:
image.png

  1. 代码可读性差,编程体验不统一
  2. 参数复杂 URL 难以维护

Feign 介绍:

Feign 是一个声明式的 HTTP 客户端,官方地址: https://github.com/OpenFeign/feign 优雅的实现http请求。

2. 定义使用 Feign

  1. 引入依赖 :::info
    <_dependency>
    <_groupId_>org.springframework.cloud
    <_artifactId_>spring-cloud-starter-openfeign
    _ :::

  2. 在启动类添加注解 @EnableFeignClients

    1. @MapperScan("cn.itcast.order.mapper")
    2. @SpringBootApplication
    3. @EnableFeignClients
    4. public class OrderApplication {
    5. public static void main(String[] args) {
    6. SpringApplication.run(OrderApplication.class, args);
    7. }
    8. }
  3. 编写 Feign 接口

    1. @FeignClient("userserivce")
    2. public interface UserClient {
    3. @GetMapping("/user/{id}")
    4. User findById(@PathVariable("id") Long id);
    5. }

    主要是基于 SpringMVC 的注解来声明远程调用的信息,比如:

  • 服务名称:userservice
  • 请求方式:GET
  • 请求路径:/user/{id}
  • 请求参数:Long id
  • 返回值类型:User
  1. 调用 ```java @Autowired private UserClient userClient;

// 利用Feign远程调用 User user = userClient.findById(userId);

  1. <a name="Ks3QU"></a>
  2. # 3. 自定义配置
  3. <a name="Ywzlz"></a>
  4. ## 3.1 修改日志级别
  5. **Feign 日志级别**:
  6. :::info
  7. NONE:不记录任何日志信息,这是默认值<br />BASIC:仅记录请求的方法,URL以及响应状态码和执行时间<br />HEADERS:在BASIC的基础上,额外记录了请求和响应的头信息<br />FULL:记录所有请求和响应的明细,包括头信息、请求体、元数据
  8. :::
  9. 在创建 FeignClient 的时候,就创建了logger, 默认logger的名称是创建 FeignClient 的服务接口类的全路径,通俗的来讲就是加了@FeignClient接口类的全路径。<br />**将项目日志级别设置为debug,因为 Feign 的 logger.level 只对 debug 做出响应:**
  10. ```yaml
  11. logging:
  12. level:
  13. cn.itcast.order.clients.UserClient: DEBUG
  14. #cn.itcast: DEBUG

配置日志级别:

  1. 方式一:配置文件

    feign:
    client:
     config:
       default:  # default表示全局配置,如果是写服务名则只针对某个服务
         loggerLevel: FULL # 日志级别
    
  2. 方式二:Java 代码,需要先声明一个Bean ```java import feign.Logger; import org.springframework.context.annotation.Bean;

public class FeignClientConfiguration {

@Bean
public Logger.Level logLevel(){
    return Logger.Level.BASIC;
}

}

① 如果是全局配置,则把它放到 `@EnableFeignClients`注解中
:::info
@EnableFeignClients_(_defaultConfiguration = FeignClientConfiguration.class_)_
:::
②如果是局部配置,则把它放到 `@FeignClient` 注解中
:::info
@FeignClient_(_value = "userservice", configuration = FeignClientConfiguration.class_)_
:::
<a name="sH2my"></a>
# 4. Feign性能优化
 Feign底层的客户端实现:

- URLConnection:默认实现,不支持连接池
- Apache HttpClient:支持连接池
- OKHttp:支持连接池

性能优化主要内容:

1. 日志级别:最好使用 BASIC 和 NONE;
1. 使用连接池代替默认的 URLConnection;
<a name="P5gXh"></a>
## 4.1 Feign 配置 HttpClient

1. 引入依赖:
:::info
<!-- httpClient 依赖 --><br />_<_dependency_><br />    <_groupId_>_io.github.openfeign_</_groupId_><br />    <_artifactId_>_feign-httpclient_</_artifactId_><br /></_dependency_>_
:::

2. 配置连接池
```yaml
#Feign配置
feign:
  client:
    config:
      default:  # default表示全局配置,如果是服务名则只针对某个服务
        loggerLevel: BASIC # 日志级别
  httpclient:
    enabled: true # 开启 Feign对 HttpClient的支持
    max-connections: 200  # 最大连接数
    max-connections-per-route: 50 # 每个路径的最大连接数

5. Feign最佳实践

方式一(继承):给消费者的 FeignClient 的提供者的 Controller 定义统一的父接口作为标准。
image.png

方式二(抽取):将 FeignClient 抽取为独立模块,并且把接口有关的 POJO、默认的 Feign 配置都放在该模块中,提供给所有消费者使用。
image.png