I've been working on the same project for some time now, and my understanding of Objective-C and Cocoa has evolved a little through time. Looking back in some parts of my code, I see this:
__weak ASIFormDataRequest *serverQueueRequest = [ASIFormDataRequest requestWithURL:url2];
[serverQueueRequest setCompletionBlock:^{
NSLog(@"%@", serverQueueRequest.responseString);
}];
[serverQueueRequest startAsynchronous];
And that's how I've been processing all my server requests. I think I did that to suppress a warning, namely that "capturing request in block may lead to a retain cycle". So I made it weak, and that seems to have solved all my issues. I haven't noticed any real problems with this.
However, looking at the code now, it seems a little odd that it works. When I declare the request as __weak
, shouldn't it immediately zero out since no one is holding on to it? Why does this code work?
Also, although this code works, I just recently discovered a case where it doesn't: when calling the method that contains this code several times in succession, say 5 times within the span of a second, 3/5 requests will have a NULL
response. This is consistently the case. Removing the __weak
qualifier solves this issue. What's the explanation for that?
And so finally, what is the correct way to declare a local request like this?
Update: According to this question, the correct way to do it is like so:
ASIHTTPRequest *_request = [[ASIHTTPRequest alloc] initWithURL:...
__weak ASIHTTPRequest *request = _request;
Edit: actually the fix above does not fix the issue where calling the code 5 times results in NULL responses. That problem still exists. The only way that problem goes away is by capturing the request strongly and not using any qualifiers.
Now the question is why my original code still worked..