烧瓶棉花糖JSON字段

时间:2019-03-30 22:04:32

标签: python flask marshmallow flask-restplus

我已经定义了需要数据的POST调用:

{
    "one" : "hello",
    "two" : "world",
    "three" : { 
                "abc": "123", 
                "def": false 
              }
}

为此,我能够定义onetwo,但是不确定定义three的权利是什么。 如何在Flask中指定JSON字段。我能够定义基本字段,例如:

from marshmallow import Schema, post_load, fields

class Foo(object):
    def __init__(self, one, two=None):
        self.one = one
        self.two = two

class MySchema(Schema):
    one = fields.String(required=True)
    two = fields.String()

    @post_load
    def create_foo(self, data):
        return Foo(**data)

如何在three中定义MySchema?我应该:

  1. 简单地将其作为字符串放置,并进行操作以使用json.loads()/json.dumps()将其作为json加载吗?还是有办法正确定义它?
  2. 将其定义为fields.Dict吗?
  3. 我可以为此字段定义一个单独的Schema
  4. 我应该扩展field.Field吗?

我正在查看https://marshmallow.readthedocs.io/en/3.0/api_reference.html,尽管仍不确定。 JSON子字段或嵌套JSON似乎是一个常见用例,但是我找不到与此相关的任何内容。任何帮助表示赞赏!

3 个答案:

答案 0 :(得分:2)

这可以通过嵌套模式完成:https://marshmallow.readthedocs.io/en/3.0/nesting.html

您的模式如下所示:

class MySchema(Schema):
    one = fields.String(required=True)
    two = fields.String()
    three = fields.Nested(ThreeSchema)

class ThreeSchema(Schema):
    abc = fields.String()
    def = fields.Boolean()

答案 1 :(得分:0)

您可以创建自己的字段

import json
from marshmallow import fields

class JSON(fields.Field):
    def _deserialize(self, value, attr, data, **kwargs):
        if value:
            try:
                return json.loads(value)
            except ValueError:
                return None

        return None
...
from marshmallow import fields, Schema
from schemas.base import JSON

class ObjectSchema(Schema):
    id = fields.Integer()
    data = JSON()

答案 2 :(得分:0)

如果您想在字段中支持任意嵌套值,而不是为它们定义架构,您可以使用:

  • fields.Dict()(接受任意 Python dict,或等效的任意 JSON 对象),或
  • fields.Raw()(用于任意 Python 对象,或等效的任意 JSON 值)

基于问题中的示例,您可以运行使用上述两种脚本的示例脚本:

import json
from marshmallow import Schema, fields, post_load


class Foo(object):
    def __init__(self, one, two=None, three=None, four=None):
        self.one = one
        self.two = two
        self.three = three
        self.four = four


class MySchema(Schema):
    one = fields.String(required=True)
    two = fields.String()
    three = fields.Dict()
    four = fields.Raw()

    @post_load
    def create_foo(self, data, **kwargs):
        return Foo(**data)


post_data = json.loads(
    """{
    "one" : "hello",
    "two" : "world",
    "three" : {
                "ab": "123",
                "cd": false
              },
    "four" : 567
}"""
)

foo = MySchema().load(post_data)
print(foo.one)
print(foo.two)
print(foo.three)
print(foo.four)