3

I'm trying to do an asynchronous request with ASIHTTPRequest, but have some problem getting notified when the request is done.

-(void)doDownload{
    NSURL *url = [NSURL URLWithString:@"http://www.someurl.com/?"];
    ASIFormDataRequest *request = [ASIFormDataRequest requestWithURL:url];
    [request setPostValue:@"someValue" forKey:@"someField"];
    [request setRequestMethod:@"POST"];

    [request setDelegate:self];
    [request setDidFinishSelector:@selector(requestFinished)];
    [request startAsynchronous];
}

- (void)requestFinished:(ASIHTTPRequest *)request
{
    // Use when fetching text data
    NSString *responseString = [request responseString];

}

requestFinished is never called. I get an exception in ASIHTTPRequest.m, -handleStreamCompleted:

if (fileError) {
    [self failWithError:fileError];
} else {
    [self requestFinished];   <----- this call fails
}

Any clues?

Vegar
  • 12,828
  • 16
  • 85
  • 151

3 Answers3

7

Are you sure that your class that implements - (void)requestFinished:(ASIHTTPRequest *)request is still there when the request finishes? It looks to me like the class gets deallocated too early. Note that the delegate property does not retain its content.

You could add a [self retain] to doDownload and a [self release] to - (void)requestFinished:(ASIHTTPRequest *)request, but make sure (!) that [self release] doesn't get called too often. This is also a possible memory leak if a request would never finish. It would be best to retain your class somewhere else.

You might also try to debug with NSZombieEnabled set to YES to find the error.

MrMage
  • 7,282
  • 2
  • 41
  • 71
  • This seems to be the right answer. I have a lifetime management problem that needs solving. Now, I create a download-class, call a method, and immediately release. I must implement some callback system to let the download-instance owner to know when things are done. I would need this eventually any way, to hide progress views and update data etc. Thanks. – Vegar Jan 29 '10 at 23:09
  • How can this be done when running with ARC? Please see my [topic here](http://stackoverflow.com/questions/8355974). – dhrm Dec 02 '11 at 13:20
  • Tosh. @tomute is right, the selector's name is requestFinished:, not requestFinished, that's the whole problem. No need to break your pretty little head over lifetime cycles and retains and stuff. – Elise van Looij Dec 28 '11 at 21:14
4

Following line of your code seems to be wrong.

[request setDidFinishSelector:@selector(requestFinished)];

requestFinished method has an argument (ASIHTTPRequest *).
Therefore you should add ":", when you set a selector like as follows.

[request setDidFinishSelector:@selector(requestFinished:)];
tomute
  • 2,673
  • 2
  • 20
  • 17
0

[request responseString];

Check retainCount of request before this call. Propably it equals zero :) If that - you shouldn't forget to retain it when you creates it in doDownload method.

alexandrmoroz
  • 337
  • 4
  • 12
  • I can't check requests retainCount in requestFinished, since requestFinished never get called. – Vegar Jan 29 '10 at 20:53