使用FeignClient比使用RestTemplate更加简洁。
依赖
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-openfeign</artifactId>
<version>2.1.1.RELEASE</version>
</dependency>
定义FeginClient接口
@FeignClient(name = "test", url = "http://xxx.xxx.xxx.xxx:xxxx")
public interface TestClient {
@PostMapping(path = "/test")
TestRes test(TestReq req);
}
示例定义了一个post请求,@FeignClient
里面定义的url是要请求的接口的服务地址和端口号,将出入参封装在类对象里,与平时写的Controller层接口一样,简洁实用。
其他示例
AuthClient.java
@FeignClient(name = "auth", url = "http://xxx.xxx.xxx.xxx:xxxx", configuration = FeignConfig.class)
public interface AuthClient {
@GetMapping(path = "/authentication-token")
TokenResDTO getToken(@RequestHeader("Authorization") String authorization);
@GetMapping(path = "/refresh-token")
TokenResDTO refreshToken(@RequestParam("token") String token);
}
FeignConfig.java
@Slf4j
public class FeignConfig extends FeignClientProperties.FeignClientConfiguration {
@Bean
public RequestInterceptor requestInterceptor() {
return requestTemplate -> {
log.info("url: {}", requestTemplate.request().url());
log.info("params: {}", requestTemplate.requestBody().asString());
};
}
}
FeignConfig类定义了一个Bean,这个Bean将请求的url和参数打印到日志中,当@FeignClient
中指定了使用FeignConfig,则该类定义的所有方法将适用FeignConfig定义的Bean方法。
上面示例中,当请求中需要传header内容时,通过@RequestHeader
指定参数名,调用该方法时通过参数传入就可以了。
特殊示例
当需要动态拼接字段在url后面的时候
FeignConfig.java
@Slf4j
public class FeignConfig extends FeignClientProperties.FeignClientConfiguration {
@Bean
public RequestInterceptor requestInterceptor() {
return requestTemplate -> {
// 从header参数中取key为Append-Url的值拼接在定义的url后面
Collection<String> url = requestTemplate.headers().get("Append-Url");
if (url != null && !url.isEmpty()) {
requestTemplate.uri(url.stream().findFirst().get(), true);
}
log.info("url: {}", requestTemplate.request().url());
log.info("params: {}", requestTemplate.requestBody().asString());
};
}
}
TestClient.java
@FeignClient(name = "test", url = "http://xxx.xxx.xxx.xxx:xxxx")
public interface TestClient {
@GetMapping(path = "/test")
TestRes test(@RequestHeader("Append-Url") String appendUrl);
}
调用FeignClient
可以在Controller层或Service层进行调用,例如:
@Resource
private AuthClient authClient;
@GetMapping("/test/refresh")
public String refreshToken(@RequestParam String token) {
TokenResDTO res = authClient.refreshToken(token);
if (res != null) {
return res.getData();
}
return null;
}