002- feign 学习笔记

feign 学习笔记

注册中心,生产者消费者创建方式参考 eureka学习记录 - 神经哇 - 博客园 (cnblogs.com)

一、创建注册中心

新建名为 feign-eureka

参看上面链接: eureka学习记录 - 神经哇 - 博客园 (cnblogs.com)

二、创建生产者

新建 名为feign-producer

参看链接: eureka学习记录 - 神经哇 - 博客园 (cnblogs.com)

2.1 新建了一个API模块feign-api,用于共享API 跟实体

API :

@FeignClient(name = "feign-producer")
public interface SendMsgToProducer {

    /**
     * 无参
     * @return
     */
    @GetMapping("/getServerNoParam")
    public String getServerNoParam();
    /**
     * 一参数
     * @return
     */
    @GetMapping("/getServer")
    public String getServer(@RequestParam("s") String s);
}

三、消费者

新建名为 feign-consumer

3.1 整合feign

3.1.1 核心依赖

在eureka 的基础上增加feign

        <!--feign 依赖-->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-openfeign</artifactId>
        </dependency>

3.1.2 配置 不配置,暂时使用默认配置

3.1.3 启动类

启动类增加@EnableFeignClients,因为我们将api抽离出来了,所以要加上扫描包basePackages = "com.zhoust.feign.api"

@SpringBootApplication
@EnableDiscoveryClient
@EnableFeignClients(basePackages = "com.zhoust.feign.api")
public class FeignConsumerApplication {

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

}

3.2 feign调用

3.2.1 创建API

引入feign-api模块(API 模块中创建了SendMsgToProducer,直接使用)

3.2.2 创建controller

@RestController
public class TestController {

    private final SendMsgToProducer sendMsgToProducer;

    public TestController(SendMsgToProducer sendMsgToProducer) {
        this.sendMsgToProducer = sendMsgToProducer;
    }


    @GetMapping("/getServer")
    public String getServer(){
        return sendMsgToProducer.getServer("你好");

    }
    @GetMapping("/getServerNoParam")
    public String getServerNoParam(){
        return sendMsgToProducer.getServerNoParam();

    }
}

feign-api 中 SendMsgToProducer 引入了 @FeignClient(name = "feign-producer")注解来指名微服务,接口通过controller注解来指明调用生产者哪个接口。

  • 启动 调用接口 测试通过

3.2.3 feign 对多参数的支持

  • 使用 @RequestParam("s")
  • 使用 Map对象来构建
  • 通过对象
3.2.3.1 添加 user对象

api 中添加 User 对象

@Data
public class User {
    private String userName;
    private int age;
}
3.2.3.2 条件接口

SendMsgToProducer

@FeignClient(name = "feign-producer")
public interface SendMsgToProducer {

    /**
     * 无参
     * @return
     */
    @GetMapping("/getServerNoParam")
    public String getServerNoParam();
    /**
     * 一参数
     * @return
     */
    @GetMapping("/getServer")
    public String getServer(@RequestParam("s") String s);

    /**
     * 多参数
     * @return
     */
    @GetMapping("/getServerParams")
    public String getServerParams(@RequestParam("userName") String userName,@RequestParam("age") int age);

    /**
     * 以map形式传递
     * @return
     */
    @GetMapping("/getServerByMap")
    public String getServerByMap(@RequestParam Map<String,Object> map);

    /**
     * 以对象形式传递
     * @return
     */
    @PostMapping("/getServerByObject")
    public String getServerByObject(@RequestBody User user);

}

producer --> TestController

@RestController
@Slf4j
public class TestController {

    @Value("${spring.application.name}")
    private String applicationName;
    @Value("${server.port}")
    private String servicePort;

    @GetMapping("/getServer")
    public String getServer(@RequestParam("s") String s){
        log.info("我是:{}对外提供服务端口:{},我接到消息:{}",applicationName,servicePort,s);
        return "我是:"+applicationName+"对外提供服务端口:"+servicePort+",我接到消息:"+s;
    }

    @GetMapping("/getServerNoParam")
    public String getServerNoParam(){
        log.info("我是:{}对外提供服务端口:{}",applicationName,servicePort);
        return "我是:"+applicationName+"对外提供服务端口:"+servicePort+",没有参数";
    }


