Reputation: 1489
I've read about CFRunLoop
but still a bit confused about it. I came a cross a piece of code that I'd like to clarify for myself:
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] init];
[request setURL:[NSURL URLWithString:[NSString stringWithFormat:url]]];
[request setHTTPMethod:@"POST"];
[request setValue:@"application/xml" forHTTPHeaderField:@"Content-Type"];
[request setValue:postLength forHTTPHeaderField:@"Content-Length"];
[request setHTTPBody:postData];
[[NSURLConnection alloc]initWithRequest:request delegate:self];
CFRunLoopRun();
So, assuming this is all being called on the main thread, will it block the main thread? Or will it spawn a new thread through the CFRunLoopRun()
function call?
Thanks!
Upvotes: 2
Views: 6143
Reputation: 25917
There is actually a case where it makes sense. While creating a recursive run loop (that's what will happen when you execute that line):
It is possible to run a run loop recursively. In other words, you can call CFRunLoopRun, CFRunLoopRunInMode, or any of the NSRunLoop methods for starting the run loop from within the handler routine of an input source or timer. When doing so, you can use any mode you want to run the nested run loop, including the mode in use by the outer run loop.
So the point is to do something like this:
- (NSMutableData *)serverRequest
{
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] init];
[request setURL:[NSURL URLWithString:[NSString stringWithFormat:url]]];
[request setHTTPMethod:@"POST"];
[request setValue:@"application/xml" forHTTPHeaderField:@"Content-Type"];
[request setValue:postLength forHTTPHeaderField:@"Content-Length"];
[request setHTTPBody:postData];
[[NSURLConnection alloc]initWithRequest:request delegate:self];
CFRunLoopRun();
return _returnDataFromServer;
}
So the method serverRequest
won't exit, until you actually stop the RunLoop:
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
// Append the new data to the instance variable you declared
[_connectionData appendData:data];
CFRunLoopStop(CFRunLoopGetCurrent());
}
I wouldn't do this, it's preferable to pass this piece of work to a working thread.There are others ways to achieve the same and not use Run Loop.
Upvotes: 9
Reputation: 53551
Assuming this is called from the main thread, there isn't really any reason to call CFRunLoopRun
, because the default run loop should already be running.
The way you're using NSURLConnection
will not block the calling thread. It may spawn additional threads internally, but you don't really have to care about that. initWithRequest:delegate:
will return pretty much immediately and your delegate methods will be called later (when a response is received, data is loaded, etc.).
Upvotes: 3