I add this anwser as it is a mix of @mekarpeles and @hd1. I mean I did not modified the sqlalchemy hierarchy of objects, just delegating to a simple JSONEncoder:
# given that you have
Base = declarative_base()
class SqlAlchemyModelEncoder(json.JSONEncoder):
def default(self, obj):
if isinstance(obj, Base):
result = OrderedDict()
for key in obj.__mapper__.c.keys():
result[key] = getattr(obj, key)
return result
return json.JSONEncoder.default(self, obj)
If your models use not serializable classes (datetime for example) you have to add them to the Encoder :
if isinstance(obj, datetime):
return obj.isoformat()
And then I use it with a jinja2 context filter :
@contextfilter
def tojson(ctx, model, *elements, **kw):
return json.dumps(model, cls=SqlAlchemyModelEncoder)