相關文章:
ServiceBean
ServiceBean 實現ApplicationListener接口監聽ContextRefreshedEvent事件(容器加載完成事件)
public void onApplicationEvent(ApplicationEvent event) {
if (ContextRefreshedEvent.class.getName().equals(event.getClass().getName())) {
if (isDelay() && ! isExported() && ! isUnexported()) {
if (logger.isInfoEnabled()) {
logger.info("The service ready on spring started. service: " + getInterface());
}
export();
}
}
在容器加載完成后執行export(); 開始暴露
ServiceConfig 類
方法執行順序:export() -> doExport() -> doExportUrls() -> doExportUrlsFor1Protocol();
export() 判斷是否延遲發布,如果延遲發布會新建個Daemon線程然后調用doExport(), 否則直接調用doExport();
doExport() 給ServiceConfig 裝載注冊中心監控中心等。
doExportUrls()
private void doExportUrls() {
List<URL> registryURLs = loadRegistries(true);
for (ProtocolConfig protocolConfig : protocols) {
doExportUrlsFor1Protocol(protocolConfig, registryURLs);
}
}
-
執行loadRegistries()遍歷注冊中心,根據注冊中心、Dubbo版本、Pid等生成要發布的URL;
URL示例: zookeeper://127.0.0.1:2181/com.alibaba.dubbo.registry.RegistryService?application=ordercenter_serviceImpl
&dubbo=2.8.4&pid=15836®istry=zookeeper×tamp=1484018365125 -
遍歷服務協議,為每個協議執行doExportUrlsFor1Protocol()
doExportUrlsFor1Protocol()
Invoker<?> invoker = proxyFactory.getInvoker(ref, (Class) interfaceClass, registryURL.addParameterAndEncoded(Constants.EXPORT_KEY, url.toFullString()));
Exporter<?> exporter = protocol.export(invoker);
- 創建 Invoker
- 調用 protocol.export() 將Invoker 轉換成Exporter
DubboProtocol類
方法執行順序:export() -> openServer() ->createServer()
createServer() 通過Exchangers.bind() 創建 ExchangeServer
RegistryProtocol類
DubboProtocol export() 執行完成后最終返回上層包裝類 RegistryProtocol類
RegistryProtocol export() 進行服務注冊和變更訂閱
public <T> Exporter<T> export(final Invoker<T> originInvoker) throws RpcException {
//export invoker
final ExporterChangeableWrapper<T> exporter = doLocalExport(originInvoker);
//registry provider
final Registry registry = getRegistry(originInvoker);
final URL registedProviderUrl = getRegistedProviderUrl(originInvoker);
registry.register(registedProviderUrl);
// 訂閱override數據
// FIXME 提供者訂閱時,會影響同一JVM即暴露服務,又引用同一服務的的場景,因為subscribed以服務名為緩存的key,導致訂閱信息覆蓋。
final URL overrideSubscribeUrl = getSubscribedOverrideUrl(registedProviderUrl);
final OverrideListener overrideSubscribeListener = new OverrideListener(overrideSubscribeUrl);
overrideListeners.put(overrideSubscribeUrl, overrideSubscribeListener);
registry.subscribe(overrideSubscribeUrl, overrideSubscribeListener);
//....
}