【高效能閘道器soul學習】14. 外掛之dubbo原理
阿新 • • 發佈:2021-01-31
【高效能閘道器soul學習】14. 外掛之dubbo原理
本文目標:
- 介紹 dubbo 外掛原理,本文主要以 alibaba-dubbo 部分作為介紹
dubbo 外掛
dubbo 外掛作為外掛鏈的一環,處理 dubbo 的請求
我們啟動相關服務,然後跟蹤請求分析邏輯程式碼做了些什麼
AlibabaDubboPlugin 相關的核心大致流程圖:
- doExecute:異常情況檢查
- alibabaDubboProxyService.genericInvoker
- 根據 metaData的資訊去快取ApplicationConfigCache 獲取或者建立一個 ReferenceConfig
- 從ReferenceConfig 中獲取一個 GenericService
- ReferenceConfig 例項很重,封裝了與註冊中心的連線以及與提供者的連線
- dubboParamResolveService.buildParameter :構建請求引數
- genericService.$invoke:呼叫結果返回
- alibabaDubboProxyService.genericInvoker
- DubboResponsePlugin: 對結果進行處理,封裝為webflux的結果進行返回
- WebFluxResultUtils.result
@Override
protected Mono<Void> doExecute(final ServerWebExchange exchange, final SoulPluginChain chain, final SelectorData selector, final RuleData rule) {
String body = exchange.getAttribute(Constants.DUBBO_PARAMS);
SoulContext soulContext = exchange.getAttribute(Constants.CONTEXT);
assert soulContext != null;
MetaData metaData = exchange.getAttribute(Constants.META_DATA);
if (!checkMetaData(metaData)) {
// return 異常處理
}
if (StringUtils.isNoneBlank(metaData.getParameterTypes()) && StringUtils.isBlank(body)) {
// return 異常處理
}
Object result = alibabaDubboProxyService.genericInvoker(body, metaData);
if (Objects.nonNull(result)) {
exchange.getAttributes().put(Constants.DUBBO_RPC_RESULT, result);
} else {
exchange.getAttributes().put(Constants.DUBBO_RPC_RESULT, Constants.DUBBO_RPC_RESULT_EMPTY);
}
exchange.getAttributes().put(Constants.CLIENT_RESPONSE_RESULT_TYPE, ResultEnum.SUCCESS.getName());
return chain.execute(exchange);
}
public Object genericInvoker(final String body, final MetaData metaData) throws SoulException {
// 獲取或者傳建一個服務引用配置 ReferenceConfig
ReferenceConfig<GenericService> reference = ApplicationConfigCache.getInstance().get(metaData.getPath());
if (Objects.isNull(reference) || StringUtils.isEmpty(reference.getInterface())) {
ApplicationConfigCache.getInstance().invalidate(metaData.getPath());
reference = ApplicationConfigCache.getInstance().initRef(metaData);
}
// 從引用配置中獲取一個泛化服務
GenericService genericService = reference.get();
try {
Pair<String[], Object[]> pair;
// 構建請求引數
if (ParamCheckUtils.dubboBodyIsEmpty(body)) {
pair = new ImmutablePair<>(new String[]{}, new Object[]{});
} else {
pair = dubboParamResolveService.buildParameter(body, metaData.getParameterTypes());
}
// 請求並返回
return genericService.$invoke(metaData.getMethodName(), pair.getLeft(), pair.getRight());
} catch (GenericException e) {
log.error("dubbo invoker have exception", e);
throw new SoulException(e.getExceptionMessage());
}
}
總結
- 介紹了 soul 中 dubbo 的呼叫流程,可以發現實現所用的邏輯還是比較清晰簡單的