    /**
     * 多参数
     * @return
     */
    @GetMapping("/getServerParams")
    public String getServerParams(@RequestParam("userName") String userName,@RequestParam("age") int age){
        return "我是:"+applicationName+"对外提供服务端口:"+servicePort+",多个参数userName:"+userName+"age:"+age;
    }

    /**
     * 以map形式传递
     * @return
     */
    @GetMapping("/getServerByMap")
    public String getServerByMap(@RequestParam Map<String,Object> map){

        String userName = String.valueOf(map.get("userName"));
        String age = String.valueOf(map.get("age"));
        return "我是:"+applicationName+"对外提供服务端口:"+servicePort+",多个参数userName:"+userName+"age:"+age;

    }

    /**
     * 以对象形式传递
     * @return
     */
    @PostMapping("/getServerByObject")
    public String getServerByObject(@RequestBody User user){
        return "我是:"+applicationName+"对外提供服务端口:"+servicePort+",多个参数 user:"+user.toString();

    }

}

consumer --> TestController

package com.zhoust.feign.consumer.controller;

import com.zhoust.feign.api.api.domain.User;
import com.zhoust.feign.api.api.service.SendMsgToProducer;
import org.springframework.web.bind.annotation.*;

import java.util.HashMap;

/**
 * @author zhoust
 */
@RestController
public class TestController {

    private final SendMsgToProducer sendMsgToProducer;

    public TestController(SendMsgToProducer sendMsgToProducer) {
        this.sendMsgToProducer = sendMsgToProducer;
    }
    @GetMapping("/getServer")
    public String getServer(){
        return sendMsgToProducer.getServer("你好");

    }
    @GetMapping("/getServerNoParam")
    public String getServerNoParam(){
        return sendMsgToProducer.getServerNoParam();
    }
    @GetMapping("/getServerNoParams")
    public String getServerParams(){
        return sendMsgToProducer.getServerParams("userName", 108);

    }
    /**
     * 以map形式传递
     * @return
     */
    @GetMapping("/getServerByMap")
    public String getServerByMap(){
        HashMap<String, Object> map = new HashMap<>();
        map.put("userName","张三");
        map.put("age",18);
        return sendMsgToProducer.getServerByMap(map);
    }

    /**
     * 以对象形式传递
     * @return
     */
    @PostMapping("/getServerByObject")
    public String getServerByObject(){
        User user = new User();
        user.setUserName("李四");
        user.setAge(28);

        return sendMsgToProducer.getServerByObject(user);
    }
}

这样consumer在调用producer时,直接接口名.方法。简化了我们的调用。

3.3 feign 对继承的支持

3.3.1 API中新建接口

TestExtendsFeign (注意接口使用的是 @RestController)

@RestControllerpublic interface TestExtendsFeign {    @PostMapping("/testExtends")    public String testExtends(@RequestBody User user);}

3.3.2 生产者

TestExtendsController 实现 API TestExtendsFeign

/** * 测试feign继承 */@RestControllerpublic class TestExtendsController implements TestExtendsFeign {    @Value("${spring.application.name}")    private String applicationName;    @Value("${server.port}")    private String servicePort;    @Override    public String testExtends(User user) {        return "我是:"+applicationName+"对外提供服务端口:"+servicePort+",多个参数 user:"+user.toString();    }}

3.3.3 消费者

继承TestExtendsFeign

@FeignClient("FEIGN-PRODUCER")public interface TestExtedsConsumer extends TestExtendsFeign {}

测试controller

@RestControllerpublic class TestExtends  {    @Autowired    private TestExtedsConsumer testExtedsConsumer;    @PostMapping("/testExtendsConsumer")    public String getServerByObject(){        User user = new User();        user.setUserName("李四");        user.setAge(28);        return testExtedsConsumer.testExtends(user);    }}

注意feign要扫描到 TestExtedsConsumer

测试通过

注意 不建议使用

spring 官方不建议使用,因为这种做法破坏了低耦合,是生产者消费者的联系紧密,并且feign本身不使用springmvc 的工作机制,所以方法参数映射不被继承。

3.4 feign 对压缩的支持

feign:  compression:    request:      enabled: true      mime-types: text/xml,application/xml,application/json    response:      enabled: true

3.5 feign 日志打印

posted @ 2021-11-01 19:56  神经哇  阅读(85)  评论(0)    收藏  举报