[解決済み] EnumのメンバをJSONにシリアライズする
2022-06-13 10:24:13
質問
Pythonの
Enum
メンバをJSONにシリアライズして、結果のJSONをPythonオブジェクトにデシリアライズして戻すことができますか?
例えば、このようなコードです。
from enum import Enum
import json
class Status(Enum):
success = 0
json.dumps(Status.success)
の結果は、エラーになります。
TypeError: <Status.success: 0> is not JSON serializable
どうすれば回避できますか?
どのように解決するのですか?
をエンコードする場合、任意の
enum.Enum
メンバをJSONにエンコードし、それをデコードしたい場合
を同じ enum メンバとしてデコードしたい場合 (単に enum メンバの
value
属性ではなく)、カスタムの
JSONEncoder
クラスを作成し、デコード関数を
object_hook
への引数として渡すデコード関数です。
json.load()
または
json.loads()
:
PUBLIC_ENUMS = {
'Status': Status,
# ...
}
class EnumEncoder(json.JSONEncoder):
def default(self, obj):
if type(obj) in PUBLIC_ENUMS.values():
return {"__enum__": str(obj)}
return json.JSONEncoder.default(self, obj)
def as_enum(d):
if "__enum__" in d:
name, member = d["__enum__"].split(".")
return getattr(PUBLIC_ENUMS[name], member)
else:
return d
は
as_enum
関数は、JSON が
EnumEncoder
またはそれと同じ振る舞いをする何かでエンコードされていることに依存します。
のメンバーへの制限は
PUBLIC_ENUMS
は、悪意を持って細工されたテキストが、例えば、呼び出し元のコードを騙してプライベートな情報 (例えば、アプリケーションで使われる秘密鍵) を無関係のデータベースフィールドに保存させ、そこから公開されることを避けるために必要です (詳しくは
https://chat.stackoverflow.com/transcript/message/35999686#35999686
).
使用例です。
>>> data = {
... "action": "frobnicate",
... "status": Status.success
... }
>>> text = json.dumps(data, cls=EnumEncoder)
>>> text
'{"status": {"__enum__": "Status.success"}, "action": "frobnicate"}'
>>> json.loads(text, object_hook=as_enum)
{'status': <Status.success: 0>, 'action': 'frobnicate'}
関連
-
[解決済み] Java enumのメンバーを比較する:==またはequals()?
-
[解決済み] 正しいJSONコンテンツタイプは何ですか?
-
[解決済み] JSONでコメントを使用することはできますか?
-
[解決済み] なぜGoogleはJSONレスポンスにwhile(1);を前置するのでしょうか?
-
[解決済み] enumを列挙するには
-
[解決済み] intをenumにキャストするにはどうすればよいですか?
-
[解決済み] JavaScriptでJSONをきれいに印刷する
-
[解決済み] Javaで文字列値からenum値を取得する方法
-
[解決済み] Microsoft JSONの日付はどのようにフォーマットするのですか?
-
[解決済み] JSON文字列を安全にオブジェクトに変換する
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
Pythonコンテナのための組み込み汎用関数操作
-
Pythonショートビデオクローラーチュートリアル
-
Pythonの画像ファイル処理用ライブラリ「Pillow」(グラフィックの詳細)
-
[解決済み] [Solved] sklearn error ValueError: 入力に NaN、infinity または dtype('float64') に対して大きすぎる値が含まれている。
-
[解決済み】 NameError: グローバル名 'xrange' は Python 3 で定義されていません。
-
[解決済み】csv.Error:イテレータはバイトではなく文字列を返すべき
-
[解決済み】TypeErrorを取得しました。エントリを持つ子テーブルの後に親テーブルを追加しようとすると、 __init__() missing 1 required positional argument: 'on_delete'
-
[解決済み】syntaxError: 'continue' がループ内で適切に使用されていない
-
[解決済み】Pythonでgoogle APIのJSONコードを読み込むとエラーになる件
-
[解決済み】ImportError: bs4という名前のモジュールがない(BeautifulSoup)