Wesley
Wesley

Reputation: 2200

ASIHTTPRequest crashing when setting delegate?

It will be probably a simple problem, but I have been staring on this for a while now and I can't find it!

I have a SOAPRequest class like following:

@interface SoapRequest : NSObject

@property (retain, nonatomic) NSURL *endPoint;
@property (retain, nonatomic) NSString *soapAction;
@property (retain, nonatomic) NSString *userName;
@property (retain, nonatomic) NSString *passWord;
@property (retain, nonatomic) NSString *postData;
@property (retain, nonatomic) NSObject *handler;
@property SEL action;

+ (SoapRequest*) create: (NSObject*) target endPoint: (NSString*) endPoint action: (SEL) action soapAction: (NSString*) soapAction postData: (NSString*) postData;

- (id)sendSynchronous;
- (void) send;

@end

Implementation like following:

@synthesize endPoint = _endPoint, soapAction = _soapAction, userName = _userName, passWord = _passWord, postData = _postData, action = _action, handler = _handler;

+ (SoapRequest*) create: (NSObject*) target endPoint: (NSString*) endPoint action: (SEL) action soapAction: (NSString*) soapAction postData: (NSString*) postData
{
    SoapRequest *request = [[SoapRequest alloc] init];
    request.endPoint = [NSURL URLWithString:endPoint];
    request.soapAction = soapAction;
    request.handler = target;
    request.action = action;
    request.postData = postData;

    return [request autorelease];
}

And my send function:

- (void) send
{
    ASIHTTPRequest *request = [ASIHTTPRequest requestWithURL:self.endPoint];
    [request setDelegate:self];

    [request addRequestHeader:@"Content-Length" value: [NSString stringWithFormat:@"%d",[self.postData length]]];
    [request addRequestHeader:@"Content-Type" value:@"text/xml"];

    if(self.soapAction)
    {
        [request addRequestHeader:@"soapAction" value:self.soapAction];
    }

    [request appendPostData:[self.postData dataUsingEncoding:NSUTF8StringEncoding]];
    [request startAsynchronous];
}

I do have the default ASIHTTPRequest methods to listen for error or finish, my finish looks as following:

- (void)requestFinished:(ASIHTTPRequest *)request
{
    [self.handler performSelector:self.action];
}

The case is, it crashes when I want to make this class a delegate for the ASIHTTPRequest, [request setDelegate:self]. I figured it has something to do with the Autoreleasing in the first function. But I don't have any idea how to fix it!

Edit:

This is how I init my SoapRequest:

- (SoapRequest*) DefinedEntities: (id) _target action: (SEL) _action
{

// some data inits

    SoapRequest *request = [SoapRequest create: _target endPoint:endPoint action:_action soapAction:soapAction postData:xmlString];
    [request send];

    return request;
}

And this i init as following:

Metadata *service = [[Metadata alloc] init];
[service DefinedEntities:self action:@selector(MetadataFinished:)];

Upvotes: 1

Views: 1081

Answers (4)

Wesley
Wesley

Reputation: 2200

Retaining was indeed a good option, I found some typo's in my code and figured out what i did wrong already.

I had to do with the class in-between:

- (SoapRequest*) DefinedEntities: (id) _target action: (SEL) _action
{

// some data inits

    SoapRequest *request = [SoapRequest create: _target endPoint:endPoint action:_action soapAction:soapAction postData:xmlString];
    [request send];

    return request;
}

Upvotes: 0

user207616
user207616

Reputation:

Had the same problem like you. The problem is, it gets deallocated before the delegate method gets called. Simply put a retain in your start method and a release in your finished method (and don't forget to release it in the error methods). This will let the object at life as long as the request is performing.

Upvotes: 6

jbat100
jbat100

Reputation: 16827

If the crash only occurs when you set self (SOAPRequest) as the delegate, are you sure that self isn't being deallocated (then the bad access occurs when the ASIHTTPRequest calls the did finish on its delegate which no longer exists).

- (SoapRequest*) DefinedEntities: (id) _target action: (SEL) _action
{

// some data inits

    SoapRequest *request = [SoapRequest create: _target endPoint:endPoint action:_action soapAction:soapAction postData:xmlString];
    [request send];

    return request;
}

When you do this, request is autoreleased and you should make sure it is retained by someone until the ASIHTTPRequest it sent has finished or failed.

Upvotes: 1

Alex
Alex

Reputation: 8991

Please post the code where you're creating the instance of a SOAPRequest object using:

+ (SoapRequest*) create: (NSObject*) target endPoint: (NSString*) endPoint action: (SEL) action soapAction: (NSString*) soapAction postData: (NSString*) postData;

You may need to retain it. As an aside, you should use 'id' instead of NSObject* for your target parameter, as your target will not be an instance of NSObject (it will be a subclass) of sorts.

Upvotes: 1

Related Questions