Feign真正正確的使用方法--供老專案呼叫
阿新 • • 發佈:2019-02-13
Feign是spring cloud中服務消費端的呼叫框架,通常與ribbon,hystrix等組合使用。
但是在某些專案中,由於遺留原因,整個系統並不是spring cloud專案,甚至不是spring專案,而使用者關注的重點僅僅是簡化http呼叫程式碼的編寫。
如果採用httpclient或者okhttp這樣相對較重的框架,對初學者來說編碼量與學習曲線都會是一個挑戰,而使用spring中RestTemplate,又沒有配置化的解決方案,由此想到是否可以脫離spring cloud,獨立使用Feign。
maven依賴
<dependency>
<groupId> com.netflix.feign</groupId>
<artifactId>feign-core</artifactId>
<version>8.18.0</version>
</dependency>
自定義介面
import feign.Param;
import feign.RequestLine;
public interface RemoteService {
@RequestLine("GET /users/list?name={name}")
String getOwner(@Param(value = "name" ) String name);
}
通過@RequestLine
指定HTTP協議及URL地址
配置類
RemoteService service = Feign.builder()
.options(new Options(1000, 3500))
.retryer(new Retryer.Default(5000, 5000, 3))
.target(RemoteService.class, "http://127.0.0.1:8085");
options方法指定連線超時時長及響應超時時長,retryer方法指定重試策略,target方法繫結介面與服務端地址。返回型別為繫結的介面型別。
呼叫
String result = service.getOwner("scott");
與呼叫本地方法相同的方式呼叫feign包裝的介面,直接獲取遠端服務提供的返回值。
附:服務生產者
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
@Controller
@RequestMapping(value="users")
public class UserController {
@RequestMapping(value="/list",method={RequestMethod.GET,RequestMethod.POST,RequestMethod.PUT})
@ResponseBody
public String list(@RequestParam String name) throws InterruptedException{
return name.toUpperCase();
}
}
更進一步(前面內容可以忽略 只看這裡往下的)
在專案中,服務消費端與生產端之間交換的資料往往是一或多個物件,feign同樣提供基於json的物件轉換工具,方便我們直接以物件形式互動。
業務介面
public interface RemoteService {
@Headers({"Content-Type: application/json","Accept: application/json"})
@RequestLine("POST /users/list")
User getOwner(User user);
}
加入@Headers註解,指定Content-Type為json
配置
RemoteService service = Feign.builder()
.encoder(new JacksonEncoder())
.decoder(new JacksonDecoder())
.options(new Options(1000, 3500))
.retryer(new Retryer.Default(5000, 5000, 3))
.target(RemoteService.class, "http://127.0.0.1:8085");
encoder指定物件編碼方式,decoder指定物件解碼方式。這裡用的是基於Jackson的編、解碼方式,需要在pom.xml中新增Jackson的依賴
<dependency>
<groupId>com.netflix.feign</groupId>
<artifactId>feign-jackson</artifactId>
<version>8.18.0</version>
</dependency>
呼叫
User result = service.getOwner(u);
附:服務生產者
@Controller
@RequestMapping(value="users")
public class UserController {
@RequestMapping(value="/list",method={RequestMethod.GET,RequestMethod.POST,RequestMethod.PUT})
@ResponseBody
public User list(@RequestBody User user) throws InterruptedException{
System.out.println(user.getUsername());
user.setId(100L);
user.setUsername(user.getUsername().toUpperCase());
return user;
}
}
唯一的變化就是使用了@RequestBody來接收json格式的資料。