I'm trying to use CFRunLoopRunInMode()
to avoid returning in [AFHTTPClient getPath:...]
completion blocks.
My code looks like:
NSLog(@"start");
__block BOOL someCondition = NO;
AFHTTPClient *client = [[AFHTTPClient alloc] initWithBaseURL:[NSURL URLWithString:@"http://domain.com"]];
[client getPath:@"my/path" parameters:nil success:^(AFHTTPRequestOperation *operation, id responseObject) {
NSLog(@"success");
} failure:^(AFHTTPRequestOperation *operation, NSError *error) {
dispatch_async(dispatch_get_main_queue(), ^{
NSLog(@"async log");
someCondition = YES;
});
while (!someCondition) {
CFRunLoopRunInMode(kCFRunLoopDefaultMode, 0.5, YES);
}
NSLog(@"failure");
}];
And I expected the output to be:
start
async log
failure
But instead I only get:
start
CFRunLoopRunInMode()
returns kCFRunLoopRunHandledSource
, but the dispatch queue never executes the submitted block. If I run the same code outside the completion blocks, the output is as expected.
I cannot figure out why the dispatch queue is not processed when run from completion blocks.
Can someone please throw some light on why this happens?
I cannot figure out why the dispatch queue is not processed when run from completion blocks.
Because you didn't "run" the dispatch queue (there is no such thing as "running" a dispatch queue). You ran the run loop. The dispatch queue is related, but is a different thing. Only one block can run at a time on a serial queue (like main). Until your block completes, no other block can be scheduled. There is no API into GCD to circumvent that. This is generally a very good thing because it gives certainty to queue operations that do not always exist on runloop operations.