参考
简介
Model 描述了数据模型,通过 Python 的类实现与关系数据库的对应(即著名的 ORM — Object Relation Mapping)。通常,我们定义的每个 Model 对象都对于 一个数据库表。
- 每个 Model 都是 django.db.models.Model 的子类
- Model 对象的每个属性都是数据表中的一个区域
- 通过这些对应,Django 可以自动同数据库交互 (请参考: Making queries -- 模型数据库查询)
Quick example
假设有如下 model 定义:
from django.db import models class Person(models.Model): first_name = models.CharField(max_length=30) last_name = models.CharField(max_length=30)
first_name 和 last_name 我们称其为 model 的 "fields" 。每个 field 都作 为 class 的一个属性,每个 class 属性对应数据库表的一个字段。
上面的定义会用类似下面 SQL 创建一个数据库表:
CREATE TABLE myapp_person ( "id" serial NOT NULL PRIMARY KEY, "first_name" varchar(30) NOT NULL, "last_name" varchar(30) NOT NULL );
几点重要技术说明:
- table 的名字 — myapp_person ,会有默认赋值,可以指定。
- id field 是自动创建 primary key
- 此处的 SQL 示例解释语句时 PostgreSQL 语法。
使用 models
一旦我们在定义好了 models ,我们需要告诉 Django 才能使用。这一步在开发 过程中就是: 创建 app ,设计 models.py ,在 project 的 settings.py 文件 的 INSTALLED_APPS 里添加此 app 的加载路径,使用 ./manage.py syncdb 更新 数据库。
如果还不知道怎么使用 models ,请参考其他的文章。
当完成添加新的 apps 到 INSTALLED_APPS 的任务时,确定执行 "./manage.py syncdb" 正确。
Fields
Fields 是一个 model 最重要也是唯一必须的部分,它们表现为 Python 类的属 性(类的属性可以为所有实例共享)。 示例:
class Musician(models.Model): first_name = models.CharField(max_length=50) last_name = models.CharField(max_length=50) instrument = models.CharField(max_length=100) class Album(models.Model): artist = models.ForeignKey(Musician) name = models.CharField(max_length=100) release_date = models.DateField() num_stars = models.IntegerField()
Filed types
参考: http://docs.djangoproject.com/en/dev/ref/models/fields/#model-field-types
在 model 里的每一个 field 都应该是一个相应的 Field 类示例。 Django 使用 field 类判断一些事情:
- 数据库表的字段类型(如:INTERGER, VARCHAR)
- Django 的 Admin 可以根据 field 做些事情
- 简单的验证
Django 默认提供大约两打(24)内置的 field 类型,你也可以定义自己的 field 类型。 完整的说明列表请看: model field reference
Filed options
每个 Filed 都可以指定一些参数,例如 CharField 需要 max_length 指定 VARCHAR 的大小。
null
如果设置为 True , Django 存放一个 NULL 到数据库字段。默认为 False。
blank
如果设置为 True , 此 field 允许为 blank (空白),默认为 False。
choices
一个2元元组的元组或者列表,如果执行 choices , Django 的 admin 就会使用 选择框而不是标准的 text 框填写这个 field。
YEAR_IN_SCHOOL_CHOICES = ( (u'FR', u'Freshman'), (u'SO', u'Sophomore'), (u'JR', u'Junior'), (u'SR', u'Senior'), (u'GR', u'Graduate'), )
2元元组的第一个元素是要存入 database 的数据,第二个元素是 admin 的界面 显示的数据。
使用了 choices 参数的 field 在其 model 示例里,可以用 "get_field的名 字_display" 方法 显示 choices 的显示字串(就是2元元组的第二个数据)。示 例:
from django.db import models class Person(models.Model): GENDER_CHOICES = ( (u'M', u'Male'), (u'F', u'Female'), ) name = models.CharField(max_length=60) gender = models.CharField(max_length=2, choices=GENDER_CHOICES)
>>> p = Person(name="Fred Flinstone", gender="M") >>> p.save() >>> p.gender u'M' >>> p.get_gender_display() u'Male'
default
field 的默认值,可以使用可调用对象(a callable object),如果使用可调用 对象,那么每次创建此 model 的新对象时调用可调用对象。常见如 datatime 。
help_text
help_text 的值可以在 admin form 里显示,不过即使不使用 admin ,也可以当 做描述文档使用。
primary_key
如果为 True , 这个 field 就是此 model 的 primary key 。
unique
如果为 True, 此 field 在这个 table 里必须唯一。
Automatic primary key
默认情况下,Django 会为每个 model 添加一项:
id = models.AutoField(primary_key=True)
这是一个自动增长的 primary key。
Verbose field names
除 ForeignKey, ManyToManyField and OneToOneField 外,每个 field 类型, 都可以添加一个可选的参数 — verbose name。如果没有指定,Django 会将 filed 名字稍作转换之后使用。
first_name = models.CharField("Person's first name", max_length=30)
ForeignKey, ManyToManyField and OneToOneField 第一个参数需要指定 model 名字,所以要使用 verbose_name 关键字指定:
poll = models.ForeignKey(Poll, verbose_name="the related poll") sites = models.ManyToManyField(Site, verbose_name="list of sites") place = models.OneToOneField(Place, verbose_name="related place")
Relationships
Django 使用3中关系。
many-to-one
这个关系很好理解,比如我们用一个 User model 类描述用户,一个 Post model 类描述发表的文章。Post 类得有表明此文章是谁发表的字段吧?这就可以 用 many-to-one 关系, Django 中使用 ForeignKey 定义 many-to-one 关系:
class User(models.Model): ... class Post(models.Model): user = models.ForeignKey(User) ...
自身 many-to-one
使用 models.ForeignKey('self')
使用尚未定义的 model
对象还没有定义,就需要传递名字给 ForeignKey 。下例中, User model 对象 在 Post 之后定义,所以在 Post 中就用使用 'User' 名字(字符串), 而不是 User 对象。
class Post(models.Model): user = models.ForeignKey('User') ... class User(models.Model): ...
many-to-many
使用 ManyToManyField 定义
class Person(models.Model): name = models.CharField(max_length=128) def __unicode__(self): return self.name class Group(models.Model): name = models.CharField(max_length=128) members = models.ManyToManyField(Person, through='Membership') def __unicode__(self): return self.name class Membership(models.Model): person = models.ForeignKey(Person) group = models.ForeignKey(Group) date_joined = models.DateField() invite_reason = models.CharField(max_length=64)
Meta 嵌套类
Meta 嵌套类很有作用。
verbose_name
verbose_name 在 Admin 中的表现就是显示自定义列名(从 Admin 首页点击一个表,进去可以看到列名 )。
verbose_name_plural
verbose_name_plural 在 Admin 中的表现就是显示自定义的表名(在 Admin 首页就可以看到表名)