Django 的 auth 系统提供了一整套非常实用的 API,包括 Model、View、Template 等等。它默认是以 username
作为用户的唯一标识的。
常见的需求是换成 email
来标识用户。Django 的 文档 提供了一个例子,但缺了 View 相关的部分。Practical Django 2 and Channels 2 一书的第 3 章有一个跟官网近似,但是更完整的实现。
- Model 层:编写自定义的
User
model 及它的 manager- 对于登录的 form,它应该负责校验用户的用户名密码是否正确,并初始化 session(使用
django.contrib.auth
中的authenticate
,login
API)
- 对于登录的 form,它应该负责校验用户的用户名密码是否正确,并初始化 session(使用
- Form 层:编写相关的
Form
,基本上是重写一套类似于django.contrib.auth.forms
中的UserCreationForm
,UserChangeForm
等实现 - View 层:
- 编写注册新用户的 view,来实现展示注册页面(GET)以及处理注册请求(POST);下面有一个实际的代码
- 对于如登录、登出、修改密码等过程,可以直接用
django.contrib.auth.views
中提供的 View,如LoginView
,LogoutView
等;如果它不足够满足你的需求,比如你想在登录过程插一段你自己的逻辑,那么你可以继承它实现一个自定义的
- URL 层:加上相应的路径映射规则使得浏览器可以访问这些页面和接口;下面有一个实际的代码
- Admin:编写
UserAdmin
的定义使得 Django Admin 可以正常工具
Signup View Example
from django.contrib.auth import authenticate, login
class SignupView(FormView):
template_name = 'main/signup.html'
form_class = forms.UserCreationForm
def get_success_url(self):
redirect_to = self.request.GET.get("next", "/")
return redirect_to
def form_valid(self, form):
response = super().form_valid(form)
form.save()
email = form.cleaned_data.get("email")
raw_password = form.cleaned_data.get("password1")
logger.info(f"New signup for email {email}")
user = authenticate(email=email, password=raw_password)
login(self.request, user)
form.send_mail()
messages.info(self.request, "You signed up successfully.")
return response
URL Example
from django.contrib.auth import views as auth_views
from django.urls import path
from main import views, models, forms
urlpatterns = [
# ...
path('signup/', views.SignupView.as_view(), name="signup"),
path('login/', auth_views.LoginView.as_view(
template_name='main/login.html', form_class=forms.AuthenticationForm
), name="signup"),
]