簡體   English   中英

Django Rest Framework - 如何重組json響應?

[英]Django Rest Framework - How to restructure json response?

我正在使用Django Rest Framework(以及rest_framework_mongoengine )並覆蓋我的序列化程序的to_representation()以發回我自己的自定義JSON對象。 一切正常,但JSON字段的順序搞砸了。 請告訴我如何重新排序/重組正在發送回的JSON對象。 序列化器看起來像這樣:

class PharmacySerializer(DocumentSerializer):
    bank_account = serializers.DictField(child=serializers.CharField(), required=False)

    class Meta:
        model = Pharmacy
        fields = (
            'id', 'name', 'email', 'mobile', 'address_line_1', 'address_line_2',
            'city', 'state', 'zip', 'created_by', 'created_on', 'last_updated_by', 'license_number',
            'bank_account', 'last_updated_on', 'is_email_verified', 'is_mobile_verified', 'is_active')
        read_only_fields = ('created_by', 'created_on', 'last_updated_by', 'last_updated_on', 'is_active')

    def to_representation(self, pharmacy):
        return {
            'id': str(pharmacy.id),
            'name': pharmacy.name,
            'email': pharmacy.email,
            'mobile': pharmacy.mobile,
            'address_line_1': pharmacy.address_line_1,
            'address_line_2': pharmacy.address_line_2,
            'city': pharmacy.city,
            'state': pharmacy.state,
            'zip': pharmacy.zip,
            'created_by': pharmacy.created_by,
            'created_on': pharmacy.created_on,
            'last_updated_by': pharmacy.last_updated_by,
            'license_number': pharmacy.license_number,
            'bank_account': {
                'bank_name': pharmacy.bank_account.bank_name,
                'account_number': pharmacy.bank_account.account_number,
                'account_type': pharmacy.bank_account.account_type
            },
            'last_updated_on': pharmacy.last_updated_on,
            'is_email_verified': pharmacy.is_email_verified,
            'is_mobile_verified': pharmacy.is_mobile_verified,
            'is_active': pharmacy.is_active
        }

而我得到的回應是:

[
    {
        "city": "City",
        "name": "Some Pharmacy",
        "zip": "778372",
        "mobile": "9880082229",
        "license_number": "SP22",
        "is_mobile_verified": false,
        "is_active": true,
        "created_on": "2016-06-18T19:01:02.901",
        "created_by": null,
        "email": "somepharmacy@gmail.com",
        "state": "State",
        "last_updated_by": null,
        "is_email_verified": false,
        "last_updated_on": "2016-06-18T19:01:02.901",
        "address_line_2": null,
        "id": "57659a6ea3b6561c0f20265e",
        "bank_account": {
            "bank_name": "HSBC",
            "account_type": "Savings",
            "account_number": "663822553"
        },
        "address_line_1": "Address"
    }
]

我希望它與to_representation()的返回字典順序相同

嘗試在to_representation返回OrderedDict

def to_representation(self, pharmacy):
  return OrderedDict([('id', str(pharmacy.id),), ...])

代碼中的dict對象本質上不是有序的。 假設框架json.dump內部使用json.dump ,您可以通過使用此處建議的有序對象來保持順序。

如果要維護響應鍵的順序,可以使用OrderedDict 但是有一點你應該記住OrderedDicts

OrderedDict僅在插入密鑰時維護訂單。 使用kwargs初始化時,訂單會丟失。

來自Python文檔:

OrderedDict構造函數和update()方法都接受關鍵字參數,但它們的順序丟失,因為Python的函數使用常規無序字典調用語義傳入關鍵字參數

您需要先創建一個OrderedDict實例,然后逐個添加鍵。

from collections import OrderedDict

def to_representation(self, pharmacy):
    ret = OrderedDict() # initialize on ordereddict

    # insert keys one by one in desired oreder
    ret['id'] = str(pharmacy.id)
    ret['name'] = pharmacy.name
    ret['email'] = pharmacy.email
    ret['mobile'] = pharmacy.mobile
    ret['address_line_1'] = pharmacy.address_line_1
    ret['address_line_2'] = pharmacy.address_line_2
    ret['city'] = pharmacy.city
    ret['state'] = pharmacy.state
    ret['zip'] = pharmacy.zip
    ret['created_by'] = pharmacy.created_by
    ret['created_on'] = pharmacy.created_on
    ret['last_updated_by'] = pharmacy.last_updated_by
    ret['license_number'] = pharmacy.license_number
    ret['bank_account'] = {
        'bank_name' = pharmacy.bank_account.bank_name
        'account_number' = pharmacy.bank_account.account_number
        'account_type' = pharmacy.bank_account.account_type
    }
    ret['last_updated_on'] = pharmacy.last_updated_on
    ret['is_email_verified'] = pharmacy.is_email_verified
    ret['is_mobile_verified'] = pharmacy.is_mobile_verified
    ret['is_active'] = pharmacy.is_active

    return ret

注意:另一個選項(推薦)是使用EmbeddedDocumentSerializer for bank_account字段。 然后,您將不需要覆蓋to_representation()方法。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM