dubbo 服務降級


1.開關 

        先講一下開關的由來,例如京東在6月18日做店慶促銷活動,在交易下單環節,可能需要調用A、B、C三個接口來完成,但是其實A和B是必須的,C只是附加的功能(例如在下單的時候做一下推薦),可有可無,在平時系統沒有壓力,容量充足的情況下,調用下沒問題但是在類似店慶之類的大促環節,系統已經滿負荷了,這時候其實完全可以不去調用C接口,怎么實現這個呢?改代碼?no,no,no,這樣太不敏捷,此時開關誕生了,開發人員只要簡單執行一下命令或者點一下頁面,就可以關掉對於C接口的調用,在大促過去之后,再把開關恢復回去即可。

2.什么是服務降級

          服務降級,當服務器壓力劇增的情況下,根據當前業務情況及流量對一些服務和頁面有策略的降級,以此釋放服務器資源以保證核心任務的正常運行。

3.服務降級方式:

  • 服務接口拒絕服務:無用戶特定信息,頁面能訪問,但是添加刪除提示服務器繁忙。頁面內容也可在Varnish或CDN內獲取。
  • 頁面拒絕服務:頁面提示由於服務繁忙此服務暫停。跳轉到varnish或nginx的一個靜態頁面。
  •  延遲持久化:頁面訪問照常,但是涉及記錄變更,會提示稍晚能看到結果,將數據記錄到異步隊列或log,服務恢復后執行。
  •  隨機拒絕服務:服務接口隨機拒絕服務,讓用戶重試,目前較少有人采用。因為用戶體驗不佳。

 

      經過過12306搶票的人應該經常會遇到這個問題:在搶票高峰的時候,明明票還有,但是查詢出來的列表卻是為空的(如果沒票列表也應該會呈現);等高峰過后再查詢,列表又恢復正常。個人猜測應該是查詢過程中出現了問題,要么超時,要么網絡問題導致查詢失敗采用的服務降級處理。所以,最終呈現給用戶的並不是內部系統出錯之類的提示,而是一個空的列表。好了,言歸正傳,在dubbo中想實現服務降級,需要怎么樣做可以實現?

 

4 dubbo降級服務    
dubbo開發中,通常是微服務架構,那么在使用過程中可能會遇到多種問題:

1)多個服務之間可能由於服務沒有啟動或者網絡不通,調用中會出現遠程調用失敗;

2) 服務請求過大,需要停止部分服務以保證核心業務的正常運行;

以上兩個問題可以使用Dubbo的服務降級來實現;
即:在服務宕掉或者並發數太高導致的RpcException異常時,進行友好的處理或者提示,而不是內部報錯導致系統不可用。也停掉非核心調用,減輕服務器壓力

 

解決方法:
dubbo提供了mock配置,可以很好的實現dubbo服務降級,
mock主要有兩種配置方式,

第1種
直接返回一個固定的字符串
具體配置:
在服務調用方配置mock參數: 直接定義返回值
<dubbo:reference id="xxxService" interface="com.x..service.xxxxService" check="false" mock="return 123456..." />

說明:配置了mock參數之后,假設在調用服務的時候,遠程服務沒有啟動,或者各種網絡異常了,那遠程服務會把這個mock配置的值返回,也就是會返回123456...
通過這種方式就可以避免了因為服務調用不了而出現異常錯誤而帶來的程序不可用(起碼是有值返回的,然后可以根據值進行業務邏輯處理判斷等等)。
注:除了配置mock參數之外,其它地方不用變。

 

第2種
根據自定義mock業務處理類進行返回     mock值設置為boolean 類型
具體配置:
在服務調用方配置mock參數:
<dubbo:reference id="xxxService" interface="com.x..service.xxxxService" check="false" mock="true" />

說明:配置了mock參數之后,假設在調用服務的時候,遠程服務沒有啟動,或者各種網絡異常了,那遠程服務會去尋找自定義的mock業務處理類進行業務處理。
因此還需配置一個自定義mock業務處理類
在接口服務xxxxService的目錄下創建相應的mock業務處理類,同時實現業務接口xxxxService(),接口名要注意命名規范:接口名+Mock后綴,mock實現需要保證有無參的構造方法。

 

//要實現接口,並實現相關方法 

public class xxxxServiceMock implements xxxxService {

    //降級時用到
    @Override
    public String getXXXX(int id) {
        return "this is exception 自定義....";
    }
}

 配置完成后,此時如果調用失敗會調用自定義的Mock業務實現(即上面的實現類中對應方法  getXXXX)。

 

5 管理界面手動配置

以上的配置其實除了在代碼中配置之外,還可以在dubb-adming管理界面直接手動配置:

分別是屏蔽和容錯:

屏蔽:force.mock (即:屏蔽請求,直接返回某個值,如上面的字符串,mock="return 123456...");

容錯:fail.mock  (即:允許請求,在請求失敗的時候,再返回某個值,如:mock="fail:return 123456...");

 

 

6、思考

    通過例子可以知道,通過mock的配置,可以很好的實現dubbo服務降級。但是,比如例子里,接口IUser本身定義了兩個接口,一個是新增用戶,一個是根據id查詢用戶信息。對於根據id查詢用戶信息,在調用失敗的時候返回null很好理解,可能是由於驗證失敗或者記錄刪除了,但是對於新增用戶,可能就需要拋出具體的業務信息,否則程序無法處理后續的業務,包括頁面彈出”添加成功“或者列表刷新的時候無法查看到最新的記錄,這樣體驗將會非常不好。所以,如果要有較好的區分,可以通過以下的方式,可以更好的實現降級:

(1)將接口進行歸類,查詢類和變更操作類:對於查詢的分為一個接口類,變更的歸類為其他的接口類,這樣對於查詢的可以使用mock="return null"進行降級操作對於變更類的,可以仍舊使用try……catch進行異常捕獲處理

(2)配置mock="true",同時mock實現接口,接口名要注意命名規范:接口名+Mock后綴。此時如果調用失敗會調用Mock實現的方法。mock實現需要保證有無參的構造方法。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM