本教程爲系列教程,爲方便閱讀,每篇教程開頭列出所有教程的目錄索引:python
Django 用戶認證系統提供了一個內置的 User 對象,用於記錄用戶的用戶名,密碼等我的信息。對於 Django 內置的 User
模型, 僅包含如下一些主要的屬性:git
對於一些網站來講,用戶可能還包含有暱稱、頭像、個性簽名等等其它屬性,所以僅僅使用 Django 內置的 User 模型是不夠。好在 Django 用戶系統遵循可拓展的設計原則,咱們能夠方便地拓展 User 模型。github
這是推薦作法。事實上,查看 User
模型的源碼就知道,User 也是繼承自 AbstractUser
抽象基類,並且僅僅就是繼承了 AbstractUser
,沒有對 AbstractUser
作任何的拓展。如下就是 User
的源碼:數據庫
class User(AbstractUser):
""" Users within the Django authentication system are represented by this model. Username, password and email are required. Other fields are optional. """
class Meta(AbstractUser.Meta):
swappable = 'AUTH_USER_MODEL'複製代碼
因此,若是咱們繼承 AbstractUser
,將得到 User
的所有特性,並且還能夠根據本身的需求進行拓展。django
咱們以前新建了一個 users 應用,一般咱們把和數據庫模型相關的代碼寫在 models.py 文件裏。打開 users/models.py 文件,寫上咱們自定義的用戶模型代碼:bash
users/models.py
from django.db import models
from django.contrib.auth.models import AbstractUser
class User(AbstractUser):
nickname = models.CharField(max_length=50, blank=True)
class Meta(AbstractUser.Meta):
pass複製代碼
咱們給自定義的用戶模型新增了一個 nickname(暱稱)屬性,用來記錄用戶的暱稱信息,設置 blank=True
的目的是讓用戶在註冊時無需填寫暱稱。根據你的需求能夠本身進一步拓展,例如增長用戶頭像、個性簽名等等,添加多少屬性字段沒有任何限制。app
同時,咱們繼承了 AbstractUser
的內部類屬性 Meta
,不過目前什麼也沒作。在這裏繼承 Meta
的緣由是在你的項目中可能須要設置一些 Meta
類的屬性值,不要忘記繼承 AbstractUser.Meta
中已有的屬性。post
注意:必定要繼承 AbstractUser
,而不是繼承 auth.User
。儘管 auth.User
繼承自 AbstractUser
且並無對其進行任何額外拓展,但 AbstractUser
是一個抽象類,而 auth.User
不是。若是你繼承了 auth.User
類,這會變成多表繼承,在目前的狀況下這種繼承方式是不被推薦的。關於 Django 的抽象模型類和多表繼承,請查閱 Django 的官方文檔 模型繼承。網站
此外,AbstractUser
類又繼承自 AbstractBaseUser
,前者在後者的基礎上拓展了一套用戶權限(Permission)系統。所以如非特殊須要,儘可能不要從 AbstractBaseUser
拓展,不然你須要作更多的額外工做。ui
爲了讓 Django 用戶認證系統使用咱們自定義的用戶模型,必須在 settings.py 裏經過 AUTH_USER_MODEL
指定自定義用戶模型所在的位置,即須要以下設置:
django_auth_example/settings.py
# 其它設置...
AUTH_USER_MODEL = 'users.User'複製代碼
即告訴 Django,使用 users 應用下的 User
用戶模型。
順便再修改一下語言設置和時區設置:
django_auth_example/settings.py
# 其它設置...
LANGUAGE_CODE = 'zh-hans'
TIME_ZONE = 'Asia/Shanghai'複製代碼
設置好自定義用戶模型後,生成數據庫遷移文件,而且遷移數據庫以生成各個應用必要的數據庫表。即運行以下兩條命令:
$ python manage.py makemigrations
$ python manage.py migrate複製代碼
OK,如今 Django 用戶系統使用的用戶模型就是自定義的 User
模型了。
注意:必定要在設置好 AUTH_USER_MODEL = 'users.User'
後在第一次遷移數據庫,即指定好自定義的用戶模型後再執行數據庫遷移命令。
若是想爲一個已使用了 Django 內置 User
模型的項目拓展用戶模型,上述繼承 AbstractUser
的拓展方式會變得有點麻煩。Django 沒有提供一套自動化的方式將內置的 User
遷移到自定義的用戶模型,由於 Django 已經爲內置的 User
模型生成了相關數據庫遷移文件和數據庫表。若是非要這麼作的話,須要手工修改遷移文件和數據庫表,而且移動數據庫中相關的用戶數據。
因此咱們採用另外一種不改動數據庫表的方式來拓展用戶模型,具體來講,咱們在建立一個模型(一般命名爲 Profile)來記錄用戶相關的數據,而後使用一對一的方式將這個 Profile 模型和 User 關聯起來,就好像每一個用戶都關聯着一張記錄我的資料的表同樣。代碼以下:
models.py
from django.contrib.auth.models import User
class Profile(models.Model):
nickname = models.CharField(max_length=50, blank=True)
user = models.OneToOneField(User)複製代碼
這種方式和 AbstractUser
的區別是,繼承 AbstractUser
的用戶模型只有一張數據庫表。而 Profile 這種模式有兩張表,一張是 User 模型對應的表,一張是 Profile 模型對應的表,兩張表經過一對一的關係關聯。可見,當要查詢某個用戶的 Profile 時,須要執行額外的跨表查詢操做,因此這種方式比起直接繼承 AbstractUser
效率更低一點。所以對於新項目來講,優先推薦使用繼承 AbstractUser
的方式來拓展用戶模型。
PS:若是你使用了Profile 模式,你可能但願在建立 User 對象的時候同時也建立與之關聯的 Profile 對象。你可使用 Django 的 Signal 實現這個需求。因爲 Profile 模式不是咱們要介紹的重點內容,所以具體的實現細節請參照相關的文檔,這裏再也不贅述。
OK,自定義的 User 模型已經創建好了,接下來就是如何建立用戶,即用戶註冊流程了。
本教程的示例項目代碼位於 GitHub:Django Auth Example。
若是遇到問題,請經過下面的方式尋求幫助。
更多 Django 相關教程,請訪問個人我的博客:追夢人物的博客。