【问题标题】:Flatting nested field to array in Flask API在 Flask API 中将嵌套字段展平为数组
【发布时间】:2020-02-22 11:04:38
【问题描述】:

我正在使用 flask_restplus 构建 API。

我有两个模型:

model_barcode = api.model('Barcode', {
        'code': fields.String,
    })

model_product = api.model('Product', {
        'id': fields.Integer,
        'name': fields.String,
        'barcodes': fields.Nested(model_barcode, as_list=True),
    })

ProductBarcode 之间的关系是多对多的。

API 响应如下所示:

[
    {
        "id": 15707,
        "name": "Jojo Leaf Eater - White",
        "barcodes": [
            {
                "code": "6009702666853"
            },
            {
                "code": "9317118010229"
            },
            {
                "code": "6009194082315"
            },
            {
                "code": "6009149569649"
            }
        ]
    }
]

但是,由于条形码模型的内容只是一个字段,我希望它像这样编组:

[
    {
        "id": 15707,
        "name": "Jojo Leaf Eater - White",
        "barcodes": ["6009702666853", "9317118010229",
                     "6009194082315", "6009149569649"]
    }
]

我该怎么做?

我尝试将对 fields.Nested() 的调用封装在 fields.List() 中,但这没有帮助。

如果有人知道如何完成这项工作,我将非常感谢您的帮助!

谢谢。

背景信息

以下是相关的包版本:

Flask==1.1.1
flask-restplus==0.13.0
marshmallow==3.3.0
SQLAlchemy==1.3.11
simplejson==3.17.0

数据库类

以下是 SQLAlchemy 类的定义:

class Product(Base):
    __tablename__ = 'product'

    id                  = Column(Integer, primary_key=True)
    name                = Column(String(256))
    barcodes            = relationship('Barcode',
                                       secondary='product_barcode',
                                       back_populates='products')

class Barcode(Base):
    __tablename__ = 'barcode'

    id                  = Column(Integer, primary_key=True)
    code                = Column(String(15))
    products            = relationship('Product',
                                       secondary='product_barcode',
                                       back_populates='barcodes')

替代实施

我有一个使用 Marshmallow 的有效实现。

from marshmallow import Schema, fields

class BarcodeSchema(Schema):
    class Meta:
        fields = ('id', 'code',)

class ProductDetailSchema(Schema):
    barcodes = fields.Pluck(BarcodeSchema, "code", many=True)
    class Meta:
        fields = ('id', 'name', 'barcodes')
        ordered = False

这正是我想要的。不过我更喜欢使用 flask_restplus 模型,因为它们使实际 API 的代码更加简洁。

【问题讨论】:

    标签: python flask marshmallow flask-restplus


    【解决方案1】:

    你可以像这样轻松地做到这一点

    'barcodes': fields.List(fields.String, attribute=lambda p: [product.code for product in p.barcodes])
    

    【讨论】:

      猜你喜欢
      • 2013-05-16
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-03-03
      • 1970-01-01
      • 2019-01-17
      • 2015-10-29
      • 1970-01-01
      相关资源
      最近更新 更多