最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Django自定義YamlField實(shí)現(xiàn)過(guò)程解析

 更新時(shí)間:2020年11月11日 10:08:26   作者:臨淵  
這篇文章主要介紹了Django自定義YamlField實(shí)現(xiàn)過(guò)程解析,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下

需求

在使用django admin時(shí)希望后臺(tái)的Textarea多行文本框可以按yaml格式編寫,數(shù)據(jù)庫(kù)保存為Text文本類型,字段和接口中讀取出來(lái)自動(dòng)變?yōu)樽值浠蛄斜砀袷健?br />

試過(guò)pip install django-yamlfied,修改支持新版django之后

接口中返回的字段是字符串形式,不符合預(yù)期。

之前寫過(guò)一版。

import yaml
from django.db import models

class YamlField(models.TextField):
  def to_python(self, value): # 將數(shù)據(jù)庫(kù)內(nèi)容轉(zhuǎn)為python對(duì)象時(shí)調(diào)用
    if not value:
      value = {}
    if isinstance(value, (list, dict)):
      return value
    return yaml.safe_load(value)

  def get_prep_value(self, value): # create時(shí)插入數(shù)據(jù), 轉(zhuǎn)為字符串存儲(chǔ)
    return value if value is None else yaml.dump(value, default_flow_style=False)

  def from_db_value(self, value, expression, connection): # 從數(shù)據(jù)庫(kù)讀取字段是調(diào)用
    return self.to_python(value)

問(wèn)題是輸入框輸入

- a
- b
- c

保存后就會(huì)變成字典的字符串形式

['a','b','c']

無(wú)法原樣保存,反復(fù)研究后,參考django-jsonfield寫了一版。

原理是,改為繼承models.Field類,(繼承models.TextField類,則formfield和value_to_string不生效)

數(shù)據(jù)庫(kù)依舊將數(shù)據(jù)庫(kù)中的yaml文本轉(zhuǎn)為dict/list,在django admin中通過(guò)自定義widget顯示為yaml字符串格式。

為了保存時(shí),驗(yàn)證表單中yaml字符串格式是否正確,還需要自定義一個(gè)form。完整代碼如下。

import django
from django.db import models
from django import forms
from django.core.exceptions import ValidationError
import yaml


class YamlWidget(forms.Textarea):
  def render(self, name, value, attrs=None, renderer=None):
    if value is None:
      value = ""
    if not isinstance(value, str):
      value = yaml.safe_dump(value, default_flow_style=False)
    if django.VERSION < (2, 0):
      return super().render(name, value, attrs)
    return super().render(name, value, attrs, renderer)


class YamlFormField(forms.CharField):
  empty_values = [None, '']

  def __init__(self, *args, **kwargs):
    if 'widget' not in kwargs:
      kwargs['widget'] = YamlWidget
    super().__init__(*args, **kwargs)

  def to_python(self, value):
    if isinstance(value, str) and value:
      try:
        return yaml.safe_load(value)
      except Exception as exc:
        raise forms.ValidationError('Yaml decode error: %s' % (exc.args[0],))
    else:
      return value

  def validate(self, value):
    if value in self.empty_values and self.required:
      raise forms.ValidationError(self.error_messages['required'], code='required')


class YamlField(models.Field):
  description = "Yaml object"

  def get_internal_type(self):
    return 'TextField'

  def formfield(self, **kwargs):
    defaults = {
      'form_class': YamlFormField,
      'widget': YamlWidget
    }
    defaults.update(**kwargs)
    return super().formfield(**defaults)

  def to_python(self, value: str): # 將數(shù)據(jù)庫(kù)內(nèi)容轉(zhuǎn)為python對(duì)象時(shí)調(diào)用
    if value is None:
      if not self.null and self.blank:
        return ""
      return None
    if isinstance(value, (list, dict)):
      return value
    value = yaml.safe_load(value)
    return value

  def validate(self, value, model_instance): # 驗(yàn)證從接受到字典格式
    if not self.null and value is None:
      raise ValidationError(self.error_messages['null'])
    try:
      self.get_prep_value(value)
    except ValueError:
      raise ValidationError(self.error_messages['invalid'] % value)

  def get_prep_value(self, value: (list, dict)): # 保存時(shí)插入數(shù)據(jù), 轉(zhuǎn)為字符串存儲(chǔ)
    if value is None:
      return None
    value = yaml.safe_dump(value, default_flow_style=False)
    return value

  def from_db_value(self, value: str, expression, connection, *args, **kwargs): # 從數(shù)據(jù)庫(kù)讀取字段是調(diào)用
    return self.to_python(value)

  def value_to_string(self, obj): # Rest Framework調(diào)用時(shí)
    return self.value_from_object(obj)

