283

我有一个应用程序可以在 Xcode6-Beta1 和 Xcode6-Beta2 上与 iOS7 和 iOS8 一起正常工作。但是对于 Xcode6-Beta3、Beta4、Beta5,我在 iOS8 上遇到了网络问题,但在 iOS7 上一切正常。我得到错误"The network connection was lost."。错误如下:

错误:错误域=NSURLErrorDomain 代码=-1005“网络连接丢失。” UserInfo=0x7ba8e5b0 {NSErrorFailingURLStringKey=, _kCFStreamErrorCodeKey=57, NSErrorFailingURLKey=, NSLocalizedDescription=网络连接丢失。, _kCFStreamErrorDomainKey=1, NSUnderlyingError=0x7a6957e0 "网络连接丢失。"}

我使用 AFNetworking 2.x 和以下代码片段进行网络调用:

AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager];
[manager setSecurityPolicy:policy];
manager.requestSerializer = [AFHTTPRequestSerializer serializer];
manager.responseSerializer = [AFHTTPResponseSerializer serializer];

[manager POST:<example-url>
   parameters:<parameteres>
      success:^(AFHTTPRequestOperation *operation, id responseObject) {
          NSLog(@“Success: %@", responseObject);
      } failure:^(AFHTTPRequestOperation *operation, NSError *error) {
          NSLog(@"Error: %@", error);
      }];

我试过NSURLSession但仍然收到同样的错误。

4

32 回答 32

413

重新启动模拟器为我解决了这个问题。

于 2014-09-15T17:24:02.223 回答
247

我们遇到了这个确切的错误,结果证明这是底层 HTTP 实现的问题NSURLRequest

据我们所知,当 iOS 8/9/10/11 收到带有Keep-Alive标头的 HTTP 响应时,它会保留此连接以供以后重用(应该如此),但它保留的时间超过timeout了Keep-Alive 标头(它似乎总是使连接保持活动 30 秒。)然后当应用程序在不到 30 秒后发送第二个请求时,它会尝试重新使用可能已被服务器丢弃的连接(如果超过实数Keep-Alive已经过去)。

以下是我们目前找到的解决方案:

  • 将服务器的超时参数增加到 30 秒以上。看起来 iOS 总是表现得好像服务器将保持连接打开 30 秒,而不管 Keep-Alive 标头中提供的值如何。(这可以通过设置KeepAliveTimeout选项为 Apache 完成。
  • 您可以根据应用程序的 User-Agent 简单地禁用 iOS 客户端的保持活动机制(例如,对于 Apache:BrowserMatch "iOS 8\." nokeepalive在 mod 文件中setenvif.conf
  • 如果您无权访问服务器,您可以尝试发送带有Connection: close标头的请求:这将告诉服务器立即断开连接并在没有任何保持活动标头的情况下进行响应。但是目前, NSURLSession 似乎在Connection发送请求时覆盖了标头(我们没有广泛测试这个解决方案,因为我们可以调整 Apache 配置)
于 2014-09-23T13:54:21.677 回答
47

对于我来说,Resetting content and settings模拟器工作。要重置模拟器,请执行以下步骤:

iOS模拟器->重置内容和设置->按重置(在即将出现的警告上)

于 2014-10-29T06:54:36.817 回答
29

iOS 8.0 模拟器运行时有一个错误,如果您的网络配置在模拟设备启动时发生更改,模拟运行时中的更高级别 API(例如:CFNetwork)会认为它已失去网络连接。目前,建议的解决方法是在网络配置更改时简单地重新启动模拟设备。

如果您受到此问题的影响,请在http://bugreport.apple.com上提交其他重复的雷达,以获得更高的优先级。

如果您在更改网络配置的情况下看到此问题,则这不是已知错误,您绝对应该提交雷达,表明该问题不是已知的网络配置更改错误。

于 2014-09-29T19:25:13.250 回答
11

打开查尔斯为我解决了这个问题,这似乎很奇怪......

Charles 是一个 HTTP 代理 / HTTP 监视器 / 反向代理,它使开发人员能够查看他们的机器和 Internet 之间的所有 HTTP 和 SSL / HTTPS 流量。这包括请求、响应和 HTTP 标头(其中包含 cookie 和缓存信息)。

于 2014-09-26T19:15:11.143 回答
11

在 iOS 8 模拟器上运行时,beta 5 和 AFNetworking 1.3 也存在问题,导致连接错误:

Domain=NSURLErrorDomain Code=-1005 "网络连接丢失。"

相同的代码在 iOS 7 和 7.1 模拟器上运行良好,我的调试代理显示失败发生在实际尝试连接之前(即没有记录请求)。

我已经跟踪到 NSURLConnection 的失败并向 Apple 报告了错误。见附图中的第 5 行:

NSURLConnection 客户端委托确实失败了错误.

更改为使用https允许从 iOS 8 模拟器进行连接,尽管会出现间歇性错误。

Xcode 6.01 (gm) 中仍然存在问题。

于 2014-08-19T01:29:39.913 回答
10

为我解决问题的是重新启动模拟器,并重置内容和设置。

于 2015-02-03T09:29:13.803 回答
10

我在使用 Alamofire 时遇到了这个问题。我的错误是我为请求[:]中的参数发送了一个空字典GET,而不是发送nil参数。

希望这可以帮助!

于 2016-04-19T19:29:54.793 回答
6

请参阅 Github 上 1 月 5 日的 pjebs 评论。

方法1:

if (error.code == -1005)
{
    dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), ^{

        dispatch_group_t downloadGroup = dispatch_group_create();
        dispatch_group_enter(downloadGroup);
        dispatch_group_wait(downloadGroup, dispatch_time(DISPATCH_TIME_NOW, 5000000000)); // Wait 5 seconds before trying again.
        dispatch_group_leave(downloadGroup);
        dispatch_async(dispatch_get_main_queue(), ^{
            //Main Queue stuff here
            [self redoRequest]; //Redo the function that made the Request.
        });
    });

    return;
}

还有一些建议重新连接到该站点,

两次触发 POST 请求

解决方法:使用方法做站点连接,返回(id),如果网络连接丢失,返回使用相同的方法。

方法二

-(id) connectionSitePost:(NSString *) postSender Url:(NSString *) URL {
     // here set NSMutableURLRequest =>  Request

    NSHTTPURLResponse *UrlResponse = nil;
    NSData *ResponseData = [[NSData alloc] init];

    ResponseData = [NSURLConnection sendSynchronousRequest:Request returningResponse:&UrlResponse error:&ErrorReturn];

     if ([UrlResponse statusCode] != 200) {

          if ([UrlResponse statusCode] == 0) {

                  /**** here re-use method ****/
                  return [self connectionSitePost: postSender Url: URL];
          }

     } else {
          return ResponseData;
     }

}
于 2015-03-29T18:16:02.817 回答
4

Apple 发布了关于2017-01-25此错误的技术问答:

苹果技术问答 QA1941

处理“网络连接丢失”错误

A: NSURLErrorNetworkConnectionLost 是 NSURLErrorDomain 错误域中的错误 -1005,向用户显示为“网络连接丢失”。此错误意味着承载 HTTP 请求的底层 TCP 连接在 HTTP 请求正在进行时断开(有关此问题的更多信息,请参见下文)。在某些情况下 NSURLSession 可能会自动重试此类请求(特别是,如果请求是幂等的),但在 HTTP 标准不允许的其他情况下。

https://developer.apple.com/library/archive/qa/qa1941/_index.html#//apple_ref/doc/uid/DTS40017602

于 2019-01-30T19:03:21.590 回答
4

我也遇到了这个错误,但是在实际设备上而不是模拟器上。当我们在 HTTPS(gunicorn 服务器)上访问我们的 heroku 后端时,我们注意到了这个错误,并使用大主体(超过 64Kb 的任何内容)进行 POSTS。我们使用 HTTP Basic Auth 进行身份验证,并注意到错误是通过不使用didReceiveChallenge:NSURLSession 上的委托方法解决的,而是通过将 Authentication 烘焙到原始请求头中添加Authentiation: Basic <Base64Encoded UserName:Password>. 这可以防止必要的 401 触发didReceiveChallenge:委托消息,以及随后的网络连接丢失。

于 2016-02-06T08:44:32.523 回答
3

我有同样的问题。我不知道 AFNetworking 是如何实现 https 请求的,但我的原因是 NSURLSession 的缓存问题。

在我的应用程序从 safari 跟踪回来然后发布一个 http 请求后,会出现“http load failed 1005”错误。如果我停止使用"[NSURLSession sharedSession]",而是使用可配置的 NSURLSession 实例来调用“dataTaskWithRequest:”方法,如下所示,问题就解决了。

NSURLSessionConfiguration *config = [NSURLSessionConfiguration defaultSessionConfiguration];
config.requestCachePolicy = NSURLRequestReloadIgnoringLocalCacheData;
config.URLCache = nil;
self.session = [NSURLSession sessionWithConfiguration:config];

只记得设置config.URLCache = nil;

于 2018-05-14T01:56:16.610 回答
3

我有同样的问题。解决方案很简单,我设置了HTTPBody,但没有设置HTTPMethodPOST。修复此问题后,一切都很好。

于 2016-05-06T14:26:48.540 回答
2

我必须退出 XCode,删除 DerivedData 文件夹内容(~/Library/Developer/Xcode/DerivedData 或 /Library/Developer/Xcode/DerivedData)并退出模拟器才能完成这项工作。

于 2014-09-23T08:29:44.237 回答
2

如果问题出现在设备上,请检查流量是否通过代理(设置 > Wi-Fi >(信息)> HTTP 代理)。我有我的设备设置与查尔斯一起使用,但忘记了代理。似乎没有查尔斯实际运行此错误。

于 2015-04-08T12:44:18.613 回答
2

我也有这个问题,在 iOS 8 设备上运行。这里有更多详细信息,似乎是 iOS 尝试使用已经超时的连接的情况。我的问题与该链接中解释的 Keep-Alive 问题不同,但它似乎是相同的最终结果。

每当我收到错误 -1005 时,我通过运行递归块来纠正我的问题,这使得连接最终通过,即使有时递归可以在连接工作之前循环 100 多次,但是它只增加了一秒钟的运行时间次,我敢打赌,这正是调试器为我打印 NSLog 所需的时间。

以下是我使用 AFNetworking 运行递归块的方法:将此代码添加到您的连接类文件中

// From Mike Ash's recursive block fixed-point-combinator strategy https://gist.github.com/1254684
dispatch_block_t recursiveBlockVehicle(void (^block)(dispatch_block_t recurse))
{
    // assuming ARC, so no explicit copy
    return ^{ block(recursiveBlockVehicle(block)); };
}
typedef void (^OneParameterBlock)(id parameter);
OneParameterBlock recursiveOneParameterBlockVehicle(void (^block)(OneParameterBlock recurse, id parameter))
{
    return ^(id parameter){ block(recursiveOneParameterBlockVehicle(block), parameter); };
}

然后像这样使用它:

+ (void)runOperationWithURLPath:(NSString *)urlPath
            andStringDataToSend:(NSString *)stringData
                    withTimeOut:(NSString *)timeOut
     completionBlockWithSuccess:(void (^)(AFHTTPRequestOperation *operation, id responseObject))success
                        failure:(void (^)(AFHTTPRequestOperation *operation, NSError *error))failure
{
    OneParameterBlock run = recursiveOneParameterBlockVehicle(^(OneParameterBlock recurse, id parameter) {
        // Put the request operation here that you want to keep trying
        NSNumber *offset = parameter;
        NSLog(@"--------------- Attempt number: %@ ---------------", offset);

        MyAFHTTPRequestOperation *operation =
            [[MyAFHTTPRequestOperation alloc] initWithURLPath:urlPath
            andStringDataToSend:stringData
            withTimeOut:timeOut];

        [operation setCompletionBlockWithSuccess:
            ^(AFHTTPRequestOperation *operation, id responseObject) {
                success(operation, responseObject);
            }
            failure:^(AFHTTPRequestOperation *operation2, NSError *error) {
                if (error.code == -1005) {
                    if (offset.intValue >= numberOfRetryAttempts) {
                        // Tried too many times, so fail
                        NSLog(@"Error during connection: %@",error.description);
                        failure(operation2, error);
                    } else {
                        // Failed because of an iOS bug using timed out connections, so try again
                        recurse(@(offset.intValue+1));
                    }
                } else {
                    NSLog(@"Error during connection: %@",error.description);
                    failure(operation2, error);
                }
            }];
        [[NSOperationQueue mainQueue] addOperation:operation];
    });
    run(@0);
}

您会看到我使用了一个AFHTTPRequestOperation子类,但添加了您自己的请求代码。重要的部分是调用recurse(@offset.intValue+1));以使块再次被调用。

