一、使用feign实现远程方法声明调用

未命名图片.png

  • provider:提供服务
    • 具体方法 不要实现common的接口,但是方法的签命要和接口一致
  • common:声明接口
    • UserRemoteService remote表示远程的
    • 接口上面有一个 @FeignClient(“微服务名”) 注解,value里是provider微服务的名字
  • consumer:消费服务(远程调用接口)

    • 直接装配 @AutoWired common工程的 UserRemoteService 即可
    • 在主启动类上添加注解 @EnableFeignClients

      二、操作

      1. 在common工程中引入依赖

  • 关于依赖的传递性,在common中导入了 consumer中就有了[如果consumer中不能使用的话,需要将consumer中也导入 openfeign依赖]

  • common 的包名要和 consumer的包名保持一致

    1. <dependency>
    2. <groupId>org.springframework.cloud</groupId>
    3. <artifactId>spring-cloud-starter-openfeign</artifactId>
    4. </dependency>

    2. common工程中创建服务接口

  • 包名:com.yixuexi.api

  • 此时 provider-service 的微服务 有一个和UserRemoteService中getQQ 同签名的方法
    /**
    * @date: 2021/3/2   22:10
    * @author: 易学习
    * common 工程下的service接口
    * @FeignClient 注解表示当前接口和一个provider对应,注解中value属性指定要调用的provider的微服务名称
    */
    @FeignClient("provider-service")
    public interface UserRemoteService {
      /**
       * 远程调用的接口方法:
       *      1.要求@RequestMapping注解映射的地址一致
       *      2.要求方法声明一致
       *      3.用来获取请求参数
       *          : @RequestParam  @PathVariable @RequestBody @RequestParam  不能省略,两边一致
       * @return
       */
      @RequestMapping("/provider/get/QQId")
      public String getQQ();
    }
    

    @FeignClient(“提供者的微服务名”) // 当前接口和一个provider对应@fe(u1967832)

3. 新建 feign-consumer工程

  • 【因为改动较大,所以新建一个 maven quickstart创建】
  • 项目中添加了feign 会自动导入 ribbon【可写可不写】
  • 关于依赖的传递性,在common中导入了 consumer中就有了 ```xml org.springframework.boot spring-boot-starter-web org.springframework.cloud spring-cloud-starter-netflix-eureka-client org.springframework.cloud spring-cloud-starter-netflix-ribbon com.yixuexi pro02_spring_cloud_common 1.0-SNAPSHOT
<a name="nqWgf"></a>
## 4. **feign-consumer的application.yaml配置文件**
```yaml
server:
  port: 7000

spring:
  application:
    name: consumer-service

eureka:
  client:
    service-url:
      defaultZone: http://localhost:5000/eureka/

5. feign-consumer的springboot主启动类

/**
 * @date: 2021/3/2   22:48
 * @author: 易学习
 * @EnableFeignClients: 表示consumer启动声明时远程调用
 */
@EnableFeignClients
@SpringBootApplication
public class ApplicationFeignConsumer {
    public static void main(String[] args) {
        SpringApplication.run(ApplicationFeignConsumer.class);
    }
}

@EnableFeignClients // q表明consumer启动声明时远程调用

6. feign-consumer工程的controller方法

/**
 * @date: 2021/3/2   23:16
 * @author: 易学习
 */
@RestController
public class UserFeignController {

    /**
     * 自动注入 远程的 userRemoteService
     */
    @Autowired
    private UserRemoteService userRemoteService;

    @RequestMapping("/remote/user/qq")
    public String getQQ(){
        return userRemoteService.getQQ();
    }
}

三、Feign调用时传参

1. 简单类型

【common 和 provider 都不要忘记@RequestParam注解】

1) common 工程里的定义provider接口

@GetMapping("/provider/search/user/by/name")
public User getUserByName(@RequestParam("keyword") String keyword);

2) provider 工程的controller

【和common接口 方法签命一致】
@GetMapping("/provider/search/user/by/name")
public User getUserByName(@RequestParam("keyword") String keyword) {
    List<User> userList = new ArrayList<>();
    userList.add(new User(1,"aaa","男"));
    userList.add(new User(2,"bbb","男"));
    userList.add(new User(3,"ccc","男"));
    return userList.get(0);
}

2. 复杂类型

【common 和 provider 都不要忘记@RequestBody】

1) common 工程里的定义provider接口

@RequestMapping("/provider/save/user")
public String saveUser(@RequestBody User user);

2) provider工程里的定义同样签命的方法

@RequestMapping("/provider/save/user")
public String SaveUser(@RequestBody User user){
    return "保存成功";
}

注意:@GetMapping 和@RequestBody 不能一起使用!