Django 再談一談json序列化

2022-09-28 18:57:09 字數 3366 閱讀 7360

我們知道json字串是目前流行的資料交換格式,在pyhton中我們通過json模組,將常用的資料型別轉化為json字串。但是,json支援轉化的資料型別是有限的。

比如,我們通過orm從資料庫查詢出的結果,試圖通過json序列化:

報錯,queryset不是json能序列化的物件。那麼有什麼辦法可以解決呢?

注意,如果是通過values查詢,如userinfo.objects.values("name"),查詢出來的結果雖然也是queryset物件,但是其結構是這樣的:, 類似於列表套字典的結構。對於這種情況,我們可以通過list()方法將querys程式設計客棧et 物件轉化為列表,這樣就可以直接用json.dumps()進行序列化了。

方法一:serializers

將返回的結果放到bejson校驗結果如下:

[ },

}]注:pk代表主鍵(可以是預設的id主鍵字段,也可以是使用者自定義的主鍵字段)

觀察序列化結果,發現這種方式將服務端資料庫的表名都暴露了;另外serializers不支援連表序列化,只能拿到另一張表的id。下面我們我們用一種新的方式。

方法二:自定義json處理器

檢視json.dumps原始碼,發現序列化時,用到了乙個引數cls = jsonencoder,我們可以繼承它,自定義乙個類,重寫它的default方法,來處理我們需要的資料型別。比如自定義對時間物件進行轉化:

import json

from datetime import date

from datetime import datetime

class jsoncustomencoder(json.jsonencoder):

def default(self, field):

if isinstance(field, datetime):

return field.strftime('%y-%m-%d %h:%m:%s')

elif isinstance(field, date):

return field.strftime('%y-%m-%d')

else:

return json.jsonencoder.default(self, field)

下面我們試著序列化乙個datetime物件:

再次訪問

補充知識:django orm物件json序列化問題

碰到了乙個問題:在使用json.dumps()序列化django orm的queryset物件,傳遞給前端的時候,程式報錯:

object of type 'queryset' is not json serializable

在python 中,常用的json 的序列化是從******json 基礎上改變而來。這個json 包主要提供了dump,load 來實現dict 與 字串之間的序列化與反序列化,這很方便的可以完成,但現在的問題是,這個json包不能序列化 django 的models 裡面的物件的例項。

經過一番度娘搜尋,發現有如下解決方案:

使用django.core自帶的serializers模組:

#djang orm的 queryset物件預設無法被直接json.dumps()序列化,django.core提供的serializers模組提供將其序列化成str型別

#的功能,serializers處理後,再次json.dumps傳給前端,前端需要經過兩次json.parse()處理,才能得到原物件型別,但是格式發

#生了變化,需要按新的方式取索引.例如:obj['pk']取主鍵,obj['fields']["caption"]取obj的caption欄位

由queryset:

變為了:

[}]這樣前端就可以正常獲取資料了,只不過此欄位需要兩次json.parse()處理。

至於使用models.host.objects.get(id=xx)的方式獲取到單個物件,而非queryset物件,serializers預設也無法處理的問題,可以自定義json方法來實現dumps序列化

json預設只支援python原生的list、tuple、dict資料型別物件的序列化,www.cppcns.com若需要擴充套件其他型別物件的序列化功能,可以這樣修改:

import json as default_json

from json.encoder import jsonencoder

class baseresponse(object):

def __init__(self):

self.status = true

self.message = none

self.data = none

self.error = none

o=baseresponse()

class jsoncustomencoder(jsonencoder):

def default(self, o):

if isinstance(o, baseresponse):

return o.__dict__

return jsonencoder.default(self, o)

o1=json.dumps(o,cls=jsoncustomencoder)

>>> print(o1)

>>> print(type(o1))

#在序列化時指定cls引數,cls=自定義的序列化類,在自定義序列化類的default方法中判斷,如果是指定的類的例項的話,則將該類轉換成dict格式返回,若指定類的例項,則使用json模組預設的序列化方法。最終得到的return值為str型別。

本文標題: django 再談一談json序列化

本文位址:

談一談教育

今晚和研究生的師兄聊了會天,突然就說到教育的問題,有點感想,就寫下來,算是我對中國教育的一點看法吧。毫無疑問,中國的教育體制存在不少問題。在高中的時候或許還不是那麼明顯 對比起大學來說 上了大學,我才看清了我們教育的一些弊端。我覺得,最大的弊端,在於價值觀的引導問題上。不知道大家有沒和我一樣覺得當今...

談一談裁員

資本寒冬,經濟不景氣,要保持公司運作,可能會涉及到裁員。另外,有些員工的價值觀已經與公司不符,再留用可能會影響團隊和公司的和諧,此時也可能會涉及到裁員。裁員,不是說想裁就能裁的,需要考慮幾個方面 為什麼要裁?是否可以不裁?裁員是否會影響業務程序?裁員是否會付出經濟代價 賠償 裁員是否會負一定的法律責...

C 談一談this指標

當你進入乙個 房子 後,你可以看見桌子 椅子 地板等,但是房子你是看不到全貌了。對於乙個類的例項來說,你可以看到它的 成員函式 成員變數 但是例項本身呢?this是乙個 指標 它時時刻刻指向你這個 例項 本身class date void printdate 結果如下 進過反彙編,我們知道了 ecx...