创建一个Python类,我可以将其序列化为嵌套的JSON对象

时间:2012-09-24 16:43:30

标签: python json

我是Python类和JSON的初学者,我不确定我是否正朝着正确的方向前进。

基本上,我有一个Web服务,它接受POST主体中的JSON请求,如下所示:

{ "item" : 
     {
     "thing" : "foo",
     "flag" : true,
     "language" : "en_us"
     },
   "numresults" : 3
}

我开始沿着为“item”创建类的路线:

class Item(object):
    def __init__:
        self.name = "item"

    @property
    def thing(self):
        return self.thing

    @thing.setter
    def thing(self, value):
        self.thing = value

    ...

所以,我的问题是:

  1. 我正朝着正确的方向前进吗?
  2. 如何将Python对象转换为JSON字符串?
  3. 我在python中发现了很多关于JSON的信息,我看过jsonpickle,但我似乎无法创建一个最终输出所需嵌套字典的类。

    编辑: 感谢Joran的建议,我坚持使用属性的类,并添加了这样的方法:

        def jsonify(self):
            return json.dumps({ "item" :  self.__dict__ }, indent=4)
    

    这完美无缺。

    感谢大家的帮助。

3 个答案:

答案 0 :(得分:1)

看看colander project;它让你定义一个面向对象的'schema',它可以很容易地与JSON串行化。

import colander

class Item(colander.MappingSchema):
    thing = colander.SchemaNode(colander.String(),
                                validator=colander.OneOf(['foo', 'bar']))
    flag = colander.SchemaNode(colander.Boolean())
    language = colander.SchemaNode(colander.String()
                                   validator=colander.OneOf(supported_languages)

class Items(colander.SequenceSchema):
    item = Item()

然后从JSON加载这些:

items = Items().deserialize(json.loads(jsondata))

colander为您验证数据,返回一组然后可以对其执行操作的python对象。

或者,您必须创建特定的每对象处理才能将Python对象转换为JSON结构,反之亦然。

答案 1 :(得分:0)

只需在您的类中添加一个返回字典的方法

def jsonify(self):
    return { 'Class Whatever':{
              'data1':self.data1,
               'data2':self.data2,
               ...
                               }

     }

并在结果上调用你的tojson函数...或者在你返回之前调用它只返回一个json结果......

答案 2 :(得分:0)

漏勺和字典建议都很棒。

我要补充一点,你应该退一步,决定如何使用这些物品 这种通用方法的一个潜在问题是您需要一个列表或函数或其他映射来决定导出哪些属性。 (你在漏勺定义和jsonify定义中看到了这一点。)

您可能想要这种行为 - 或者您可能不想这样做。

例如,sqlalchemy项目具有使用字段名称定义的类,例如离子漏勺等特征。 对象本身存储了许多与数据库和数据库连接相关的辅助数据。

为了获得您关心的基础字段数据,您需要访问包装数据的私有内部数据,或者查询类的映射列:

def columns_as_dict(self):
    return dict((col.name, getattr(self, col.name)) for col in sqlalchemy_orm.class_mapper(self.__class__).mapped_table.c)

我并不是要过度复杂化这一点 - 我只是想建议您考虑一下您是如何使用这些对象的。如果你只想从你放入它的对象中获得相同的信息 - 那么一个简单的解决方案就可以了。但是如果这些对象有其他类型的“私有”数据,您可能需要在不同类型的信息之间保持一些区别。