一. 什么是Feign
Feign是Netflix公司开源的轻量级Rest客户端,SpringCloud对Feign进行了封装,Feign默认集成了Ribbon实现了客户端负载均衡调用。使用Feign只需要定义一个接口,并使用注解的方式配置它(在接口上添加注解即可)。
微服务间的调用有两种方式:
1. 通过微服务名称,获得服务的调用地址---Ribbon
2. 通过接口 + 注解,获得服务的调用---Feign
类似于在Mapper接口上使用@Mapper注解进行标识,而使用Feign只要在接口上标注@Feign注解。
二. Feign实例
2.1 创建Feign模块(只需在之前的消费者模块上稍作修改)
2.2 pom.xml的配置(添加feign的配置)
<!--feign 依赖-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-openfeign</artifactId>
</dependency>
2.3新建ProductClientService接口
在代码中调用了 MICROSERVICE-PRODUCT 服务的 /product/list 、/product/get/{id}、/product/add 接 口,代码如下:
package com.dsx.service;
import java.util.List;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import com.dsx.domain.Product;
//指定调用的服务 MICROSERVICE-PRODUCT
@FeignClient(value="MICROSERVICE-PRODUCT")
public interface ProductClientService {
@RequestMapping(value = "/product/get/{id}",method = RequestMethod.GET)
Product get(Long id);
@RequestMapping(value = "/product/list",method = RequestMethod.GET)
List<Product> list();
@RequestMapping(value = "/product/add",method = RequestMethod.POST)
boolean add(Product product);
}
2.4 创建ConsumerControler_Feign
package com.dsx.controller;
import java.util.List;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.dsx.domain.Product;
import com.dsx.service.ProductClientService;
@RestController
public class ConsumerControler_Feign {
@Autowired
private ProductClientService service;
@RequestMapping(value = "/consumer/product/add")
public boolean add(Product product) {
return service.add(product);
}
@RequestMapping(value = "/consumer/product/get/{id}")
public Product get(@PathVariable("id") Long id) {
return service.get(id);
}
@RequestMapping(value = "/consumer/product/list")
public List<Product> list() {
return service.list();
}
}
2.5 修改启动类
package com.dsx;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.netflix.eureka.EnableEurekaClient;
import org.springframework.cloud.openfeign.EnableFeignClients;
//会扫描标记了指定包下@FeignClient注解的接口,并生成此接口的代理对象
@EnableFeignClients(basePackages= {"com.dsx"})
@EnableEurekaClient //标识Eureka客户端
@SpringBootApplication
public class ConsumerApp_Feign {
public static void main(String[] args) {
SpringApplication.run(ConsumerApp_Feign.class, args);
}
}
2.6 功能测试
启动2个Eureka集群
启动 2 个商品提供者 8001/8002
启动ConsumerApp_Feign
访问 http://localhost/consumer/product/list 发现一样具有负载均衡的效果。
三. Feign 的工作原理
Feign 通过接口的方法调用 Rest 服务(之前是 Ribbon+RestTemplate ), 请求发送给 Eureka 服务器 , 通过 Feign 直接找到服务接口 ,因为集成了 Ribbon 技术, Feign 自带负载均衡配置功能。
1 、 启动类添加 @EnableFeignClients 注解, Spring 会扫描标记了 @FeignClient 注解的接口,并生成此接口的代理
对象
2、 @FeignClient(" 服务名称 ") 即指定了 product 服务名称, Feign 会从 Eureka 注册中心获取 product 服务列表,
并通过负载均衡算法进行服务调用。
3 、在接口方法中使用注解 @RequestMapping(value = "/product/list",method = RequestMethod.GET) ,指定调
用的 url , Feign 会根据 url 进行远程调用。
四. feign注意事项
SpringCloud 对 Feign 进行了增强兼容了 SpringMVC 的注解 ,我们在使用 SpringMVC 的注解时需要注意:
1、@FeignClient接口方法有基本类型参数在参数必须加@PathVariable("XXX") 或 @RequestParam("XXX")
2、@FeignClient接口方法返回值为复杂对象时,此类型必须有无参构造方法
Feign是声明式的web service客户端,它让微服务之间的调用变得更简单了。