c# - 在 Internet 中断时继续尝试与服务器通信

标签 c# .net httpwebrequest httpwebresponse system.net.webexception

所以我的应用程序正在与服务器交换请求/响应(没有问题),直到互联网连接中断几秒钟,然后恢复。然后是这样的代码:

response = (HttpWebResponse)request.GetResponse();

会抛出异常,状态如ReceiveFailureConnectFailureKeepAliveFailure

现在,如果互联网连接恢复,我能够继续与服务器通信是非常重要的,否则我必须从头开始,这将花费很长时间。

当互联网恢复后,您将如何恢复这种通信?

目前,我一直在检查与服务器通信的可能性,直到可能(至少在理论上)。我的代码尝试如下所示:

try
{
    response = (HttpWebResponse)request.GetResponse();
}
catch (WebException ex)
{
    // We have a problem receiving stuff from the server. 
    // We'll keep on trying for a while
    if (ex.Status == WebExceptionStatus.ReceiveFailure || 
        ex.Status == WebExceptionStatus.ConnectFailure || 
        ex.Status == WebExceptionStatus.KeepAliveFailure)
    {
        bool stillNoInternet = true;

        // keep trying to talk to the server
        while (stillNoInternet)
        {
            try
            {
                response = (HttpWebResponse)request.GetResponse();
                stillNoInternet = false;
            }
            catch
            {
                stillNoInternet = true;
            }
        }
    }
}

但是,问题在于即使互联网恢复正常,第二个 try-catch 语句仍会抛出异常。

我做错了什么?还有其他方法可以解决这个问题吗?

谢谢!

最佳答案

您应该每次都重新创建请求,并且您应该在每次重试之间等待的循环中执行重试。等待时间应随着每次失败而逐渐增加。

例如

ExecuteWithRetry (delegate {
    // retry the whole connection attempt each time
    HttpWebRequest request = ...;
    response = request.GetResponse();
    ...
});

private void ExecuteWithRetry (Action action) {
    // Use a maximum count, we don't want to loop forever
    // Alternativly, you could use a time based limit (eg, try for up to 30 minutes)
    const int maxRetries = 5;

    bool done = false;
    int attempts = 0;

    while (!done) {
        attempts++;
        try {
            action ();
            done = true;
        } catch (WebException ex) {
            if (!IsRetryable (ex)) {
                throw;
            }

            if (attempts >= maxRetries) {
                throw;
            }

            // Back-off and retry a bit later, don't just repeatedly hammer the connection
            Thread.Sleep (SleepTime (attempts));
        }
    }
}

private int SleepTime (int retryCount) {
    // I just made these times up, chose correct values depending on your needs.
    // Progressivly increase the wait time as the number of attempts increase.
    switch (retryCount) {
        case 0: return 0;
        case 1: return 1000;
        case 2: return 5000;
        case 3: return 10000;
        default: return 30000;
    }
}

private bool IsRetryable (WebException ex) {
    return
        ex.Status == WebExceptionStatus.ReceiveFailure ||
        ex.Status == WebExceptionStatus.ConnectFailure ||
        ex.Status == WebExceptionStatus.KeepAliveFailure;
}

关于c# - 在 Internet 中断时继续尝试与服务器通信,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6956233/

相关文章:

c# - 如何在 Windows Phone 7 中的 webBrowser 中捕获单击链接的事件

c# - 将字符串数组添加到组合框

java - 通过Java创建交换通用通讯组

objective-c - 在 Objective-C 中为 POST HTTP 请求生成 JSON 负载

c# - 在类之外编写的嵌套类

c# - 引用自定义组件的设计时程序集

c# - COM 接口(interface)将 COM 回调传递给 .Net 应用程序时出现内存泄漏

c# - 如何为 HttpWebRequest 定义更积极的超时?

c# - 在 C# 中使用 Windows 应用程序执行 http 方法

c# - DefaultModelBinder 无法反序列化作为 JSON 对象传递给操作的 .NET Dictionary 对象?