3

I'm building in tornado (cyclone, actually), and RequestHandler.write is choking on some of my objects. How do I write a JSONencoder for these objects in tornado?

One complication: some of the objects are borrowed from external libraries, so I don't really have access to their constructors.

Apologies for not posting code -- I'm just not sure how to begin here.

Abe
  • 22,738
  • 26
  • 82
  • 111

4 Answers4

3

Yes, you can change the default encoder, by adding this befor your mainloop

import json
json._default_encoder = YourJSONEncoder() #patch json
Zhuo.M
  • 466
  • 3
  • 18
2

Basically, the answer is that tornado doesn't support custom json formatting, so you have to use the json library. Here's the code I used in the end:

import json

class MongoEncoder(json.JSONEncoder):
    def default(self, obj):
        if isinstance(obj, ObjectId):
            return str(obj)
        return json.JSONEncoder.default(self, obj)

print json.dumps(my_mong_obj, cls=MongoEncoder, indent=2)
Abe
  • 22,738
  • 26
  • 82
  • 111
  • Is there a way to hook it up to be the default output for every handler in my application? – tutuca Apr 30 '13 at 18:28
  • 1
    @tutuca define it in one python class and import from that python class instead of `import json`. You also may try setting it within the handler object through inheritance. – NuclearPeon Dec 19 '17 at 20:17
1

For datetime object with json formatting it would looks like this

    import json

    dthandler = lambda obj: obj.isoformat() if isinstance(obj, datetime) else None
    response = json.dumps(data, ensure_ascii=False, default=dthandler)
Michael_XIII
  • 175
  • 1
  • 14
0

here's my monkey patch:

import json, datetime
from tornado import escape
DT_HANDLER = lambda obj: obj.isoformat() if isinstance(obj, datetime.datetime) or     isinstance(obj, datetime.date) else None
def json_encode(value):
    return json.dumps(value, default=DT_HANDLER).replace("</", "<\/")

escape.json_encode = json_encode
amohr
  • 455
  • 3
  • 10