溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶(hù)服務(wù)條款》

Dubbo并發(fā)調(diào)優(yōu)的參數(shù)分別是什么

發(fā)布時(shí)間:2021-11-25 16:51:29 來(lái)源:億速云 閱讀:151 作者:柒染 欄目:編程語(yǔ)言

這期內(nèi)容當(dāng)中小編將會(huì)給大家?guī)?lái)有關(guān)Dubbo并發(fā)調(diào)優(yōu)的參數(shù)分別是什么,文章內(nèi)容豐富且以專(zhuān)業(yè)的角度為大家分析和敘述,閱讀完這篇文章希望大家可以有所收獲。

消費(fèi)端調(diào)優(yōu): 

一、connections 

這個(gè)參數(shù)可以在服務(wù)提供端發(fā)布服務(wù)的時(shí)候配置,也可以在消費(fèi)端引用服務(wù)的時(shí)候配置,但是這個(gè)值是只對(duì)消費(fèi)端生效的,所以一般是服務(wù)提供端不建議配置,如果配置,請(qǐng)斟酌一下。不管是在消費(fèi)端或者服務(wù)提供端,如果對(duì)某個(gè)服務(wù)配置了connections參數(shù),并且該參數(shù)大于1,那么就會(huì)導(dǎo)致消費(fèi)端在創(chuàng)建該服務(wù)的遠(yuǎn)程socketclient的時(shí)候(如果是dubbo協(xié)議的話(huà))將會(huì)給該服務(wù)初始化一個(gè)私有的socketclient。所以一般不建議對(duì)這個(gè)值進(jìn)行調(diào)整。 

服務(wù)端優(yōu)化調(diào)整: 

相對(duì)余消費(fèi)端,服務(wù)端調(diào)優(yōu)的參數(shù)相對(duì)多一些,但是配置的時(shí)候也需要謹(jǐn)慎。 

一、executes 

這個(gè)參數(shù)是可以精確到方法級(jí)別的參數(shù),就是可以指定調(diào)用遠(yuǎn)程接口某個(gè)方法的是該參數(shù)的值。具體是怎么配置的可以到官方文檔里面去看看那,這里只是描述這個(gè)參數(shù)實(shí)際意義以及使用的時(shí)候應(yīng)該注意點(diǎn)。 

要說(shuō)這個(gè)參數(shù),就要所介紹ExecuteLimitFilter,他是這個(gè)參數(shù)使用者,看到Filter大家就應(yīng)該懂了,就是在每個(gè)方法請(qǐng)求前后加上業(yè)務(wù)邏輯。下面貼出里面的代碼: 

@Activate(group = Constants.PROVIDER, value = Constants.EXECUTES_KEY)

public class ExecuteLimitFilter implements Filter {

    public Result invoke(Invoker<?> invoker, Invocation invocation) throws RpcException {

        URL url = invoker.getUrl();

        String methodName = invocation.getMethodName();

        int max = url.getMethodParameter(methodName, Constants.EXECUTES_KEY, 0);

        if (max > 0) {

            RpcStatus count = RpcStatus.getStatus(url, invocation.getMethodName());

            if (count.getActive() >= max) {

                throw new RpcException("Failed to invoke method " + invocation.getMethodName() + " in provider " + url + ", cause: The service using threads greater than <dubbo:service executes=\"" + max + "\" /> limited.");

            }

        }

        long begin = System.currentTimeMillis();

        boolean isException = false;

        RpcStatus.beginCount(url, methodName);

        try {

            Result result = invoker.invoke(invocation);

            return result;

        } catch (Throwable t) {

            isException = true;

            if(t instanceof RuntimeException) {

                throw (RuntimeException) t;

            }

            else {

                throw new RpcException("unexpected exception when ExecuteLimitFilter", t);

            }

        }

        finally {

            RpcStatus.endCount(url, methodName, System.currentTimeMillis() - begin, isException);

        }

    }

}

上面這段代碼主要是看兩個(gè)地方,分別是第7行和第10行,第7行是獲取配置的executes的值,是一個(gè)int類(lèi)型的,描述數(shù)量,然后第10行是獲取當(dāng)前請(qǐng)求方法當(dāng)前的狀態(tài),里面既有一個(gè)active屬性(該屬性是AtomacInteger類(lèi)型的,大家應(yīng)該懂了為什么用這個(gè)類(lèi)型),表示當(dāng)前請(qǐng)求的方法處于執(zhí)行狀態(tài)的線程數(shù)量,如果這個(gè)值大于或者等于配置的值那么直接拋出異常,那么消費(fèi)端就會(huì)收到一個(gè)RPC的異常導(dǎo)致調(diào)用服務(wù)失敗,這是這個(gè)參數(shù)最終導(dǎo)致的效果。   

二、actives   

這個(gè)參數(shù)基本上和excetes一樣,但是有一點(diǎn)不同,在說(shuō)這不同之前,還是看看另一個(gè)Filter,看名字你們應(yīng)該就知道它是做什么的了—— ActiveLimitFilter,下面同樣貼出代碼:  