于 2014-09-30T12:58:38.803 回答
2

当我使用 Xcode 6.2 beta 时,我在 iOS 7 设备上遇到了错误。

从 Xcode 6.2 beta 切换回 6.1.1 解决了这个问题,至少在 iOS 7 设备上是这样。

于 2015-01-06T15:02:25.210 回答
2

如果有人在将文件上传到后端服务器时遇到此错误,请确保接收服务器具有您的媒体允许的最大内容大小。就我而言,NGINX 需要更高的client_max_body_size. NGINX 会在上传完成之前拒绝该请求,因此不会返回错误代码。

于 2015-12-09T20:15:07.373 回答
1

解决了几个月的问题,终于发现当我们在我们的 api 域上禁用 DNSSEC 时,一切正常:simple_smile:

于 2015-06-04T13:01:36.337 回答
1

就我而言,这是因为我连接到 HTTP 并且它在 HTTPS 上运行

于 2019-06-26T09:04:46.477 回答
1

在将 NSURLRequest 传递给 NSURLSession而不设置请求的 HTTPMethod时,我遇到了这个错误。

NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:urlComponents.URL];

错误域=NSURLErrorDomain 代码=-1005 “网络连接丢失。”

但是,添加HTTPMethod,并且连接工作正常

NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:urlComponents.URL];
[request setHTTPMethod:@"PUT"];
于 2016-03-05T00:20:00.317 回答
1

