一、feign使用
1、集成方法
1.1、pom
consumer添加依赖
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-openfeign</artifactId>
<version>2.2.6.RELEASE</version>
</dependency>
1.2、启动类
consumer启动类加上@EnableFeignClients注解,即开启feign;
1.3、consumer调用provider:
编写一个中间service,consumer调用service,service调用provider。这个service类头加@FeignClient注解:
@FeignClient(value = "my-service",path = "/myProvider")
(1)value:provider配置文件中的spring.application.name,
注意这里的value值不分大小写,my-service和MY-SERVICE都可以。
(2)path:如果provider在配置文件里面配置了server.context-path,FeignClient就需要指明path。
2、调用方法
上面提到的service,关于service调用provider传参的问题:
2.1、无参调用
post、get请求都可以
2.2、非对象参数
如Integer、String等,适用于get请求。
service方法上需要加@RequestParam注解,且括号中一定要有值(参数的别名)和被调用方provider的参数名保持一致,被调用方可加@RequestParam也可不加;
2.3、对象参数
javaBean,map,list等,只适用于post请求。
被调用方provider加@RequestBody注解,调用方service的方法可加可不加;
2.4、header头部参数:
provider和service方法上都使用@RequestHeader注解,且value指明参数别名。
二、集成demo
1、初版
1.1、父pom
<?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 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.demo.nacos</groupId>
<artifactId>nacos-demo</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>nacos-demo</name>
<packaging>pom</packaging>
<!-- springBoot -->
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.0.4.RELEASE</version>
</parent>
<!-- 模块说明:这里声明多个子模块 -->
<modules>
<module>provider</module>
<module>consumer</module>
<module>nacos-common</module>
</modules>
<!-- 版本说明:这里统一管理依赖的版本号 -->
<dependencyManagement>
<dependencies>
<!-- SpringCloud -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
<version>Finchley.RELEASE</version>
</dependency>
<!-- SpringCloud Alibaba -->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
<version>2.1.0.RELEASE</version>
</dependency>
<!--服务注册-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
<version>0.2.2.RELEASE</version>
</dependency>
<!-- nacos 注册中心客户端 -->
<!-- <dependency>-->
<!-- <groupId>com.alibaba.cloud</groupId>-->
<!-- <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>-->
<!-- <version>2.1.0.RELEASE</version>-->
<!-- </dependency>-->
<!--集中配置-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
<version>2.1.0.RELEASE</version>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter</artifactId>
</dependency>
<!--nocas必须在web环境下-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
</project>
1.2、provider:
(1)pom:
<parent>
<artifactId>nacos-demo</artifactId>
<groupId>com.demo.nacos</groupId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<dependencies>
<dependency>
<groupId>com.demo.nacos</groupId>
<artifactId>nacos-common</artifactId>
<version>0.0.1-SNAPSHOT</version>
</dependency>
<!-- SpringCloud -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
</dependency>
<!-- SpringCloud Alibaba -->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
</dependency>
<!--服务注册-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<!--集中配置-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
</dependency>
</dependencies>
(2)bootstrap:
spring:
application:
name: my-service
cloud:
compatibility-verifier:
enabled: false
nacos:
#服务注册
discovery:
server-addr: xxx.xx.xxx:8848
#配置中心
config:
server-addr: xxx.xx.xxx:8848
group: wtyy
profiles:
active: prod
server:
port: 1111
servlet:
context-path: /myProvider
(3)启动类:
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
@SpringBootApplication
@EnableDiscoveryClient
public class ProviderApplication {
public static void main(String[] args) {
SpringApplication.run(ProviderApplication.class, args);
}
}
(4)controller接口
import com.demo.nacos.common.dto.UserDTO;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.cloud.context.config.annotation.RefreshScope;
import org.springframework.web.bind.annotation.*;
import javax.servlet.http.HttpServletRequest;
@RestController
@RequestMapping("/configTest")
//刷新配置
@RefreshScope
public class ProviderTestController {
@Value("${user.text}")
private String userText;
private static Logger logger = LoggerFactory.getLogger(ProviderTestController.class);
/**
* 1、无参 无返回
* @param request
* @return
* @throws InterruptedException
*/
@GetMapping("/hanNoParam")
public void getUserText(HttpServletRequest request) throws InterruptedException {
logger.info("调用无参接口");
}
/**
* 2、有参
* @return
* @throws InterruptedException
*/
@GetMapping("/hanParams")
public String hanParams(String userName) throws InterruptedException {
logger.info("调用有参接口");
return userName+":"+userText;
}
/**
* 3、有参,对象参数
* @return
* @throws InterruptedException
*/
@PostMapping("/hanObjParams")
public UserDTO hanObjParams(@RequestBody UserDTO userDTO) throws InterruptedException {
logger.info("调用对象参数接口");
return userDTO;
}
/**
* 4、参数加header
* @return
* @throws InterruptedException
*/
@PostMapping("/hanParamsAndHeader")
public String hanParamsAndHeader(@RequestBody UserDTO userDTO,@RequestHeader("token") String token) throws InterruptedException {
logger.info("调用参数和header接口");
return userDTO.getUserName()+"的token:"+token;
}
}
1.3、consumer:
(1)pom:
<parent>
<artifactId>nacos-demo</artifactId>
<groupId>com.demo.nacos</groupId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<dependencies>
<dependency>
<groupId>com.demo.nacos</groupId>
<artifactId>nacos-common</artifactId>
<version>0.0.1-SNAPSHOT</version>
</dependency>
<!-- SpringCloud -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-dependencies</artifactId>
</dependency>
<!-- SpringCloud Alibaba -->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-dependencies</artifactId>
</dependency>
<!--服务注册-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<!--集中配置-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-openfeign</artifactId>
<version>2.2.6.RELEASE</version>
</dependency>
</dependencies>
(2) bootstrap:
spring:
application:
name: my-consumer
cloud:
compatibility-verifier:
enabled: false
nacos:
#服务注册
discovery:
server-addr: xxx.xx.xxx:8848
#配置中心
config:
server-addr: xxx.xx.xxx:8848
group: wtyy
server:
port: 2222
servlet:
context-path: /myConsumer
(3) 启动类:
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cloud.client.discovery.EnableDiscoveryClient;
import org.springframework.cloud.openfeign.EnableFeignClients;
@SpringBootApplication
@EnableDiscoveryClient
@EnableFeignClients
public class ConsumerApplication {
public static void main(String[] args) {
SpringApplication.run(ConsumerApplication.class, args);
}
}
(4) service:重点
import com.demo.nacos.common.dto.UserDTO;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestHeader;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
@FeignClient(value = "my-service",path = "/myProvider")
public interface NacosConfigTestService {
@RequestMapping("/configTest/hanNoParam")
void hanNoParam();
@RequestMapping("/configTest/hanParams")
String hanParams(@RequestParam("userName")String userName);
@RequestMapping("/configTest/hanObjParams")
UserDTO hanObjParams(@RequestBody UserDTO userDTO);
@RequestMapping("/configTest/hanParamsAndHeader")
String hanParamsAndHeader(@RequestBody UserDTO userDTO,@RequestHeader("token") String token);
}
(5) controler:
import com.demo.nacos.common.dto.UserDTO;
import com.demo.nacos.consumer.service.NacosConfigTestService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import javax.servlet.http.HttpServletRequest;
@RestController
@RequestMapping("/consumerTest")
public class ConsumerTestController {
@Autowired
private NacosConfigTestService nacosConfigTestService;
@GetMapping("/hanNoParam")
public void getTemp(HttpServletRequest request) throws InterruptedException {
nacosConfigTestService.hanNoParam();
}
@GetMapping("/hanParams")
public String hanParams(String userName) throws InterruptedException {
return nacosConfigTestService.hanParams(userName);
}
@PostMapping("/hanObjParams")
public UserDTO hanObjParams(@RequestBody UserDTO userDTO) throws InterruptedException {
return nacosConfigTestService.hanObjParams(userDTO);
}
@PostMapping("/hanParamsAndHeader")
public String hanParamsAndHeader(@RequestBody UserDTO userDTO,HttpServletRequest request) throws InterruptedException {
String token = request.getHeader("token");
return nacosConfigTestService.hanParamsAndHeader(userDTO,token);
}
}
1.4、测试
分别启动provider、consumer,可以看到都注册到nacos上了:
(1)非对象参数
(2)对象参数
(3)对象参数&header
2、feign的继承特性
上面的代码有很多重复的地方,下面利用feign的继承特性进行抽取。