Python Django中null=True和blank=True有什么区别?

Python Django中null=True和blank=True有什么区别?,python,django,django-models,Python,Django,Django Models,在django中添加数据库字段时,我们通常会编写: models.CharField(max_length=100, null=True, blank=True) 这同样适用于外键、分码字段等。这两者的基本区别是什么 null=True仅限 blank=True仅限 null=True,blank=True 关于不同的(CharField,ForeignKey,ManyToManyField,DateTimeField)字段。使用1/2/3的优点/缺点是什么?null=True在数据库的列上设

在django中添加数据库字段时,我们通常会编写:

models.CharField(max_length=100, null=True, blank=True)
这同样适用于
外键
分码字段
等。这两者的基本区别是什么

  • null=True
    仅限
  • blank=True
    仅限
  • null=True
    blank=True

  • 关于不同的(
    CharField
    ForeignKey
    ManyToManyField
    DateTimeField
    )字段。使用1/2/3的优点/缺点是什么?

    null=True
    在数据库的列上设置
    null
    (相对于
    非null
    )。Django字段类型的空白值,如
    DateTimeField
    ForeignKey
    将作为
    NULL
    存储在数据库中

    blank
    确定表单中是否需要该字段。这包括管理员和自定义表单。如果
    blank=True
    则不需要该字段,而如果
    False
    则该字段不能为空

    这两者的组合非常频繁,因为通常,如果要允许表单中的某个字段为空,则还需要数据库为该字段允许
    NULL
    值。例外情况是
    CharField
    s和
    TextField
    s,它们在Django中永远不会保存为
    NULL
    。空白值作为空字符串存储在数据库中(
    '

    举几个例子:

    models.DateTimeField(blank=True) # raises IntegrityError if blank
    
    models.DateTimeField(null=True) # NULL allowed, but must be filled out in a form
    
    显然,使用这两个选项在逻辑上没有意义(尽管如果希望表单中始终需要一个字段,则可能存在
    null=True,blank=False的用例,但在通过类似shell的方式处理对象时是可选的)


    Django从不将
    CHAR
    TEXT
    类型保存为
    NULL
    ,因此不需要
    NULL=True
    。但是,您可以手动将其中一个字段设置为
    None
    ,以强制将其设置为
    NULL
    。如果您有一个可能需要这样做的场景,您仍然应该包括
    null=True

    这就是ORM映射Django 1.8的
    blank
    &
    null
    字段的方式

    class Test(models.Model):
        charNull        = models.CharField(max_length=10, null=True)
        charBlank       = models.CharField(max_length=10, blank=True)
        charNullBlank   = models.CharField(max_length=10, null=True, blank=True)
    
        intNull         = models.IntegerField(null=True)
        intBlank        = models.IntegerField(blank=True)
        intNullBlank    = models.IntegerField(null=True, blank=True)
    
        dateNull        = models.DateTimeField(null=True)
        dateBlank       = models.DateTimeField(blank=True)
        dateNullBlank   = models.DateTimeField(null=True, blank=True)        
    
    为PostgreSQL 9.4创建的数据库字段包括:

    CREATE TABLE Test (
      id              serial                    NOT NULL,
    
      "charNull"      character varying(10),
      "charBlank"     character varying(10)     NOT NULL,
      "charNullBlank" character varying(10),
    
      "intNull"       integer,
      "intBlank"      integer                   NOT NULL,
      "intNullBlank"  integer,
    
      "dateNull"      timestamp with time zone,
      "dateBlank"     timestamp with time zone  NOT NULL,
      "dateNullBlank" timestamp with time zone,
      CONSTRAINT Test_pkey PRIMARY KEY (id)
    )
    
    CREATE TABLE Test (
         `id`            INT(11)     NOT  NULL    AUTO_INCREMENT,
    
         `charNull`      VARCHAR(10) NULL DEFAULT NULL,
         `charBlank`     VARCHAR(10) NOT  NULL,
         `charNullBlank` VARCHAR(10) NULL DEFAULT NULL,
    
         `intNull`       INT(11)     NULL DEFAULT NULL,
         `intBlank`      INT(11)     NOT  NULL,
         `intNullBlank`  INT(11)     NULL DEFAULT NULL,
    
         `dateNull`      DATETIME    NULL DEFAULT NULL,
         `dateBlank`     DATETIME    NOT  NULL,
         `dateNullBlank` DATETIME    NULL DEFAULT NULL
    )
    
    为MySQL 5.6创建的数据库字段包括:

    CREATE TABLE Test (
      id              serial                    NOT NULL,
    
      "charNull"      character varying(10),
      "charBlank"     character varying(10)     NOT NULL,
      "charNullBlank" character varying(10),
    
      "intNull"       integer,
      "intBlank"      integer                   NOT NULL,
      "intNullBlank"  integer,
    
      "dateNull"      timestamp with time zone,
      "dateBlank"     timestamp with time zone  NOT NULL,
      "dateNullBlank" timestamp with time zone,
      CONSTRAINT Test_pkey PRIMARY KEY (id)
    )
    
    CREATE TABLE Test (
         `id`            INT(11)     NOT  NULL    AUTO_INCREMENT,
    
         `charNull`      VARCHAR(10) NULL DEFAULT NULL,
         `charBlank`     VARCHAR(10) NOT  NULL,
         `charNullBlank` VARCHAR(10) NULL DEFAULT NULL,
    
         `intNull`       INT(11)     NULL DEFAULT NULL,
         `intBlank`      INT(11)     NOT  NULL,
         `intNullBlank`  INT(11)     NULL DEFAULT NULL,
    
         `dateNull`      DATETIME    NULL DEFAULT NULL,
         `dateBlank`     DATETIME    NOT  NULL,
         `dateNullBlank` DATETIME    NULL DEFAULT NULL
    )
    

    如Django模型现场参考中所述:

    字段选项 以下参数适用于所有字段类型。所有都是可选的


    null
    Field.null


    如果
    True
    ,Django将在数据库中将空值存储为
    null
    。默认值为
    False
    。 避免对基于字符串的字段(如
    CharField
    TextField
    ,因为空字符串值将始终存储为空 字符串,而不是
    NULL
    。如果基于字符串的字段具有
    null=True
    ,则 表示它有两个可能的“无数据”值:
    NULL
    ,以及空值 一串在大多数情况下,有两个可能的值是多余的 “无数据”;Django约定使用空字符串,而不是
    NULL

    对于基于字符串和非基于字符串的字段,您还需要 要设置
    blank=True
    ,如果希望在表单中允许空值,请执行以下操作:
    null
    参数仅影响数据库存储(请参见
    blank

    注意

    在使用Oracle数据库后端时,不管该属性如何,都将存储值NULL以表示空字符串


    空白
    字段。空白


    如果
    True
    ,则该字段允许为空。默认值为
    False

    请注意,这与
    null
    不同
    null
    完全是 与数据库相关,而
    blank
    与验证相关。如果一个字段 如果
    blank=True
    ,则表单验证将允许输入空值。 如果某个字段有
    blank=False
    ,则该字段为必填字段


    简单地
    null=True
    定义数据库应接受
    null
    值,另一方面
    blank=True
    定义表单验证时此字段应接受或不接受空值(如果
    blank=True
    它接受该字段中没有值的表单,并且
    blank=False
    [默认值]表单验证时,它将显示此字段为必填项错误

    null=True/False
    与数据库相关


    与表单验证相关的
    blank=True/False

    以下是
    blank=True
    null=True

    description = models.TextField(blank=True, null= True)
    
    在这种情况下:
    blank=True
    :告诉表单可以将“描述”字段留空


    null=True
    :告诉我们的数据库,在数据库字段中记录一个null值是可以的,并且不会给出错误。

    当我们在Django admin中保存任何内容时,会在Django级别和数据库级别进行两步验证。我们不能在数字字段中保存文本

    数据库的数据类型为NULL,这算不了什么。当Django在数据库中创建列时,它会指定这些列不能为空。如果尝试保存NULL,则会出现数据库错误

    同样在Django管理层,默认情况下所有字段都是必需的,您不能保存空白字段,Django将向您抛出一个错误

    所以,若要保存空白字段,需要在Django和数据库级别上允许它。 blank=True-允许管理面板中出现空字段
    null=True-允许将null保存到数据库列。

    了解Django模型字段定义中的选项(至少)有两个用途是至关重要的:定义数据库表,以及定义默认格式和模型表单验证。(我说“默认”是因为
    blank = True
    
    date = models.DateTimeField(null=True)
    
    epic = models.ForeignKey(null=True, blank=True)
    // The exception is CharFields() and TextFields(), which in Django are never saved as NULL. Blank values a
    
    a_unique_string = models.CharField(blank=True, null=True, unique=True)
    
    +--------------------------------------------------------------------+
    | Purpose                  | null=True        | blank = True         |
    |--------------------------|------------------|----------------------|
    | Field can be empty in DB | Do this          | Unaffected           |
    |--------------------------|------------------|----------------------|
    | ModelForm(required field)| Unaffected       | field not required   |
    |--------------------------|------------------|----------------------|
    | Form Validation          | Unaffected       | field not required   |
    |--------------------------|------------------|----------------------|
    | on_delete=SET_NULL       | Need this        | Unaffected           |
    +--------------------------------------------------------------------+
    
    class Client (models.Model):
        name = models.CharField (max_length=100, blank=True)
        address = models.CharField (max_length=100, blank=False)
    
    class ClientForm (ModelForm):
        class Meta:
            model = Client
            fields = ['name', 'address']
            widgets = {
                'name': forms.TextInput (attrs = {'class': 'form-control form-control-sm'}),
                'address': forms.TextInput (attrs = {'class': 'form-control form-control-sm'})
            }
    
    class ClientForm (ModelForm):
        class Meta:
            model = Client
            fields = ['name', 'address']
    
        name = forms.CharField (
            widget = forms.TextInput (attrs = {'class': 'form-control form-control-sm'}),
        )
        address = forms.CharField (
            widget = forms.TextInput (attrs = {'class': 'form-control form-control-sm'}),
        )
    
    Blank=False # this field is required.
    Null=False # this field should not be null
    
    Blank=True # this field is optional.
    Null=True # Django uses empty string (''), not NULL.