@Activate(group = Constants.CONSUMER, value = Constants.ACTIVES_KEY)

public class ActiveLimitFilter implements Filter {

    public Result invoke(Invoker<?> invoker, Invocation invocation) throws RpcException {

        URL url = invoker.getUrl();

        String methodName = invocation.getMethodName();

        int max = invoker.getUrl().getMethodParameter(methodName, Constants.ACTIVES_KEY, 0);

        RpcStatus count = RpcStatus.getStatus(invoker.getUrl(), invocation.getMethodName());

        if (max > 0) {

            long timeout = invoker.getUrl().getMethodParameter(invocation.getMethodName(), Constants.TIMEOUT_KEY, 0);

            long start = System.currentTimeMillis();

            long remain = timeout;

            int active = count.getActive();

            if (active >= max) {

                synchronized (count) {

                    while ((active = count.getActive()) >= max) {

                        try {

                            count.wait(remain);

                        } catch (InterruptedException e) {

                        }

                        long elapsed = System.currentTimeMillis() - start;

                        remain = timeout - elapsed;

                        if (remain <= 0) {

                            throw new RpcException("Waiting concurrent invoke timeout in client-side for service:  "

                                                   + invoker.getInterface().getName() + ", method: "

                                                   + invocation.getMethodName() + ", elapsed: " + elapsed

                                                   + ", timeout: " + timeout + ". concurrent invokes: " + active

                                                   + ". max concurrent invoke limit: " + max);

                        }

                    }

                }

            }

        }

        try {

            long begin = System.currentTimeMillis();

            RpcStatus.beginCount(url, methodName);

            try {

                Result result = invoker.invoke(invocation);

                RpcStatus.endCount(url, methodName, System.currentTimeMillis() - begin, true);

                return result;

            } catch (RuntimeException t) {

                RpcStatus.endCount(url, methodName, System.currentTimeMillis() - begin, false);

                throw t;

            }

        } finally {

            if(max>0){

                synchronized (count) {

                    count.notify();

                }

            }

        }

    }

}

上面代碼大致上和executes一樣,唯一不同的就是多了一個(gè)等待時(shí)間,當(dāng)當(dāng)前執(zhí)行該方法的線程超出了最大限制,那么可以等待一個(gè)timeout時(shí)間,如果時(shí)間過(guò)了還是超出了最大限制,那么就拋出異常。這個(gè)相對(duì)余executes來(lái)說(shuō)溫柔那么點(diǎn)。這就是那點(diǎn)不同!   

三、accepts 

在看代碼之前先看看這個(gè)參數(shù)的意思,這個(gè)參數(shù)是告知服務(wù)提供端能接收多少個(gè)消費(fèi)端連接該服務(wù)提供方。下面接著上代碼,這個(gè)參數(shù)的體現(xiàn)是在類(lèi)AbstractServer中。代碼如下:  

要說(shuō)這個(gè)參數(shù),就要所介紹ExecuteLimitFilter,他是這個(gè)參數(shù)使用者,看到Filter大家就應(yīng)該懂了,就是在每個(gè)方法請(qǐng)求前后加上業(yè)務(wù)邏輯。下面貼出里面的代碼: 

@Override

    public void connected(Channel ch) throws RemotingException {

        Collection<Channel> channels = getChannels();

        if (accepts > 0 && channels.size() > accepts) {

            logger.error("Close channel " + ch + ", cause: The server " + ch.getLocalAddress() + " connections greater than max config " + accepts);

            ch.close();

            return;

        }

        super.connected(ch);

    }

這個(gè)方法是每個(gè)消費(fèi)端向服務(wù)提供端創(chuàng)建一個(gè)socket連接的時(shí)候都會(huì)觸發(fā),上面可以清晰看到如果連接當(dāng)前服務(wù)端的消費(fèi)端數(shù)量超出了配置的值,那么將會(huì)關(guān)閉當(dāng)前消費(fèi)端連接的請(qǐng)求。這個(gè)只是對(duì)socket連接的數(shù)量限制,而不是像上面兩個(gè)參數(shù)對(duì)調(diào)用線程的配置。   

以上歸納出的幾個(gè)參數(shù)建議服務(wù)端生效的在服務(wù)端配置,消費(fèi)端生效的在消費(fèi)端配置,不然會(huì)導(dǎo)致一些不可控的現(xiàn)象出現(xiàn)。這也叫改哪里的東西就應(yīng)該在哪里,而不能亂放。

上述就是小編為大家分享的Dubbo并發(fā)調(diào)優(yōu)的參數(shù)分別是什么了,如果剛好有類(lèi)似的疑惑,不妨參照上述分析進(jìn)行理解。如果想知道更多相關(guān)知識(shí),歡迎關(guān)注億速云行業(yè)資訊頻道。

向AI問(wèn)一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI