首页 > 解决方案 > 为什么我有多个悬空的 OkHttp ConnectionPool 线程

问题描述

我有一个在后台执行 HTTP 获取请求的 Android 应用程序。我将很快提供一些有关如何执行此操作的详细信息。我将首先重点描述这个问题。

我在调试器中观察到s在 Android StudioOkHttp ConnectionPool的窗口中堆积。Threads这与我有关,因为它似乎表明资源泄漏,并且随着时间的推移,这些将无限增加(似乎)。

我的主要问题是我不知道为什么会发生这种情况。我几乎可以肯定这是我的错,但我不知道要寻找什么。所以我的一般问题是:

“每次发出 HTTP 请求时,什么可能导致创建新池?”

首先,这是我用来执行获取请求的代码。请注意,它被简化了,但我已经使用这个确切的代码运行并看到了问题。

private TestResult test() {
    final long startTime = SystemClock.elapsedRealtime();
    final String server = "connectivitycheck.gstatic.com";

    URL url;
    try {
        url = new URL("http", SOME_PATH);
    } catch (MalformedURLException e) {
        // We shouldn't get here since the url is well known
        return new TestResult(
                "failed to generate url " + e,
                SystemClock.elapsedRealtime() - startTime
        );
    }

    HttpURLConnection urlConnection = null;
    int httpResponseCode;
    try {
        urlConnection = (HttpURLConnection) url.openConnection();
        urlConnection.setInstanceFollowRedirects(false);
        urlConnection.setConnectTimeout(SOCKET_TIMEOUT_MS);
        urlConnection.setReadTimeout(SOCKET_TIMEOUT_MS);
        urlConnection.setUseCaches(false);
        InputStream is = urlConnection.getInputStream();
        httpResponseCode = urlConnection.getResponseCode();
        is.close();
    } catch (IOException e) {
        return new TestResult(
                e,
                SystemClock.elapsedRealtime() - startTime
        );
    } finally {
        if (urlConnection != null)
            urlConnection.disconnect();
    }
    if (httpResponseCode != HttpURLConnection.HTTP_NO_CONTENT) {
        return new TestResult(
                "invalid error code, expected 204 but got " + httpResponseCode,
                SystemClock.elapsedRealtime() - startTime
        );
    }

    return new TestResult(
            SystemClock.elapsedRealtime() - startTime
    );
}

那么,这段代码什么时候运行……?

首先让我说我已经尝试在我的应用程序上从我的家庭活动中运行此代码(在一个单独的线程中 - 因为在主 android 线程上不允许使用 HTTP)。当我这样做时,一切都很好。我可以提出多个请求,但永远不会看到多个池。

我运行代码并看到问题的情况如下:

请注意,这听起来可能令人费解,但所有这些都是有目的的。一方面,除了运行方法ExecutorService之外,还将执行许多其他任务。test

我已经很好地查看了悬挂引用,这些引用可能会以某种方式使底层 HTTP 资源保持活动状态,但我看不到任何内容。

有没有对 OkHttp 有很好了解的人知道为什么会发生这种情况?我希望有一些见解可以帮助我发现问题。

标签: androidmultithreadingokhttpresource-leak

解决方案


最简单的查找方法是在 ConnectionPool 构造函数中设置断点并运行您的应用程序。这将显示谁在创建它。我的猜测是它是一个不相关的类,比如崩溃报告器或分析库。


推荐阅读