I am having the weirdest of the problems trying to communicate with a Django API from a iOS device and POST a NSDictionary and can't seem to make it work. Curious thing is: the same code works like a charm talking to a Ruby API.
This is my ObjC method:
- (void)makePostToServerWithClass:(NSString *)stringClass object:(NSDictionary *)parametersDict success:(void (^)(AFHTTPRequestOperation *operation, id responseObject))success failure:(void (^)(AFHTTPRequestOperation *operation, NSError *error))failure
{ [[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:YES];
AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager];
[manager setRequestSerializer:[AFJSONRequestSerializer serializer]];
[manager.requestSerializer setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
[manager.requestSerializer setValue:@"application/json" forHTTPHeaderField:@"Accept"];
manager.responseSerializer.acceptableContentTypes = [NSSet setWithObject:@"text/html"];
__block NSError *errorMessage;
NSMutableURLRequest *request = [manager.requestSerializer requestWithMethod:@"POST" URLString:[baseURLString stringByAppendingString:stringClass] parameters:parametersDict error:&errorMessage];
[request setTimeoutInterval:120];
AFHTTPRequestOperation *operation = [manager HTTPRequestOperationWithRequest:request success:^(AFHTTPRequestOperation *operation, id responseObject) {
[[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:NO];
success(operation, responseObject);
} failure:^(AFHTTPRequestOperation *operation, NSError *error) {
NSLog(@"Error: %@", operation.responseString);
NSLog(@"ERROR2: %@", errorMessage.description);
NSLog(@"ERROR3: %@", error.description);
if(operation.responseObject)
errorMessage = [self creteErrorMessageForOperation:operation error:error];
[[UIApplication sharedApplication] setNetworkActivityIndicatorVisible:NO];
failure(operation, errorMessage);
}];
[manager.operationQueue addOperation:operation];
}
In that code, the URLString would be:
@"http://linuxServerIP:8080/api/v1/create_user/"
and the parametersDict would be a NSDictionary containing:
(lldb) po parametersDict
{ "raw_password" = 1234; username = testuser; }
On the Linux server, the Django debug prints:
[28/Mar/2014 13:04:29] "GET /api/v1/create_user/ HTTP/1.1" 405 4
And the error I'm getting on iOS is:
ERROR3: Error Domain=NSCocoaErrorDomain Code=3840 "The operation couldn’t be completed. (Cocoa error 3840.)" (JSON text did not start with array or object and option to allow fragments not set.) UserInfo=0xb44e5b0 {NSDebugDescription=JSON text did not start with array or object and option to allow fragments not set., NSUnderlyingError=0xb44e860 "Request failed: method not allowed (405)"}
The most curious thing is: I'm sending a POST and the Linux server prints the error as a GET.
Do you guys have any idea what I'm doing wrong? As I said before, it works well on a Ruby API.
Just in case someone stumbles on this same problem at any time, the issue was caused because I was using a POD called RNCachingURLProtocol to cache retrieved images and HTML pages from UIWebViews. This POD, for some reason, interfered with AFNetworking not allowing it to make POST requests. Once I removed RNCachingURLProtocol, everything worked like a charm.