Django继承User表实现注册和登录
django中已经有了user表,这篇文章将为大家详细讲解有关Django如何继承自带user表并重写。
一、后端部分
1、引入AbstractUser并继承
(1)、引入
from django.contrib.auth.models import AbstractUser
**(2)、继承 **
class User(AbstractUser):
phone = models.CharField(max_length=11, null=True, verbose_name="手机号")
class Meta:
db_table = "tb_user"
verbose_name = "用户表"
verbose_name_plural = verbose_name
2、在settings.py中配置
AUTH_USER_MODEL = "users.User"
3、配置app以及跨域
INSTALLED_APPS = [
'users.apps.UsersConfig', # 用户app
'corsheaders', # 跨域
]
# 中间件
MIDDLEWARE = [
'corsheaders.middleware.CorsMiddleware', # 跨域中间件
# 'django.middleware.csrf.CsrfViewMiddleware', # 注释掉CSRF这一行
]
CORS_ORIGIN_ALLOW_ALL = True # 允许所有请求
4、生成迁移文件并执行迁移
python manage.py makemigrations # 生成迁移文件
python manage.py migrate # 执行迁移文件
5、编写视图
from django.contrib.auth.hashers import make_password, check_password
from django.views import View
from django.http.response import JsonResponse
import re
from .models import User
class RegisterView(View):
"""
@author donghm
@date 2024-05-16
用户注册
"""
def post(self, request):
username = request.POST.get('username')
email = request.POST.get('email')
phone = request.POST.get('phone')
password = request.POST.get('password')
# 校验数据是否有空值
if not all([username, email, phone, password]):
return JsonResponse({'data': {}, 'message': '数据不完整,请检查数据', 'code': 0})
# 校验用户是否已存在
user_obj = User.objects.filter(username=username).first()
if user_obj:
return JsonResponse({'data': {}, 'message': '用户已存在', 'code': 0})
# 校验手机号
phone_pattern = re.compile(r'1[3-9]\d{9}$')
phone_info = phone_pattern.match(phone)
if not phone_info:
return JsonResponse({'data': {}, 'message': '手机号不正确', 'code': 0})
user = User.objects.create(
username=username,
email=email,
phone=phone,
password=make_password(password)
)
return JsonResponse({'data': {"id": user.id}, 'message': '注册成功', 'code': 1})
class LoginView(View):
"""
@author donghm
@date 2024-05-16
用户登录接口
"""
def post(self, request):
username = request.POST.get('username')
password = request.POST.get('password')
user = User.objects.filter(username=username).first()
if not user:
return JsonResponse({'data': {}, 'message': '用户不正确,请重新输入', 'code': 0})
is_correct = check_password(password, user.password)
if not is_correct:
return JsonResponse({'data': {}, 'message': '密码校验失败', 'code': 0})
if user and is_correct:
return JsonResponse({'data': {"username": username, "user_id": user.id}, 'message': 'success', 'code': 1})
6、配置路由
(1)、app下的urls.py
from django.urls import path
from . import views
urlpatterns = [
path('register/', views.RegisterView.as_view(), name='register'),
path('login/', views.LoginView.as_view(), name='login'),
]
(2)、主路由下配置
from django.urls import path, include
urlpatterns = [
path('users/', include('users.urls')),
]
默认urls.py文件是不存在的,需要进行创建。
7、使用postman对接口进行测试
(1)、注册
(2)、登录
a、登录失败
b、登录成功
8、接口文档
开发当中,接口文档还是很重要的,优雅的写好你的接口文档,有以下好处:
1、前后端联调时非常方便,前端人员可以根据请求地址、请求方式以及所需要的参数去获取,省去很多麻烦。
2、后端人员可以根据接口文档知道当前接口所要做的事情以及所需要的参数。
3、离职后交接代码也会很省心。
接口文档格式
1)、请求地址
http://127.0.0.1:8000/users/register/
2)、请求方式
post
3)、接口说明
根据所提供的参数,注册用户信息
4)、请求参数
字段 | 类型 | 是否必填 | 说明 |
---|---|---|---|
username | string | true | 要注册的用户的名称 |
password | string | true | 用户登录时的密码 |
string | true | 用户的邮箱地址 | |
phone | string | true | 用户的手机号信息 |
5)、请求示例
{
"username": "donghm",
"password": "donghm123",
"email": "donghm@163.com",
"phon3": "13311112222"
}
6)、返回结果示例
{
"data": {
"id": 1
},
"message": "注册成功",
"code": 1
}
7)、返回结果说明
字段 | 类型 | 说明 |
---|---|---|
data | object | 返回的数据 |
message | string | 返回消息说明 |
code | int | 返回编码,1表示成功,0表示失败 |
二、前端部分
1、register代码
<template>
<div style="margin: 30px auto;text-align: center; width: 400px">
<h1 style="color: #484848;">用户注册</h1>
<el-form :label-position="labelPosition" label-width="80px" :model="formRegister" >
<el-form-item label="用户名" >
<el-input v-model="formRegister.username"></el-input>
</el-form-item>
<el-form-item label="密 码">
<el-input v-model="formRegister.password" type="password"></el-input>
</el-form-item>
<el-form-item label="邮 箱">
<el-input v-model="formRegister.email"></el-input>
</el-form-item>
<el-form-item label="手机号">
<el-input v-model="formRegister.phone"></el-input>
</el-form-item>
</el-form>
<el-button type="primary" @click="register">注册</el-button>
<el-link @click="toLogin">有账号,去登录</el-link>
</div>
</template>
<script>
import axios from 'axios';
import { MessageBox, Message } from 'element-ui';
export default {
data() {
return {
labelPosition: 'right',
formRegister: {
username: '',
password: '',
email: '',
phone: ''
}
}a
},
methods: {
// 用户注册
register(){
let formData = new FormData()
formData.append('username', this.formRegister.username);
formData.append('password', this.formRegister.password);
formData.append('email', this.formRegister.email);
formData.append('phone', this.formRegister.phone);
axios({
url: 'http://127.0.0.1:8000/users/register/',
method: 'post',
data: formData,
}).then(res => {
if (res.status == 200) {
let result = res.data;
if (result.code == 1) {
Message.success(result.message);
} else {
Message.warning(result.message);
}
} else {
Message.warning(res.statusText);
}
}).catch(err => {
Message.warning(err.statusText);
})
},
// 去登录
toLogin() {
this.$router.push(
{
name: 'Login',
}
)
}
}
}
</script>
2、login代码
<template>
<div style="margin: 30px auto;text-align: center; width: 400px">
<h1 style="color: #484848;">用户登录</h1>
<el-form :label-position="labelPosition" label-width="80px" :model="formLogin" >
<el-form-item label="用户名" >
<el-input v-model="formLogin.username"></el-input>
</el-form-item>
<el-form-item label="密 码">
<el-input v-model="formLogin.password" type="password"></el-input>
</el-form-item>
</el-form>
<el-button type="primary" @click="login">登录</el-button>
<el-link @click="toRegister">没有账号,去注册</el-link>
</div>
</template>
<script>
import axios from 'axios';
import { MessageBox, Message } from 'element-ui';
export default {
data() {
return {
labelPosition: 'right',
formLogin: {
username: '',
password: ''
}
}
},
methods: {
login() {
let formData = new FormData();
formData.append('username', this.formLogin.username);
formData.append('password', this.formLogin.password);
axios({
url: 'http://127.0.0.1:8000/users/login/',
method: 'post',
data: formData
}).then(res => {
if (res.status == 200) {
let result = res.data;
if (result.code == 1) {
Message.success(result.message);
} else {
Message.warning(result.message);
}
} else {
Message.warning(res.statusText);
}
}).catch(err => {
Message.warning(err.statusText);
})
},
toRegister() {
this.$router.push({
name: 'Register'
})
}
}
}
</script>
<style>
</style>
至此,一个简单的登录注册流程就完成了,前后端全部实现,后面会继续在这个流程之上进行优化,添加上token、django的自带认证流程,让流程更加完善。