TCP-подключения складываются до 65 КБ при использовании функции извлечения HttpWebRequest - подключение к Интернету теряется

Я не понимаю, что может вызвать эту ошибку

Я использую приведенную ниже функцию с примерно 1000 одновременных подключений.

Каждое соединение использует другой веб-прокси

Через некоторое время, например, 15 минут работы, количество установленных TCP-соединений начинает складываться, и подключение к Интернету теряется.

Когда я не использую веб-прокси, я не сталкиваюсь с какой-либо ошибкой

Я использую функцию ниже для получения количества активных TCP-соединений

var properties = IPGlobalProperties.GetIPGlobalProperties();

Я не вижу никакой утечки в моей функции

Поэтому мне нужна ваша помощь, чтобы решить эту надоедливую проблему

С# .нет 4.6.2

Здесь статусы активных TCP-соединений при возникновении этой проблемы

введите здесь описание изображения

public static cs_HttpFetchResults func_fetch_Page(
    string srUrl, int irTimeOut = 60,
    string srRequestUserAgent = "Mozilla/5.0 (Windows NT 6.3; WOW64; rv:31.0) Gecko/20100101 Firefox/31.0",
    string srProxy = null, int irCustomEncoding = 0, bool blAutoDecode = true, bool blKeepAlive = true)
{
    cs_HttpFetchResults mycs_HttpFetchResults = new cs_HttpFetchResults();
    mycs_HttpFetchResults.srFetchingFinalURL = srUrl;

    HttpWebRequest request = null;
    WebResponse response = null;

    try
    {
        request = (HttpWebRequest)WebRequest.Create(srUrl);
        request.CookieContainer = new System.Net.CookieContainer();

        if (srProxy != null)
        {
            string srProxyHost = srProxy.Split(':')[0];
            int irProxyPort = Int32.Parse(srProxy.Split(':')[1]);
            WebProxy my_awesomeproxy = new WebProxy(srProxyHost, irProxyPort);
            my_awesomeproxy.Credentials = new NetworkCredential();
            request.Proxy = my_awesomeproxy;
        }
        else
        {
            request.Proxy = null;
        }

        request.ContinueTimeout = irTimeOut * 1000;
        request.ReadWriteTimeout = irTimeOut * 1000;
        request.Timeout = irTimeOut * 1000;
        request.UserAgent = srRequestUserAgent;
        request.KeepAlive = blKeepAlive;
        request.Accept = "text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8";

        WebHeaderCollection myWebHeaderCollection = request.Headers;
        myWebHeaderCollection.Add("Accept-Language", "en-gb,en;q=0.5");
        myWebHeaderCollection.Add("Accept-Encoding", "gzip, deflate");

        request.AutomaticDecompression = DecompressionMethods.Deflate | DecompressionMethods.GZip;

        using (response = request.GetResponse())
        {
            using (Stream strumien = response.GetResponseStream())
            {
                Encoding myEncoding = Encoding.UTF8;
                string srContentType = "";

                if (response.ContentType != null)
                {
                    srContentType = response.ContentType;
                    if (srContentType.Contains(";"))
                    {
                        srContentType = srContentType.Split(';')[1];
                    }
                    srContentType = srContentType.Replace("charset=", "");
                    srContentType = func_Process_Html_Input(srContentType);
                }

                try
                {
                    myEncoding = Encoding.GetEncoding(srContentType);
                }
                catch
                {
                    myEncoding = irCustomEncoding == 0 ? Encoding.UTF8 : Encoding.GetEncoding(irCustomEncoding);
                }

                using (StreamReader sr = new StreamReader(strumien, myEncoding))
                {
                    mycs_HttpFetchResults.srFetchBody = sr.ReadToEnd();
                    if (blAutoDecode == true)
                    {
                        mycs_HttpFetchResults.srFetchBody = HttpUtility.HtmlDecode(mycs_HttpFetchResults.srFetchBody);
                    }
                    mycs_HttpFetchResults.srFetchingFinalURL = Return_Absolute_Url(response.ResponseUri.AbsoluteUri.ToString(), response.ResponseUri.AbsoluteUri.ToString());
                    mycs_HttpFetchResults.blResultSuccess = true;
                }
            }
        }

        if (request != null)
            request.Abort();
        request = null;
    }
    catch (Exception E)
    {
        if (E.Message.ToString().Contains("(404)"))
            mycs_HttpFetchResults.bl404 = true;

        csLogger.logCrawlingErrors("crawling failed url: " + srUrl, E);

    }
    finally
    {
        if (request != null)
            request.Abort();
        request = null;

        if (response != null)
            response.Close();
        response = null;
    }

    return mycs_HttpFetchResults;
}