以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

  • 使用Python腳本操作MongoDB的教程

    使用Python腳本操作MongoDB的教程

    這篇文章主要介紹了使用Python腳本操作MongoDB的教程,MongoDB作為非關(guān)系型數(shù)據(jù)庫(kù)得到了很大的宣傳力度,而市面上的教程一般都是講解JavaScript的腳本操作,本文則是基于Python,需要的朋友可以參考下
    2015-04-04
  • python數(shù)據(jù)可視化之matplotlib.pyplot基礎(chǔ)以及折線圖

    python數(shù)據(jù)可視化之matplotlib.pyplot基礎(chǔ)以及折線圖

    不論是數(shù)據(jù)挖掘還是數(shù)據(jù)建模,都免不了數(shù)據(jù)可視化的問(wèn)題,對(duì)于Python來(lái)說(shuō),Matplotlib是最著名的繪圖庫(kù),它主要用于二維繪圖,這篇文章主要給大家介紹了關(guān)于python數(shù)據(jù)可視化之matplotlib.pyplot基礎(chǔ)以及折線圖的相關(guān)資料,需要的朋友可以參考下
    2021-07-07
  • python中子類調(diào)用父類函數(shù)的方法示例

    python中子類調(diào)用父類函數(shù)的方法示例

    Python中類的初始化方法是__init__(),因此父類、子類的初始化方法都是這個(gè),下面這篇文章主要給大家介紹了關(guān)于python中子類調(diào)用父類函數(shù)的方法示例,文中通過(guò)示例代碼介紹的非常詳細(xì),需要的朋友可以參考下。
    2017-08-08
  • Python中的三目(元)運(yùn)算符詳解

    Python中的三目(元)運(yùn)算符詳解

    這篇文章主要介紹了python 三元運(yùn)算符使用解析,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2021-09-09
  • python分分鐘繪制精美地圖海報(bào)

    python分分鐘繪制精美地圖海報(bào)

    基于Python中諸如matplotlib等功能豐富、自由度極高的繪圖庫(kù),我們可以完成各種極富藝術(shù)感的可視化作品,關(guān)于這一點(diǎn)我在系列文章在模仿中精進(jìn)數(shù)據(jù)可視化中已經(jīng)帶大家學(xué)習(xí)過(guò)很多案例了
    2022-02-02
  • Python的條件語(yǔ)句與運(yùn)算符優(yōu)先級(jí)詳解

    Python的條件語(yǔ)句與運(yùn)算符優(yōu)先級(jí)詳解

    這篇文章主要介紹了Python的條件語(yǔ)句與運(yùn)算符優(yōu)先級(jí),是Python入門學(xué)習(xí)中的基礎(chǔ)知識(shí),需要的朋友可以參考下
    2015-10-10
  • Django中的文件的上傳的幾種方式

    Django中的文件的上傳的幾種方式

    這篇文章主要介紹了Django中的文件的上傳的幾種方式,小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧
    2018-07-07
  • Python多進(jìn)程同步Lock、Semaphore、Event實(shí)例

    Python多進(jìn)程同步Lock、Semaphore、Event實(shí)例

    這篇文章主要介紹了Python多進(jìn)程同步Lock、Semaphore、Event實(shí)例,Lock用來(lái)避免訪問(wèn)沖突、Semaphore用來(lái)控制對(duì)共享資源的訪問(wèn)數(shù)量、Event用來(lái)實(shí)現(xiàn)進(jìn)程間同步通信,需要的朋友可以參考下
    2014-11-11
  • 詳解Open Folder as PyCharm Project怎么添加的方法

    詳解Open Folder as PyCharm Project怎么添加的方法

    這篇文章主要介紹了詳解Open Folder as PyCharm Project怎么添加的方法,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2020-12-12
  • Python+Turtle制作海龜迷宮小游戲

    Python+Turtle制作海龜迷宮小游戲

    這篇文章主要是帶大家寫一個(gè)利用Turtle庫(kù)制作的一款海龜闖關(guān)的三大迷宮,文中的示例代碼講解詳細(xì),對(duì)我們學(xué)習(xí)Python有一定幫助,感興趣的可以了解一下
    2022-04-04

最新評(píng)論

沙洋县| 绍兴县| 乌拉特前旗| 江安县| 诸暨市| 日照市| 邵东县| 乌审旗| 唐河县| 宿松县| 沙田区| 类乌齐县| 乐山市| 万源市| 潼南县| 扶余县| 邛崃市| 洛浦县| 宁安市| 合肥市| 类乌齐县| 万州区| 石景山区| 舒城县| 福贡县| 宁化县| 芜湖县| 鹰潭市| 南岸区| 民权县| 龙岩市| 徐汇区| 股票| 黄梅县| 五莲县| 崇阳县| 河南省| 江源县| 杂多县| 迭部县| 获嘉县|