[json] provide a custom json encoder for entities that includes eid in the json object
--- a/entity.py Fri Apr 16 19:24:53 2010 +0200
+++ b/entity.py Fri Apr 16 19:45:11 2010 +0200
@@ -269,6 +269,14 @@
return '<Entity %s %s %s at %s>' % (
self.e_schema, self.eid, self.keys(), id(self))
+ def __json_encode__(self):
+ """custom json dumps hook to dump the entity's eid
+ which is not part of dict structure itself
+ """
+ dumpable = dict(self)
+ dumpable['eid'] = self.eid
+ return dumpable
+
def __nonzero__(self):
return True
--- a/utils.py Fri Apr 16 19:24:53 2010 +0200
+++ b/utils.py Fri Apr 16 19:45:11 2010 +0200
@@ -347,6 +347,21 @@
class CubicWebJsonEncoder(JSONEncoder):
"""define a simplejson encoder to be able to encode yams std types"""
+
+ # _iterencode is the only entry point I've found to use a custom encode
+ # hook early enough: .default() is called if nothing else matched before,
+ # .iterencode() is called once on the main structure to encode and then
+ # never gets called again.
+ # For the record, our main use case is in FormValidateController with:
+ # dumps((status, args, entity), cls=CubicWebJsonEncoder)
+ # where we want all the entity attributes, including eid, to be part
+ # of the json object dumped.
+ # This would have once more been easier if Entity didn't extend dict.
+ def _iterencode(self, obj, markers=None):
+ if hasattr(obj, '__json_encode__'):
+ obj = obj.__json_encode__()
+ return JSONEncoder._iterencode(self, obj, markers)
+
def default(self, obj):
if isinstance(obj, datetime.datetime):
return obj.strftime('%Y/%m/%d %H:%M:%S')