Dubbo之路由與配置規則(2.6.x)


Dubbo版本

  1. Dubbo 2.6.7版本
  2. 官方文檔舊路由規則文檔中【標簽路由規則】存在描述錯誤。 https://github.com/apache/dubbo-website/issues/1022這是我提交的issue

簡介

  1. 路由規則決定Dubbo調用哪些目標服務器,分為條件路由規則和腳本路由規則

  2. 一般由監控中心(Dubbo-Admin)或者治理中心來配置路由規則

  3. 向注冊中心寫入路由規則的API方式

    RegistryFactory registryFactory =
      ExtensionLoader.getExtensionLoader(RegistryFactory.class).getAdaptiveExtension();
    Registry registry = registryFactory.getRegistry(URL.valueOf("zookeeper://10.20.153.10:2181"));
    registry.register(
      URL.valueOf("route://0.0.0.0/com.foo.BarService?category=routers&dynamic=false&rule="
                + URL.encode("host = 10.20.153.10 => host = 10.20.153.11")));
    
  4. URL參數說明

    參數 描述 是否必填
    route:// 表示路由規則的類型,支持條件路由規則和腳本路由規則。可擴展
    0.0.0.0 表示對所有 IP 地址生效,如果只想對某個 IP 的生效,請填入具體 IP
    com.foo.BarService 表示只對指定服務生效
    group=foo 對指定服務的指定group生效,不填表示對未配置group的指定服務生效
    version=1.0 對指定服務的指定version生效,不填表示對未配置version的指定服務生效
    category=routers 表示該數據為動態配置類型
    dynamic=false 表示該數據為持久數據,當注冊方退出時,數據依然保存在注冊中心
    enabled=true 覆蓋規則是否生效,可不填,缺省生效
    force=false 當路由結果為空時,是否強制執行,如果不強制執行,路由結果為空的路由規則將自動失效,可不填,缺省為 false
    runtime=false 是否在每次調用時執行路由規則,否則只在提供者地址列表變更時預先執行並緩存結果,調用時直接從緩存中獲取路由結果。如果用了參數路由,必須設為 true,需要注意設置會影響調用的性能,可不填,缺省為 false
    priority=1 路由規則的優先級,用於排序,優先級越大越靠前執行。默認是0
    rule=URL.encode("host = 10.20.153.10 => host = 10.20.153.11") 路由規則的內容

條件路由

  1. 規則:consumer匹配條件 => provider匹配條件

    • => 之前的為消費者匹配條件,所有參數和消費者的 URL 進行對比,當消費者滿足匹配條件時,對該消費者執行后面的過濾規則。
    • => 之后為提供者地址列表的過濾條件,所有參數和提供者的 URL 進行對比,消費者最終只拿到過濾后的地址列表。
    • 如果匹配條件為空,表示對所有消費方應用,如:=> host != 10.20.153.11
    • 如果過濾條件為空,表示禁止訪問,如:host = 10.20.153.10 =>
  2. 表達式

    • 參數支持:

      • 服務調用信息,如:method, argument 等,暫不支持參數路由

      • URL 本身的字段,如:protocol, host, port 等

      • 以及 URL 上的所有參數,如:application, organization 等

    • 條件支持:

      • 等號 = 表示"匹配",如:host = 10.20.153.10
      • 不等號 != 表示"不匹配",如:host != 10.20.153.10
    • 值支持:

      • 以逗號 , 分隔多個值,如:host != 10.20.153.10,10.20.153.11
      • 以星號 * 結尾,表示通配,如:host != 10.20.*
      • 以美元符 $ 開頭,表示引用消費者參數,如:host = $host
  3. 示例

    1. 排除IP
    => host != 172.22.3.91
    
    2. 白名單(一個服務只能有一條白名單規則,否則兩條規則交叉,就都被篩選掉了)
    host != 10.20.153.10,10.20.153.11 =>
    
    3. 黑名單:
    host = 10.20.153.10,10.20.153.11 =>
    
    4. 服務寄宿在應用上,只暴露一部分的機器,防止整個集群掛掉:
    => host = 172.22.3.1*,172.22.3.2*
    
    5. 為重要應用提供額外的機器:
    application != kylin => host != 172.22.3.95,172.22.3.96
    
    6. 讀寫分離:
    method = find*,list*,get*,is* => host = 172.22.3.94,172.22.3.95,172.22.3.96
    method != find*,list*,get*,is* => host = 172.22.3.97,172.22.3.98
    
    7.前后台分離:
    application = bops => host = 172.22.3.91,172.22.3.92,172.22.3.93
    application != bops => host = 172.22.3.94,172.22.3.95,172.22.3.96
    
    8. 隔離不同機房網段:
    host != 172.22.3.* => host != 172.22.3.*
    
    9. 提供者與消費者部署在同集群內,本機只訪問本機的服務:
    => host = $host
    
  4. 端口

    1. 只調用指定端口的服務
    => port = 20881
    => port = 20881,20882
    
    2. ip和端口
    => port = 20881,20882 & host = 172.16.117.33 
    

