1.引入依賴
Maven坐標
<!--feign 依賴-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-openfeign</artifactId>
<version>${feign.version}</version>
</dependency>
2. 定義FeignClient
/**
* @description: 基礎服務
*
* FeignClient注解:
* name/value屬性: 這兩個的作用是一樣的,指定的是調用服務的微服務名稱(獨立使用時,只需唯一) 可以使用環境變量或者jvm屬性定義url字段
* url: 定義遠程服務的domain
* fallbackFactory: 定義熔斷器(可以在熔斷器中定義熔斷處理,返回兜底的結果)
*
* @date: 2020/11/24 14:49
* @author: fdh
*/
//@FeignClient(name = "baseSapi", url = "${qs.sapi.base.url.prefix}", fallbackFactory = RemoteBaseFallBackFactory.class)
@FeignClient(name = "baseSapi", url = "http://localhost:9001", fallbackFactory = RemoteBaseFallBackFactory.class)
public interface RemoteBaseService {
/**
* 獲取考季知識點
*
* 接口地址: http:// xxxxx
*
* @param seasonId
* @return
*/
@RequestMapping(value = "/s1/v1/seasonKnowledgePoint/kpListBySeasonId", method = RequestMethod.GET)
SapiResult<List<KnowledgePointVo>> getKpListBySeasonId(@RequestParam("seasonId") Long seasonId);
}
3.定義熔斷器
/**
* @description: 遠程基礎熔斷工廠
* @date: 2020/11/25 13:48
* @author: fdh
*/
@Component
public class RemoteBaseFallBackFactory implements FallbackFactory<RemoteBaseService> {
@Override
public RemoteBaseService create(Throwable throwable) {
RemoteBaseFallBackServiceImpl remoteBaseFallBackService = new RemoteBaseFallBackServiceImpl();
remoteBaseFallBackService.setThrowable(throwable);
return remoteBaseFallBackService;
}
}
4.定義FeignClient熔斷實現
/**
* @description: RemoteBaseService熔斷處理
* @date: 2020/11/25 13:49
* @author: fdh
*/
public class RemoteBaseFallBackServiceImpl implements RemoteBaseService {
private static final Logger log = LoggerFactory.getLogger(RemoteBaseFallBackServiceImpl.class);
@Setter
private Throwable throwable;
private void printLog(String modules, Throwable throwable){
if( modules == null ){
modules = StringUtils.EMPTY;
}
log.info("{}異常:", modules, throwable);
}
@Override
public SapiResult<List<KnowledgePointVo>> getKpListBySeasonId(Long seasonId) {
printLog("知識點接口", throwable);
return SapiResultUtil.success(Collections.emptyList());
}
}
5. 掃描FeignClient
/**
* @description: 啟動類
* @date: 2020/11/25 13:52
* @author: fdh
*/
@SpringBootApplication
@EnableFeignClients(basePackages = "com.xxx.feign")
public class DaApplication extends SpringBootServletInitializer {
@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
return application.sources(DaApplication.class);
}
public static void main(String[] args) {
SpringApplication.run(DaApplication.class, args);
}
}
以上就可以實現Feign獨立使用,不依賴注冊中心,進行獨立遠程調用
補充:
1. 生產環境上往往需要記錄FeignClient遠程調用日志,我們可以定義日志輸出級別
/**
* @description: Feign日志
* @date: 2020/11/5 16:35
* @author: fdh
*/
@Configuration
public class FeignConfig {
@Bean
Logger.Level feignLoggerLevel() {
return Logger.Level.FULL;
}
}
推薦日志級別:
| 級別 | 打印內容 |
| NONE(默認值) | 不記錄任何日志 |
| BASIC(更適合生產環境) | 僅記錄請求方法、URL、響應狀態代碼以及執行時間 |
| HEADERS | 記錄BASIC級別的基礎上,記錄請求和響應的 header |
| FULL(更適合開發環境) | 記錄請求和響應的 header、body和元數據 |
2. 啟用熔斷並設置熔斷超時時間(默認1秒)
feign.hystrix.enabled=true
hystrix.command.default.execution.isolation.thread.timeoutInMilliseconds: 30000
統一處理,需要增加FeignClient遠程調用攜帶加密參數
@Component
public class FeignRequestInterceptor implements RequestInterceptor {
private org.slf4j.Logger log = LoggerFactory.getLogger(FeignRequestInterceptor.class);
@Override
public void apply(RequestTemplate requestTemplate) {
try {
// xxxx 算法
//String sign = DigestUtils.md5DigestAsHex(params.getBytes("utf-8"));
requestTemplate.query("sign", "xxxxxx");
} catch (UnsupportedEncodingException e) {
log.error("簽名失敗:", e);
}
}
}