person MonsterMMORPG    schedule 21.03.2017    source источник
comment
Мой главный совет здесь — не использовать WebRequest и вместо этого перейти на более новый HttpClient. Если ничего другого, он поддерживает IDisposable   -  person DavidG    schedule 21.03.2017
comment
(a) вы никогда не получите высокую пропускную способность, используя синхронные API. (b) при использовании асинхронных API помните, что фаза поиска DNS является синхронной. Это можно смягчить ( stackoverflow.com/a/26050285/14357 ) с помощью сторонней библиотеки DNS (возможно, arsofttoolsnet.codeplex.com ) (c) исходя из моего опыта сканирования, наиболее вероятная точка отказа (если вы абсолютно уверены ваш код работает) находится на маршрутизаторе. Домашние маршрутизаторы, как правило, крайне неадекватны для сканирования больших объемов данных, и когда им не хватает памяти, соединения просто исчезают.   -  person spender    schedule 21.03.2017
comment
@spender отлично работает 15-20 минут. после этого какие-то странные ошибки. я уверен, что некоторые ошибки происходят из-за того, что количество установленных соединений начинает накапливаться. я ничего не понимаю :( мой домашний маршрутизатор довольно хорош. пропускная способность никогда не достигает максимума. я попытаюсь предоставить IP-хост. может быть, это о DNS.   -  person MonsterMMORPG    schedule 21.03.2017
comment
@DavidG я проверил. он не поддерживает прокси :(   -  person MonsterMMORPG    schedule 21.03.2017
comment
Он абсолютно поддерживает прокси. stackoverflow.com/a/24677189/1663001   -  person DavidG    schedule 21.03.2017
comment
@MonsterMMORPG Для меня не была проблемой пропускная способность. Моя первая попытка такого рода вещей, у маршрутизатора буквально закончилась память при обслуживании большого количества подключений. Может быть, это то же самое для вас.   -  person spender    schedule 21.03.2017
comment
@spender я все равно могу определить, проблема в этом или нет?   -  person MonsterMMORPG    schedule 21.03.2017
comment
@DavidG, ты очень много. проверит это. похоже, он поддерживает все функции HttpWebRequest, верно?   -  person MonsterMMORPG    schedule 21.03.2017
comment
Он поддерживает все и даже больше.   -  person DavidG    schedule 21.03.2017
comment
HttpClient (в обычной среде Windows) будет полагаться на HttpWebRequest для всего подъема, но я согласен с @DavidG. Объединение HttpMessageHandlers/DelegatingHandlers в HttpClient — отличный способ настроить поведение HttpClient. Это также упрощает асинхронный код, на который вы захотите переключиться.   -  person spender    schedule 21.03.2017
comment
Можете ли вы войти в свой маршрутизатор и просмотреть статистику? Предлагает ли он вход в систему SSH/telnet, где вы можете вводить любые команды для просмотра статистики?   -  person spender    schedule 21.03.2017
comment
@DavidG, я преобразовал его в HttpClient, можете ли вы проверить, пожалуйста? codereview.stackexchange.com/questions/158359/   -  person MonsterMMORPG    schedule 21.03.2017
comment
@spender мой роутер Huawei HG253/S. Я думаю, он не поддерживает такую ​​статистику. Это оптоволоконный маршрутизатор   -  person MonsterMMORPG    schedule 21.03.2017
comment
@spender Я еще проверю, связана ли проблема с маршрутизатором или нет, надеюсь, завтра. здесь 6 утра. между тем вы можете проверить это? stackoverflow.com/questions/42917528/   -  person MonsterMMORPG    schedule 21.03.2017
comment
@DavidG, ты можешь это проверить? я хочу запретить поиск DNS: stackoverflow.com/questions/42917528/   -  person MonsterMMORPG    schedule 21.03.2017
comment
Похоже, ваш код всегда будет прерываться, а не пытаться закрыть. Ознакомьтесь с документацией по адресу msdn. .microsoft.com/en-us/library/   -  person Mokubai    schedule 21.03.2017
comment
Даже с Abort вам все равно нужно закрыть соединение: msdn.microsoft.com/en-us/library/   -  person Mokubai    schedule 21.03.2017
comment
@Mokubai у httpwebrequest нет ничего похожего. Также я использую предложение using для ответа. ответ действительно имеет значение close, но, поскольку он обернут с помощью предложения using, его следует обрабатывать правильно. или не?   -  person MonsterMMORPG    schedule 21.03.2017