每当出现错误 -1005 时,都需要再次调用 API。

AFHTTPRequestOperationManager *manager = 
[AFHTTPRequestOperationManager manager];
[manager setSecurityPolicy:policy];
manager.requestSerializer = [AFHTTPRequestSerializer serializer];
manager.responseSerializer = [AFHTTPResponseSerializer serializer];

[manager POST:<example-url>
   parameters:<parameteres>
    success:^(AFHTTPRequestOperation *operation, id responseObject) {
      NSLog(@“Success: %@", responseObject);
  } failure:^(AFHTTPRequestOperation *operation, NSError *error) {
      NSLog(@"Error: %@", error);
      if (error.code == -1005) {
          // Call method again... 
       }
  }];

您需要添加代码以再次调用函数。确保您调用了一次方法,否则调用递归循环。

于 2018-04-03T07:00:46.093 回答
1

我遇到了同样的问题,我启用了 Network Link Conditioner 以对应用程序进行慢速网络测试。有时会产生此错误,当我从中禁用它时Settings > Developer > Network Link Conditioner,它解决了我的问题。

在此处输入图像描述

希望这对某人有所帮助。

于 2018-05-14T19:06:06.380 回答
1

我是通过 VPN 连接的。禁用VPN解决了这个问题。

于 2015-11-30T15:15:47.853 回答
1

测试您是否可以从其他应用程序(如 safari)请求。如果不是,则可能是您计算机上的某些内容。就我而言,我遇到了 Avast Antivirus 的这个问题,它阻止了我的模拟器请求(不要问我为什么)。

于 2016-04-19T13:23:07.917 回答
1

在所有答案之上,我找到了一个不错的解决方案。实际上,iOS 12 onword 网络连接失败的问题是因为 iOS 12.0 onword 中存在错误。它尚未解决。当应用程序来自后台并尝试进行网络调用并在建立连接时失败时,我已经通过 git hub 社区解决 AFNetworking 相关问题。我在这上面花了 3 天时间,并尝试了很多事情来解决这个问题的根本原因,但一无所获。最后,当我把这个博客变红时,我在黑暗中得到了一些光明https://github.com/AFNetworking/AFNetworking/issues/4279

据说iOS 12中存在一个错误。如果应用程序操作系统不在前台,基本上你不能指望网络调用完成。由于这个错误,网络调用被丢弃,我们在日志中得到网络失败。

我对您的最佳建议是,当您的应用程序从后台转到前台并且有网络调用时,请提供一些延迟。在调度中使该网络调用具有一定的延迟。您永远不会遇到网络呼叫掉线或连接丢失的情况。

不要等待 Apple 让 iOS 12 解决这个问题,因为它还没有解决。你可以通过为你的网络请求提供一些延迟来解决这个问题,即它的 NSURLConnection、NSURLSession 或 AFNetworking 或 ALAMOFIRE。干杯:)

