1. 程式人生 > >Dubbo 2.7.1 踩坑記

Dubbo 2.7.1 踩坑記

Dubbo 2.7 版本增加新特性,新系統開始使用 Dubbo 2.7.1 嚐鮮新功能。使用過程中不慎踩到這個版本的 Bug。

系統架構

Spring Boot 2.14-Release + Dubbo 2.7.1

現象

Dubbo 服務者啟動成功,正常提供服務,消費者呼叫偶現失敗的情況。錯誤如下圖:

可以看出,主要原因為 cause: message can not send, because channel is closed。 但是檢查提供者,卻發現服務程序正常。

登陸 Dubbo admin 檢視提供者服務,發現這個服務存在兩個節點。

192.168.164.77 為測試伺服器的 ip,提供者位於這臺機器,而另一個 10.20.80.67 卻是本地電腦的 IP,但是此時本地並未執行這個服務。

再次檢視服務報錯的原因,可以看到提供者呼叫l本地提供 RPC 的服務。由於本地服務已停止,導致呼叫失敗。

這個問題在之前版本從未碰到,剛開始隱約記得 Dubbo 服務提供者註冊使用 ZooKeeper 臨時節點,服務斷開,會刪除該節點。

問題原因

在 Dubbo 主頁搜尋相關 issue,看到同樣的問題 Dubbo-2.7.1 providers 重複註冊.

檢視相關回復,可以看到問題主要由於 dynamic 預設值變成 false ,而 2.7.1 之前版本預設不賦值,初始值為 null。

後續 PR 中已修復該問題 Fix issue 3785,修復程式碼將 dynamic 預設設定成 true。但是截止 20190515 該版本暫未釋出。

原始碼分析

知道問題原因,這裡我們從原始碼分析一下,為什麼 dynamic 設定成 false 會導致該問題。

注:下面分析的是 Dubbo 2.7.1 的原始碼
下面我們使用 Dubbo xml 配置相關。

在 xml 配置中,可以在以下兩個地方設定 dynamic 屬性。

服務啟動時將會使用 DubboNamespaceHandler 解析,注入 Spring 容器。

其中會將 provider 標籤解析成 ProviderConfig 物件,service 標籤解析成 ServiceBean 物件。

檢視繼承關係,可以看到以上兩個類都繼承 AbstractServiceConfig , dynamic 位於這個父物件中。

可以看到該欄位預設值為 false。

接著檢視 Dubbo 服務匯出過程,位於 ServiceBean#export,略過其他程式碼,我們直接跳到關鍵 ServiceConfig#doExportUrlsFor1Protocol 。

可以看到這裡呼叫了多次 appendParameters 方法。 這個方法將利用反射,獲取物件的中所有欄位資訊,然後新增到 map 中。其中欄位名字為鍵值,欄位實際值為內容。此時 map 鍵值內容為:

可以看到 map 中還有一個 default.dynamic,大家翻看程式碼自己思考一下,為什麼會出現這個?

接著我們跳到後面:

在這裡會將上面得到 map 組裝到 URL 物件中,然後再註冊到註冊中心。。

由於註冊中心使用的是 ZooKeeper,所以這裡將會使用 ZookeeperRegistry 實現類。

首先檢視 url##getParameter 方法,這裡 Constants.DYNAMIC_KEY 值為 dynamic。

該方法會先從 parameters 中根據鍵值取值。若不存在,會再根據 default 作為字首拼接再次取值。若還不存在則使用傳入的預設值。

檢視此時的 parameters 物件。

url.getParameter(Constants.DYNAMIC_KEY, true) 返回為 false。

然後分析 zkClient#create 方法,

由於 ephemeral 為 false,所以這個服務註冊到 ZooKeeper 的節點為持久節點。

臨時節點,客戶端斷開,會話超時後,ZooKeeper 將會自動刪除這個節點。zookeeper-faq
面試題:服務提供者能實現失效踢出是什麼原理(高頻題)

服務宕機的時候,該節點由於是持久節點會永遠存在,而且當服務再次重啟的時候會將重新註冊一個新節點。這樣就導致 ZooKeeper 中存在額外失效的節點,且該節點還無法自然消除(除非手動呼叫 ZooKeeper 刪除節點方法)。

總結

由於 Dubbo 2.7.2 暫未釋出,所以建議若想使用 Dubbo 2.7 新功能的同學,使用 2.7.0 版本。若現在正在使用 2.7.2 版本,也不要慌張。只要服務不是異常宕機或者使用 kill -9 強制殺死程序,以上的現象將不會碰到。正常服務關閉的時候,Dubbo 服務會主動去 ZooKeeper 登出該服務,並刪除這個節點。

還未使用該版本的同學們,建議使用 2.7.0 或者等 2.7.2 釋出以後,再使用。

相關推薦

Dubbo 2.7.1

Dubbo 2.7 版本增加新特性,新系統開始使用 Dubbo 2.7.1 嚐鮮新功能。使用過程中不慎踩到這個版本的 Bug。 系統架構 Spring Boot 2.14-Release + Dubbo 2.7.1 現象 Dubbo 服務者啟動成功,正常提供服務,消費者呼叫偶現失敗的情況。錯誤如下圖: 可

ELK之ES2.4.1雙例項平滑升級調優至5.2.1並supervisor管理

  ES老叢集用的2.4.1版本,跑的比較好就一直沒動,最近看資料ES5.X已經穩定,並且效能有較大提升,心裡就發癢了,但由於業務要保持高可用的屬性,就得想一個平滑升級的方案,最後想到了多例項過度的辦法,5.X版本網上介紹配置變化較大,也做好了踩坑準備,確定好要升級後,立刻

