It turns out this is cause by the Content-Type setting:
On the BaseHandler:
def prepare(self):
if self.request.headers.get("Content-Type") == "application/json":
self.json_args = tornado.escape.json_decode(self.request.body)
But actually in the request header:
'Content-Type': 'application/json; charset=utf-8'
This string doesn't match at all. But even after setting the Content-Type = "application/json" from the client, the string appended "; charset=utf-8" again. The only way I fixed this is change the basehandler code to:
def prepare(self):
if self.request.headers.get("Content-Type") == "application/json; charset=utf-8":
self.json_args = tornado.escape.json_decode(self.request.body)
It fixed my problem. But still, anybody know where "charset=utf-8" come from? Is it automatically set up by AFNetworking?
Thanks!
On Mar 31, 2013, at 1:38 PM, horace <
contact...@gmail.com> wrote:
> I am trying to use AFHTTPClient to connect with a tornado server(3.0). Here is my code from client:
>
> - (id)initWithBaseURL:(NSURL *)url {
> self = [super initWithBaseURL:url];
> if (!self) {
> return nil;
> }
>
>
> [self setDefaultHeader:@"User-Agent" value:@"Client"];
>
> [self setDefaultHeader:@"Accept" value:@"application/json"];
> self.parameterEncoding = AFJSONParameterEncoding;
> [self registerHTTPOperationClass:[AFJSONRequestOperation class]];
>
> On the server side, I setup the handler as bellow:
>
>
> class BaseHandler(tornado.web.RequestHandler):
> @property
> def db(self):
> return self.application.db
>
> def prepare(self):
> if self.request.headers.get("Content-Type") == "application/json":
> self.json_args = tornado.escape.json_decode(self.request.body)
>
>
> Then built a subclass of this handler:
>
>
> class TimelineHandler(BaseHandler):
> def post(self):
> user_id = self.json_args.get("user_id")
> device_id = self.json_args.get("device_id")
> token = self.json_args.get("token")
>
> //do something with the request
>
> self.write(response)
>
> But when I run this code, it failed with following ERROR message:
>
>
> HTTPRequest(protocol='http', host=<CORRECT URL HERE>, method='POST', uri='CORRECT URL HERE', version='HTTP/1.0', remote_ip='127.0.0.1', body='{"user_id":1,"device_id":"b9af8d9039ec1e527fecca70caf486e1","token":"36c9a0fe-2c4f-4273-9e12-0f855e05de87"}', headers={'Content-Length': '107', 'Accept-Language': 'en;q=1, fr;q=0.9, de;q=0.8, ja;q=0.7, nl;q=0.6, it;q=0.5', 'Accept-Encoding': 'gzip, deflate', 'X-Scheme': 'http', 'Host': 'CORRECT URL HERE', 'Accept': 'application/json', 'User-Agent': 'Client', 'Connection': 'close', 'X-Real-Ip': '58.246.153.177', **'Content-Type': 'application/json**; charset=utf-8'})
> Traceback (most recent call last):
> File "/usr/local/lib/python2.7/dist-packages/tornado/web.py", line 1077, in _execute
> *self.path_args, **self.path_kwargs)
> File "/server.py", line 128, in post
> user_id = self.json_args.get("user_id")
> **AttributeError: 'TimelineHandler' object has no attribute 'json_args'**
>
> The strange thing is, in the request header, it's clearly showing 'Content-Type': 'application/json. Then why the handler still has no attribute 'json_args'?
>
> Thanks you very much if you could give me any advice.
>
> -Horace