于 2018-11-01T12:39:24.007 回答
0

我收到此错误,还注意到应用程序 Postman 也在下降,但在应用程序 Advanced Rest Client (ARC) 中工作并在 Android 中工作。所以我不得不安装 Charles 来调试通信,我注意到响应代码是 -1。问题是 REST 程序员忘记返回响应代码 200。

我希望这可以帮助其他开发人员。

于 2017-09-18T09:00:43.920 回答
0

由于以下原因,我遇到了这个问题。

TLDR:检查您发送的GET请求是否应该在 url 而不是NSURLRequest's HTTBody属性上发送参数。

====================================================

我在我的应用程序上安装了一个网络抽象,它对我的​​所有请求都运行良好。

我向另一个 Web 服务(不是我自己的)添加了一个新请求,它开始向我抛出这个错误。

我去了一个操场,从头开始构建一个准系统请求,它奏效了。所以我开始接近我的抽象,直到找到原因。

我的抽象实现有一个错误:我正在发送一个请求,该请求应该发送在 url 中编码的参数,并且我也在NSURLRequest's HTTBody用查询参数填充属性。我一删除HTTPBody它就起作用了。

于 2016-09-20T06:39:05.900 回答
0

我的问题出在服务器上。我正在使用 Python 的BaseHTTPRequestHandler课程,但我没有在响应中发送正文。当我像下面这样放置一个空的身体时,我的问题就解决了。