2018-7-30B:SpringCloud下mybatis DAO例項化失敗

Field baseDAO in per.wilson.distributed.dao.service.BaseServiceImpl required a bean of type 'per.wilson.distributed.dao.BaseDAO' that could not be

2018-7-30A:SpringCloud下@ConfigurationProperties屬性注入無效解決

解決方法:Bean的生成方法上添加註解@RefreshScope(也可新增到配置類上),關聯的配置類也需新增 範例如下: @Configuration @EnableAutoConfiguration public class DataSourceConfig { @Bean

centos 7( linux )下搭建elasticsearch

目錄 概述 環境準備 elasticsearch配置 啟動踩坑記 彩蛋 概述     公司最近在做全文檢索的專案,發現elasticsearch踩了不少坑,百度點進去又是坑,在此記錄一下自己的

SpringBoot 2.0.6 連線 Redis 切換db

專案中有一個小需求,在一個專案上不同的請求連線到同一個Redis 的不同的db上。 我使用的 SpringBoot是 2.0.6 RELEASE 版本的,按照網上說的方法,切換完db後(redisTemplete裡面打斷點可以看出來已經成功切換),還是會按原來的連線去查詢,

redhat6.7下使用rpm方式 安裝 mysql8.0.12,修改密碼,允許遠端訪問

1.首先需要下載mysql rpm 包,下載地址  輸入mysql database server後搜尋,將你需要的mysql加入購物車,然後打包下載 下載好的包如下 2.將下載好的mysql rpm包上傳至linux伺服器 3.依次執行以下命令  -iv

Spring Boot 2.x 基礎案例:整合Dubbo 2.7.3+Nacos1.1.3(最新版)

1、概述 本文將介紹如何基於Spring Boot 2.x的版本,通過Nacos作為配置與註冊中心,實現Dubbo服務的註冊與消費。 整合元件的版本說明: Spring Boot 2.1.9 Dubbo 2.7.3 Nacos 1.1.3 本文的亮點: 1.採用yml方式進行dubbo的配置。 2.

Spring Boot 2.x 基礎案例:整合Dubbo 2.7.3+Nacos1.1.3(配置中心)

本文原創首發於公眾號:Java技術乾貨 1、概述 本文將Nacos作為配置中心,實現配置外部化,動態更新。這樣做的優點:不需要重啟應用,便可以動態更新應用裡的配置資訊。在如今流行的微服務應用下,將應用的配置統一管理,顯得尤為重要。 上一篇寫了《Spring Boot 2.x 基礎案例:整合Dubbo

2.7.1 元素定位:selenium消息框處理 (alert、confirm、prompt)

ttext def 總結篇 必須 tro -s 按鈕 默認 答案 來源:http://blog.csdn.net/cui_angel/article/details/7784211 http://www.cnblogs.com/tobecrazy/p/45

Visual Studio For MacOS (二)

mirrors class app macosx andro mce 資料 library devel Visual Studio For MacOS安裝安卓SDK。 系統默認安裝了安卓6.0 API23的SDK。 但是我需要安卓7.0的,API24. 遂安裝。

spark共享變量

park oid and 共享變量 roi syn out his andro %E5%9C%A8android%E4%B8%AD%E6%80%8E%E4%B9%88%E7%94%A8this removeviewinlayout?к????? repo????л???

Linux使用

gre 16px -- 機器 操作 onf 問題: 失敗 gbk Ubuntu安裝坑: 1、對於新手第一次安裝ubuntu,特殊情況會出現因為分辨率問題導致安裝界面不全,無法進行下一步操作。 解決方案:使用alt+鼠標左鍵拖動屏幕Linux文件名亂碼問題:

java-getResourceAsStream

mov load color () tar type 當前 blog ase 本文主要是研究下面集中方法到底誰才能真正的load到文件,你能一眼看出來嗎? GetResourcesSample.class.getClassLoader.getResourceAsStream

c# 重載運算符(ovveride operator),關於null比對

漏洞 pre console blog 為什麽 留言 報表 bool 解決辦法 場景描述: 需要比對兩個版本的對應對象是否完全一致(每個屬性值一致),不一致的導出報表顏色標識,以便提醒後續使用報表人員。 實現思路: 對象重載ToString方法,另實現一比對基類(為了通用)

Spring @Transactional

然而 效果 記錄 dcl iso 如果 分庫分表 ignore mar @Transactional踩坑記 總述 ? Spring在1.2引入@Transactional註解, 該註解的引入使得我們可以簡單地通過在方法或者類上添加@Transactional註解,實現事務控

配置Python 2.7.1外加環境pywin32-216.win32-py2.7

href str pytho AR content track blog clas edi python-2.7.1 ?安裝包 下載地址:http://down

桌面應用“標註器”打包

環境 的確 變量 標註 imp sci 技術 報錯 編寫 昨天(2018/4/6)花了幾乎一天的時間打包我的桌面應用“標註器”。下午3點完成最後的編寫之後,準備在女朋友雅喻的電腦上配環境打包(我的電腦不能用pyinstaller打包,重裝也不行,玄學錯誤。)。雅喻的電腦上缺

[轉]Spark :數據庫(Hbase+Mysql)

cep 直接 策略 https rds 但是 更新 base ID https://cloud.tencent.com/developer/article/1004820 Spark 踩坑記:數據庫(Hbase+Mysql) 前言 在使用Spark Streaming的過程

uWSGI

dex wsgi oba 啟動 監聽 head HR nvi header 一、協議的一致性 uWSGI 是在 nginx 後面,所以 nginx 轉發請求時的協議要和 uWSGI 監聽的協議一致。否則就會出現問題,因為是三者之間的通信,排查起來需要想清楚請求傳遞的次序: