views:

112

answers:

2

Whenever I set a body on a mutable request with the method set to anything other than POST, the body is not included in the request and I get a kCFErrorDomainCFNetwork error 303 (kCFErrorHTTPParseFailure) when the server replies. Changing the method to POST is all it takes for the request to go through with no error. Is there any way to attach a body to other methods, or are we stuck with POST for everything?

This is the submission code:

NSMutableURLRequest *req = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:assembleURL]];// cachePolicy:NSURLRequestReloadIgnoringLocalAndRemoteCacheData timeoutInterval:45.0];

#if (SERVER_TARGET_ARGS_ALLOWED==1)
[req setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
[req setValue:@"application/json" forHTTPHeaderField:@"Accept"];

[req setHTTPMethod:ServerMessageMethods[operation]];    //value is @"POST" or other method name

#endif  

//run the payload into a JSON
SBJsonWriter *json = [[SBJsonWriter alloc] init];
NSString *encodedPayload = [json stringWithObject:payload];
encodedPayload = [NSString stringWithFormat:@"%@", [encodedPayload stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding]];
NSData *dataPayload = [encodedPayload dataUsingEncoding:NSUTF8StringEncoding];
[req setHTTPBody:dataPayload];

NSURLConnection *conn = [NSURLConnection connectionWithRequest:req delegate:self];
A: 

Are you remembering to set the Content-Length/Transfer-Encoding and Content-Type headers? I don't think that Content-Length is put in automatically for you, which means the server is going to assume it's 0.

More info: http://www.w3.org/Protocols/rfc2616/rfc2616-sec9.html

Dave DeLong
Just wondering how that would explain it working for POST but not for other operations? You thinking maybe it gets set for one operation and not the other?
christophercotton
@christophercotton it might be set automatically, but i don't know; however, an undefined `Content-Length` might explain why the server never reads the body of the request.
Dave DeLong
Content-Length is not necessary if you use HTTP/1.1's chunked encoding. NSURLConnection should handle all of that transparently for you.
tc.
A: 

I tried finding more recent information about it, but there was an old post about the exact issue you were talking about: http://lists.apple.com/archives/cocoa-dev/2004/May/msg01847.html

Basically, they mention it is a bug in the code. Sadly, I wished I could find something more recent that confirms it.

The code I've been using is ASIHTTPRequest and it can definitely do PUT requests, since they use a lower level set of code to create the HTTP messages and don't rely on the NSMutableUrlRequest.

Also, I found another blog post talking about the issue and what you need to put for a PUT request. http://iphonedevelopment.blogspot.com/2008/06/http-put-and-nsmutableurlrequest.html

blog post:

When using NSMutableURLRequest to do an HTTP PUT request, add the following line of code (req is the NSMutableURLRequest):

[req setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-Type"];

That's all there is to it. If you add this line of code, your PUT requests will work just fine.

christophercotton