標簽路由

  1. 當應用選擇裝配標簽路由(TagRouter)之后,一次 dubbo 調用能夠根據請求攜帶的 tag 標簽智能地選擇對應 tag 的服務提供者進行調用。

    • dubbo.tag=provder1 時優先選擇 tag=provider1 的 provider。若集群中不存在與請求標記對應的服務,可以降級請求tag=null 的 provider,即默認 provider。
    • dubbo.tag=null時,只會匹配 tag=null 的 provider。即使集群中存在可用的服務,若 tag 不匹配就無法調用,這與規則1不同,攜帶標簽的請求可以降級訪問到無標簽的服務,但不攜帶標簽/攜帶其他種類標簽的請求永遠無法訪問到其他標簽的服務
  2. 生產者配置

    1. 應用設置標簽
    <dubbo:application name="xml-demo-provider">
        <dubbo:parameter key="qos.enable" value="false"/>
        <dubbo:parameter key="dubbo.tag" value="provder1"/>
    </dubbo:application>
    
    2. provider設置標簽
    <dubbo:provider tag="provder2"></dubbo:provider>
    
  3. 消費者配置

    //dubbo.tag
    RpcContext.getContext().setAttachment(Constants.TAG_KEY, "provder1");
    //dubbo.force.tag 如果設置為true,則不降級,否則降級為默認provider
    RpcContext.getContext().setAttachment(Constants.FORCE_USE_TAG, "provder1");
    
  4. 源碼分析TagRouter#route

    @Override
    public <T> List<Invoker<T>> route(List<Invoker<T>> invokers, URL url, Invocation invocation) throws RpcException {
        // filter
        List<Invoker<T>> result = new ArrayList<Invoker<T>>();
        // Dynamic param 獲取dubbo.tag
        String tag = RpcContext.getContext().getAttachment(Constants.TAG_KEY);
        // Tag request
        if (!StringUtils.isEmpty(tag)) {
            // Select tag invokers first
            for (Invoker<T> invoker : invokers) {
                if (tag.equals(invoker.getUrl().getParameter(Constants.TAG_KEY))) {
                    result.add(invoker);
                }
            }
        }
        // If Constants.REQUEST_TAG_KEY unspecified or no invoker be selected, downgrade to normal invokers
        if (result.isEmpty()) {
            // Only forceTag = true force match, otherwise downgrade
            //如果dubbo.force.tag=true則不降級,否則降級為默認provider
            String forceTag = RpcContext.getContext().getAttachment(Constants.FORCE_USE_TAG);
            if (StringUtils.isEmpty(forceTag) || "false".equals(forceTag)) {
                for (Invoker<T> invoker : invokers) {
                    if (StringUtils.isEmpty(invoker.getUrl().getParameter(Constants.TAG_KEY))) {
                        result.add(invoker);
                    }
                }
            }
        }
        return result;
    }
    

配置規則

  1. 覆蓋規則是 Dubbo 設計的在無需重啟應用的情況下,動態調整 RPC 調用行為的一種能力。可以通過監控中心或者治理中心向注冊中心寫入動態配置覆蓋規則

    RegistryFactory registryFactory = ExtensionLoader.getExtensionLoader(RegistryFactory.class).getAdaptiveExtension();
    Registry registry = registryFactory.getRegistry(URL.valueOf("zookeeper://10.20.153.10:2181"));
    registry.register(URL.valueOf("override://0.0.0.0/com.foo.BarService?category=configurators&dynamic=false&application=foo&timeout=1000"));
    
  2. URL參數說明

    參數 描述 是否必填
    override:// 表示數據采用覆蓋方式,支持 overrideabsent
    0.0.0.0 表示對所有 IP 地址生效,如果只想覆蓋某個 IP 的數據,請填入具體 IP
    com.foo.BarService 表示只對指定服務生效
    category=configurators 表示該數據為動態配置類型
    dynamic=false 表示該數據為持久數據,當注冊方退出時,數據依然保存在注冊中心
    enabled=true 覆蓋規則是否生效,缺省生效
    application=foo 表示只對指定應用生效,不填,表示對所有應用生效。
    timeout=1000 表示將滿足以上條件的 timeout 參數的值覆蓋為 1000。如果想覆蓋其它參數,直接加在 override 的 URL 參數上
  3. 示例

    • 禁用提供者:(通常用於臨時踢除某台提供者機器,相似的,禁止消費者訪問請使用路由規則)

      override://10.20.153.10/com.foo.BarService?category=configurators&dynamic=false&disbaled=true
      
    • 調整權重:(通常用於容量評估,缺省權重為 100)

      override://10.20.153.10/com.foo.BarService?category=configurators&dynamic=false&weight=200
      
    • 調整負載均衡策略:(缺省負載均衡策略為 random)

      override://10.20.153.10/com.foo.BarService?category=configurators&dynamic=false&loadbalance=leastactive
      
    • 服務降級:(通常用於臨時屏蔽某個出錯的非關鍵服務)

      override://0.0.0.0/com.foo.BarService?category=configurators&dynamic=false&application=foo&mock=force:return+null
      


免責聲明!

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



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