ios - AFNetworking 离线队列
<p><p>目前我正在使用 <code>AFHTTPRequestOperationManager</code> 对一个简单的离线请求进行排队,但它似乎无法以所需的方式工作:</p>
<p>这是负责的代码,下面是不同的执行模式:</p>
<pre><code>@interface ViewController ()
{
AFHTTPRequestOperationManager *manager;
}
@end
@implementation ViewController
- (void)viewDidLoad
{
;
manager = ;
NSOperationQueue *operationQueue = manager.operationQueue;
[ startMonitoring];
[ setReachabilityStatusChangeBlock:^(AFNetworkReachabilityStatus status){
NSLog(@"Reachability: %@", AFStringFromNetworkReachabilityStatus(status));
switch (status) {
case AFNetworkReachabilityStatusReachableViaWWAN:
case AFNetworkReachabilityStatusReachableViaWiFi:
NSLog(@"Operation: %@", operationQueue.operations);
;
NSLog(@"ONLINE");
break;
case AFNetworkReachabilityStatusNotReachable:
default:
NSLog(@"Operation: %@", operationQueue.operations);
;
NSLog(@"OFFLINE");
break;
}
}];
manager.responseSerializer = ;
[manager GET:@"http://www.google.com"
parameters:nil
success:^(AFHTTPRequestOperation *operation, id response){
NSLog(@"success");
}
failure:^(AFHTTPRequestOperation *operation, NSError *failure){
NSLog(@"failure");
}];
}
</code></pre>
<p><strong>模式 1:</strong></p>
<ul>
<li>设备处于 AirPlane 模式</li>
<li>运行</li>
</ul>
<p>控制台输出:</p>
<pre><code>2015-03-21 16:03:54.486 OfflineSupport Reachability: Not Reachable
2015-03-21 16:03:54.494 OfflineSupport Operation: (
"<AFHTTPRequestOperation: 0x1701d0c20, state: isExecuting, cancelled: NO request: <NSMutableURLRequest: 0x170014ab0> { URL: http://www.google.com }, response: (null)>"
)
2015-03-21 16:03:54.494 OfflineSupport OFFLINE
2015-03-21 16:03:54.544 OfflineSupport failure
</code></pre>
<ul>
<li>Wifi 开启</li>
</ul>
<p>控制台输出续:</p>
<pre><code>2015-03-21 16:04:05.594 OfflineSupport Reachability: Reachable via WiFi
2015-03-21 16:04:05.595 OfflineSupport Operation: (
)
2015-03-21 16:04:05.595 OfflineSupport ONLINE
</code></pre>
<hr/>
<p><strong>模式 2:</strong></p>
<ul>
<li>Wifi 活跃</li>
<li>运行</li>
</ul>
<p>控制台输出:</p>
<pre><code>2015-03-21 16:05:43.818 OfflineSupport Reachability: Reachable via WiFi
2015-03-21 16:05:43.826 OfflineSupport Operation: (
"<AFHTTPRequestOperation: 0x1701dde20, state: isExecuting, cancelled: NO request: <NSMutableURLRequest: 0x17001ad10> { URL: http://www.google.com }, response: (null)>"
)
2015-03-21 16:05:43.826 OfflineSupport ONLINE
2015-03-21 16:05:43.960 OfflineSupport success
</code></pre>
<ul>
<li>AirPlane 已启用</li>
</ul>
<p>控制台输出续:</p>
<pre><code>2015-03-21 16:05:53.437 OfflineSupport Reachability: Not Reachable
2015-03-21 16:05:53.438 OfflineSupport Operation: (
)
2015-03-21 16:05:53.438 OfflineSupport OFFLINE
</code></pre>
<p>在模式 1 中,请求导致失败 block ,因为没有访问权限。但是当设备上线时,请求不再执行。我在这里缺少什么吗?我必须在操作队列或失败 block 中配置一些东西吗?</p>
<p>引用:<a href="https://stackoverflow.com/questions/21938680/afnetworking-2-0-queue-request-when-device-is-offline-with-setreachabilitystatus" rel="noreferrer noopener nofollow">AFNetworking 2.0 queue request when device is offline with setReachabilityStatusChangeBlock does nothing</a> , <a href="https://stackoverflow.com/questions/13811022/ios-best-way-to-queue-requests-to-be-sent-when-connection-is-reestablished" rel="noreferrer noopener nofollow">IOS - best way to queue requests to be sent when connection is reestablished</a> </p></p>
<br><hr><h1><strong>Best Answer-推荐答案</ strong></h1><br>
<p><p>一些观察:</p>
<ol>
<li><p>在模式 1 中,由于可达性状态 block 是异步运行的,因此存在一些竞争条件,因此如果启动可达性并立即添加操作,则状态可能尚未被识别为离线,因此队列可能尚未暂停,因此操作可能会立即开始(并且由于您处于离线状态而失败)。</p>
<p>如果在开始可达性之前和开始任何操作之前挂起队列,问题就解决了。如果您实际上处于脱机状态,则队列将保持脱机状态,并且添加的任何操作也将暂停。但是如果你真的在线,可达性 block 将被相当快地调用,并且队列将被立即解除暂停。它消除了这种竞争条件。</p></li>
<li><p>队列的<code>suspended</code> 状态不会影响已经开始的操作。仅影响那些尚未开始的操作。因此,如果在网络操作正在进行时连接脱机,则没有内置机制可以暂停操作直到连接恢复,也没有在状态更改时重新启动操作。如果您需要该功能,则必须自己实现。</p></li>
</ol>
<hr/>
<p>更多观察:</p>
<ol 开始=“3”>
<li><p>值得注意的是,仅仅因为可达性表明连接可用,它并不能保证请求会成功。您仍然需要优雅地处理失败的请求。</p></li>
<li><p>对于前面一点,如果您想要更可靠的“我可以连接到特定服务器”,您可以考虑使用 <code>managerForDomain</code> 而不是 <code>sharedManager</code>。只需确保对生成的 <code>AFNetworkReachabilityManager</code> 保持强引用,因为与单例不同,它不会对自身保持强引用。</p></li>
<li><p><code>AFHTTPRequestOperationManager</code> 来自 2.x 版,您可以考虑升级到最新版本(以便您使用 <code>AFHTTPSessionManager</code>,一个 <code>NSURLSession </code> 基于实现)。 2.x 中使用的 <code>NSURLConnection</code> 已被弃用。</p>
<p>不幸的是,<code>AFHTTPSessionManager</code> 不是基于 <code>NSOperation</code> 的。但是,如果您想享受“仅在建立连接时发送请求”功能,您可以自己将它们包装在异步 <code>NSOperation</code> 子类中(参见 <a href="https://stackoverflow.com/questions/34753816/afnetworking-3-0-afhttpsessionmanager-using-nsoperation/34755467#34755467" rel="noreferrer noopener nofollow">AFNetworking 3.0 AFHTTPSessionManager using NSOperation</a>),您可以使用后台 session (请参阅 <a href="https://stackoverflow.com/questions/21350125/afnetworking-2-0-and-background-transfers/21359684#21359684" rel="noreferrer noopener nofollow">AFNetworking 2.0 and background transfers</a> ,虽然是为 AFNetworking 2.x 编写的,但概述了使用 <code>AFHTTPSessionManager</code> 和后台 session 的基本要素,这仍然主要适用于版本 3)。</p></li>
</ol></p>
<p style="font-size: 20px;">关于ios - AFNetworking 离线队列,我们在Stack Overflow上找到一个类似的问题:
<a href="https://stackoverflow.com/questions/29187488/" rel="noreferrer noopener nofollow" style="color: red;">
https://stackoverflow.com/questions/29187488/
</a>
</p>
页:
[1]