def do_POST(self):
    content_len = int(self.headers.get('Content-Length'))
    post_body = self.rfile.read(content_len)
    msg_string = post_body.decode("utf-8")
    msg_json = json.loads(msg_string)
    self.send_response(200)
    self.end_headers() #this and the following lines were missing
    self.wfile.write(b'') 
于 2020-07-14T12:19:19.900 回答
0

这可能是您传递给请求正文的参数的问题。我也面临同样的问题。但是后来我在这里遇到了 CMash 的答案https://stackoverflow.com/a/34181221/5867445我更改了我的参数并且它有效。

我传递的参数中的问题是关于String Encoding.

希望这可以帮助。

于 2019-09-03T10:31:20.840 回答
0

重新启动计算机为我解决了 Xcode9.1 的问题。我已经重新启动了模拟器和 Xcode,它不起作用。

于 2017-11-08T06:18:03.763 回答
0

在使用物理设备从 iOS 12 应用程序使用我公司的服务器进行呼叫时,我遇到了同样的问题。问题是服务器硬盘已满。释放服务器空间解决了这个问题。

我在另一种情况下发现了同样的错误,我认为这是由于无法通过 Apple 提供的标准网络 API 参数化的超时(URLSession.timeoutIntervalForRequestURLSession.timeoutIntervalForResource)。即使在那里..使服务器回答更快解决了问题

于 2019-04-03T07:30:22.390 回答