day 75天 bbs 项目第一天 ,auth登陆
from django.db import models from django.contrib.auth.models import AbstractUser class UserInfo(AbstractUser):
'''
用户表
'''
nid =models.AutoField(primary_key=True)
phone =models.CharField(max_length=11,null=True,unique=True)
avatar = models.FileField(upload_to='avatars/',default='avatars/default.png',verbose_name='头像')
create_time =models.DateTimeField(auto_now_add=True)
blog =models.OneToOneField(to='Blog',to_field='nid',null=True)
def __str__(self):
return self.username class Blog(models.Model):
'''
博客信息
'''
nid =models.AutoField(primary_key=True)
title =models.CharField(max_length=64)
site =models.CharField(max_length=32,unique=True)
theme =models.CharField(max_length=32) def __str__(self):
return self.title class Category(models.Model):
'''
个人博客文章分类
'''
nid =models.AutoField(primary_key=True)
title =models.CharField(max_length=32)#分类标题
blog = models.ForeignKey(to ='Blog',to_field='nid')#外键关联博客,一个博客站点可以有多个分类 def __str__(self):
return self.title class Tag(models.Model):
''''
标签
'''
nid =models.AutoField(primary_key=True)
title =models.CharField(max_length=32)
blog =models.ForeignKey(to='Blog',to_field='nid') #所属博客 def __str__(self):
return self.title class Article(models.Model):
'''
文章
'''
nid =models.AutoField(primary_key=True)
title = models.CharField(max_length=50) #文章标题描述
desc =models.CharField(max_length=255) #文章描述
create_time =models.DateTimeField()#创建时间 category = models.ForeignKey(to ='Category',to_field='nid',null=True)
user = models.ForeignKey(to='UserInfo',to_field='nid')
tags =models.ManyToManyField( # 中介模型
to ='Tag',
through='Article2Tag',
through_fields=('article','tag')#注意顺序 ) def __str__(self):
return self.title class ArticleDetail(models.Model):
'''
文章详情
'''
nid =models.AutoField(primary_key=True)
content = models.TextField()
article =models.OneToOneField(to ='Article',to_field='nid') class Article2Tag(models.Model):
'''
文章和标签的多对多关系表
'''
nid =models.AutoField(primary_key=True)
article =models.ForeignKey(to='Article',to_field='nid')
tag =models.ForeignKey(to ='Tag',to_field='nid') class Meta:
unique_together = (('article','tag'),) class ArticleUpDown(models.Model):
'''
点赞
'''
nid= models.AutoField(primary_key=True)
user =models.ForeignKey(to ='UserInfo',null=True)
artcle = models.BooleanField(default=True) class Meta:
unique_together = (('article','user'),) class Comment(models.Model):
'''
评论表
'''
nid = models.AutoField(primary_key=True)
article =models.ForeignKey(to ='Article',to_field='nid')
user =models.ForeignKey(to ='UserInfo',to_field='nid')
content =models.CharField(max_length=255)#评论内容
create_time =models.DateTimeField(auto_now_add=True)
parent_comment =models.ForeignKey('self',null=True) def __str__(self):
return self.content
settings 里配置
# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/1.11/howto/static-files/ STATIC_URL = '/static/'
STATICFILES_DIRS=[
os.path.join(BASE_DIR,'static')
] # 告诉Djanog 项目用哪张表做认证
AUTH_USER_MODEL='app01.UserInfo'
# Database
# https://docs.djangoproject.com/en/1.11/ref/settings/#databases DATABASES = {
# 'default': {
# 'ENGINE': 'django.db.backends.sqlite3',
# 'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
# }, 'default':{
'ENGINE':'django.db.backends.mysql',
'NAME':'day77',
'USER':'root',
'PASSWORD':'',
'HOST':'127.0.0.1',
'PORT':, }
}
init配置文件
import pymysql
pymysql.install_as_MySQLdb()
登录配置
from app01 import views urlpatterns = [
url(r'^admin/', admin.site.urls),
url(r'^login/',views.login)
]
login登陆页面
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>欢迎登陆</title>
<link rel="stylesheet" href="/static/bootstrap/css/bootstrap.min.css">
<link rel="stylesheet" href="/static/mystyle.css">
#导入bootstrap
</head>
<body> <div class="container">
<div class="row">
<form class="form-horizontal col-md-6 col-md-offset-3 login-form" >
{% csrf_token %} 登陆界面的csrf token校验
<div class="form-group" >
<label for="inputEmail3" class="col-sm-2 control-label">用户名:</label>
<div class="col-sm-10">
<input type="text" class="form-control" id="username" name="username" placeholder="用户名">
</div>
</div>
<div class="form-group">
<label for="password" class="col-sm-2 control-label">密码</label>
<div class="col-sm-10">
<input type="password" class="form-control" id="password" name="password" placeholder="密码">
</div>
</div>
{# <div class="form-group">#}
{# <div class="col-sm-offset-2 col-sm-10">#}
{# <div class="checkbox">#}
{# <label>#}
{# <input type="checkbox"> 记住密码#}
{# </label>#}
{# </div>#}
{# </div>#}
{# </div>#}
<div class="form-group">
<div class="col-sm-offset-2 col-sm-10">
<button type='button' class="btn btn-default" id="login-button">登陆</button>
<span class="login-error"></span>
</div>
</div>
</form>
</div>
</div> <script src="/static/jquery-3.3.1.js"></script>
<script src="/static/bootstrap/js/bootstrap.min.js"></script>
<script>
$('#login-button').click(function(){
// 1.取到用户填写的用户名和密码:-->取input框的值
var username = $('#username').val();
var password =$('#password').val();
//2. 用AJAX 发送到服务器端.
$.ajax({
url:'/login/',
type:'post',
data:{ 'username':username,
'password': password ,
'csrfmiddlewaretoken': $("[name='csrfmiddlewaretoken']").val()
},
success:function (data) {
console.log(data);
if (data.status){
//有错误,在页面中提示
$(".login-error").text(data.msg)
}else {
//登陆成功
location.href = data.msg
} }
}) })
})
//当input框获取焦点时将之前的错误信息清空
$("#username,#password") .focus(function () {
//将之前的内容清空
$('.login-error').text('');
})
</script>
</body>
</html>
views文件
from django.shortcuts import render,redirect,HttpResponse
from django.http import JsonResponse
from django.contrib import auth # Create your views here. def login(request):
# if request.is_ajax():
if request.method =='POST':
print(request.POST) #初始化一个给ajax返回的数据
ret ={'status':0,'msg':''}
#从提交过来的数据中取到用户名和密码
username =request.POST.get('username')
pwd =request.POST.get('password')
#利用auth模块进行验证 导入auth模块
user = auth.authenticate(username=username, password =pwd)
if user:
#用户名密码正确 ,登陆成功.
#给用户做登陆
auth.login(request,user)
ret['msg']='/index/'
return JsonResponse(ret)
#跳转到index 界面
else:
#用户名密码错误,
ret['status'] =1
ret['msg']='用户名或密码错误'
return JsonResponse(ret)
return render(request,'login.html'
) def index(request):
return HttpResponse('ok')
二、生成验证码图片
验证码:
1. 验证码要随机生成
1.如何自己生成一个图片
2. PIL Pillow
views 文件配置
#获取验证码图片的视图
def get_valid_img(request):
with open( 'valid_code.png','rb') as f :
data =f.read()
#自己生成一个图片
from PIL import Image,ImageDraw,ImageFont
import random #获取随机颜色的函数
def get_random_color():
return random.randint(0,255),\
random.randint(0, 255),\
random.randint(0, 255), #生成一个图片对象
img_obj = Image.new(
'RGB',
(220,35),
get_random_color()
)
#在生成的图片上写字符
#生成一个画笔对象
draw_obj =ImageDraw.Draw(img_obj)
#加载字体文件,得到一个字体对象
font_obj = ImageFont.truetype("static/font/kumo.ttf",28)
#循环五次添加随机字符
valid_code_tmp =[]
for i in range(5):
n =str(random.randint(0,9))
l=chr(random.randint(97,122))
u=chr(random.randint(65,90))
tmp = random.choice([n,l,u])
valid_code_tmp.append(tmp)
draw_obj.text((20+40*i,0),tmp,fill=get_random_color(),font =font_obj)
#将生成的图片保存在磁盘上.
# with open( 's10.png','wb') as f :
# img_obj.save(f,"png")
# #把刚才生成的图片返回给页面
# with open('s10.png','rb')as f :
# data =f.read() #不需要在硬盘上保存文件,直接在内存中加载就可以
from io import BytesIO
io_obj =BytesIO()
#将生成的图片数据保存在io对象中
img_obj.save(io_obj,'png')
#从io对象里面取上一步保存的数据
data =io_obj.getvalue()
return HttpResponse(data)
Login登陆页面配置
<div class="form-group">
<label for="password" class="col-sm-2 control-label">密码</label>
<div class="col-sm-10">
<input type="password" class="form-control" id="password" name="password" placeholder="密码">
</div>
</div> <div class="form-group">
<label for="password" class="col-sm-2 control-label">验证码</label>
<div class="col-sm-10">
<input type="text" name="valid_code" >
<img class="valid-img" src="/get_valid_img/" alt="">
</div>
</div> <div class="form-group">
<div class="col-sm-offset-2 col-sm-10">
<button type='button' class="btn btn-default" id="login-button">登陆</button>
<span class="login-error"></span>
</div>
</div>
老师写的登录view文件
from django.shortcuts import render, redirect, HttpResponse
from django.http import JsonResponse
from django.contrib import auth
# Create your views here. # VALID_CODE = "" def login(request):
# if request.is_ajax(): # 如果是AJAX请求
if request.method == "POST":
# 初始化一个给AJAX返回的数据
ret = {"status": , "msg": ""}
# 从提交过来的数据中 取到用户名和密码
username = request.POST.get("username")
pwd = request.POST.get("password")
valid_code = request.POST.get("valid_code") # 获取用户填写的验证码
print(valid_code)
print("用户输入的验证码".center(, "="))
if valid_code and valid_code.upper() == request.session.get("valid_code", "").upper():
# 验证码正确
# 利用auth模块做用户名和密码的校验
user = auth.authenticate(username=username, password=pwd)
if user:
# 用户名密码正确
# 给用户做登录
auth.login(request, user)
ret["msg"] = "/index/"
else:
# 用户名密码错误
ret["status"] =
ret["msg"] = "用户名或密码错误!"
else:
ret["status"] =
ret["msg"] = "验证码错误" return JsonResponse(ret)
return render(request, "login.html") def index(request):
return render(request, "index.html") # 获取验证码图片的视图
def get_valid_img(request):
# with open("valid_code.png", "rb") as f:
# data = f.read()
# 自己生成一个图片
from PIL import Image, ImageDraw, ImageFont
import random # 获取随机颜色的函数
def get_random_color():
return random.randint(, ), random.randint(, ), random.randint(, ) # 生成一个图片对象
img_obj = Image.new(
'RGB',
(, ),
get_random_color()
)
# 在生成的图片上写字符
# 生成一个图片画笔对象
draw_obj = ImageDraw.Draw(img_obj)
# 加载字体文件, 得到一个字体对象
font_obj = ImageFont.truetype("static/font/kumo.ttf", )
# 开始生成随机字符串并且写到图片上
tmp_list = []
for i in range():
u = chr(random.randint(, )) # 生成大写字母
l = chr(random.randint(, )) # 生成小写字母
n = str(random.randint(, )) # 生成数字,注意要转换成字符串类型 tmp = random.choice([u, l, n])
tmp_list.append(tmp)
draw_obj.text((+*i, ), tmp, fill=get_random_color(), font=font_obj) print("".join(tmp_list))
print("生成的验证码".center(, "="))
# 不能保存到全局变量
# global VALID_CODE
# VALID_CODE = "".join(tmp_list) # 保存到session
request.session["valid_code"] = "".join(tmp_list)
# 加干扰线
# width = # 图片宽度(防止越界)
# height =
# for i in range():
# x1 = random.randint(, width)
# x2 = random.randint(, width)
# y1 = random.randint(, height)
# y2 = random.randint(, height)
# draw_obj.line((x1, y1, x2, y2), fill=get_random_color())
#
# # 加干扰点
# for i in range():
# draw_obj.point((random.randint(, width), random.randint(, height)), fill=get_random_color())
# x = random.randint(, width)
# y = random.randint(, height)
# draw_obj.arc((x, y, x+, y+), , , fill=get_random_color()) # 将生成的图片保存在磁盘上
# with open("s10.png", "wb") as f:
# img_obj.save(f, "png")
# # 把刚才生成的图片返回给页面
# with open("s10.png", "rb") as f:
# data = f.read() # 不需要在硬盘上保存文件,直接在内存中加载就可以
from io import BytesIO
io_obj = BytesIO()
# 将生成的图片数据保存在io对象中
img_obj.save(io_obj, "png")
# 从io对象里面取上一步保存的数据
data = io_obj.getvalue()
return HttpResponse(data)
自己写的整个登录界面
from django.shortcuts import render,redirect,HttpResponse
from django.http import JsonResponse
from django.contrib import auth # Create your views here.
VALID_CODE=''
def login(request):
# if request.is_ajax():
if request.method =='POST':
print(request.POST)
#初始化一个给ajax返回的数据
ret ={'status':0,'msg':''}
#从提交过来的数据中取到用户名和密码
username =request.POST.get('username')
pwd =request.POST.get('password')
valid_code = request.POST.get('valid_code')#获取用户填写的验证码
print(valid_code)
print('用户输入的验证码'.center(120,'='))
if valid_code.upper() ==request.session["valid_code"].upper():
#利用auth模块进行验证 导入auth模块
user = auth.authenticate(username=username, password =pwd)
if user:
#用户名密码正确 ,登陆成功.
#给用户做登陆
auth.login(request,user)
ret['msg']='/index/'
return JsonResponse(ret)
#跳转到index 界面
else:
#用户名密码错误,
ret['status'] =1
ret['msg']='用户名或密码错误'
return JsonResponse(ret)
return render(request,'login.html'
) def index(request):
return HttpResponse('ok') #获取验证码图片的视图
def get_valid_img(request):
with open( 'valid_code.png','rb') as f :
data =f.read()
#自己生成一个图片
from PIL import Image,ImageDraw,ImageFont
import random #获取随机颜色的函数
def get_random_color():
return random.randint(0,255),\
random.randint(0, 255),\
random.randint(0, 255), #生成一个图片对象
img_obj = Image.new\
(
'RGB',
(220,35),
get_random_color()
)
#在生成的图片上写字符
#生成一个画笔对象
draw_obj =ImageDraw.Draw(img_obj)
#加载字体文件,得到一个字体对象
font_obj = ImageFont.truetype("static/font/kumo.ttf",28)
#循环五次添加随机字符
valid_code_tmp =[]
for i in range(5):
n =str(random.randint(0,9))
l=chr(random.randint(97,122))
u=chr(random.randint(65,90))
tmp = random.choice([n,l,u])
valid_code_tmp.append(tmp)
draw_obj.text((20+40*i,0),tmp,fill=get_random_color(),font =font_obj) print("".join(valid_code_tmp))
print("生成的验证码".center(120, "="))
# 不能保存到全局变量
# global VALID_CODE
# VALID_CODE = "".join(tmp_list)
# 保存到session
request.session["valid_code"] = "".join(valid_code_tmp) #将生成的图片保存在磁盘上.
# with open( 's10.png','wb') as f :
# img_obj.save(f,"png")
# #把刚才生成的图片返回给页面
# with open('s10.png','rb')as f :
# data =f.read() #不需要在硬盘上保存文件,直接在内存中加载就可以
from io import BytesIO
io_obj =BytesIO()
#将生成的图片数据保存在io对象中
img_obj.save(io_obj,'png')
#从io对象里面取上一步保存的数据
data =io_obj.getvalue()
return HttpResponse(data)
前端登录
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>欢迎登陆</title>
<link rel="stylesheet" href="/static/bootstrap/css/bootstrap.min.css">
<link rel="stylesheet" href="/static/mystyle.css">
#导入bootstrap
</head>
<body> <div class="container">
<div class="row">
<form class="form-horizontal col-md-6 col-md-offset-3 login-form" >
{% csrf_token %}
<div class="form-group" >
<label for="inputEmail3" class="col-sm-2 control-label">用户名:</label>
<div class="col-sm-10">
<input type="text" class="form-control" id="username" name="username" placeholder="用户名">
</div>
</div>
<div class="form-group">
<label for="password" class="col-sm-2 control-label">密码</label>
<div class="col-sm-10">
<input type="password" class="form-control" id="password" name="password" placeholder="密码">
</div>
</div> <div class="form-group">
<label for="password" class="col-sm-2 control-label">验证码</label>
<div class="col-sm-10">
<input type="text" name="valid_code" id="valid_code" >
<img class="valid-img" src="/get_valid_img/" alt="">
</div>
</div> <div class="form-group">
<div class="col-sm-offset-2 col-sm-10">
<button type='button' class="btn btn-default" id="login-button">登陆</button>
<span class="login-error"></span>
</div>
</div>
</form>
</div>
</div> <script src="/static/jquery-3.3.1.js"></script>
<script src="/static/bootstrap/js/bootstrap.min.js"></script> <script>
$('#login-button').click(function(){
// 1.取到用户填写的用户名和密码:-->取input框的值
var username = $('#username').val();
var password =$('#password').val();
var valid_code=$('#valid_code').val();
//2. 用AJAX 发送到服务器端.
$.ajax({
url:'/login/',
type:'post',
data:{ 'username':username,
'password': password ,
'valid_code':valid_code,
'csrfmiddlewaretoken': $("[name='csrfmiddlewaretoken']").val()
},
success:function (data) {
console.log(data);
if (data.status){
//有错误,在页面中提示
$(".login-error").text(data.msg)
}else {
//登陆成功
location.href = data.msg
} }
}) })
//当input框获取焦点时将之前的错误信息清空
$("#username,#password") .focus(function () {
//将之前的内容清空
$('.login-error').text('');
}) </script> </body>
</html>
day 75天 bbs 项目第一天 ,auth登陆的更多相关文章
- auth复习和BBS项目的登录(1)
auth复习 auth组件 验证:authenticate(request,username='andy',password='123) 登录:login(request,user) 注销:login ...
- python 自动化之路 day 20 Django进阶/BBS项目【一】
一.django进阶 1.django orm 增删改查 1.1.创建表: 1 2 3 >>> from blog.models import Blog >>> b ...
- BBS项目(二)
目录 BBS项目(二) ORM 创建相关表 表模型 修改admin样式 Simple-UI 注册表添加数据 注册forms类编写 注册功能前端搭建 头像实时显示功能实现 BBS项目(二) 可以在本地写 ...
- BBS项目详解(forms快速创建登陆页面,登陆验证、通过阅读器进行头像上传的预览、内存管理器)
BBS项目涉及的知识点 django中知识点 钩子函数(局部钩子和全局钩子) 1.局部钩子就是用来做合法性校验,比如用户名有没有被使用等 2.全局的就是用来做对比校验,比如两次输入的密码是否一致 3. ...
- BBS项目知识点汇总
目录 bbs项目知识点汇总 一. JavaScript 1 替换头像 2 form表单拿数据 3 form组件error信息渲染 4 添加html代码 5 聚焦操作 二 . html在线编辑器 三 . ...
- BBS项目-01
目录 BBS项目 BBS开发流程: BBS表格创建: BBS项目 BBS开发流程: BBS项目: 开发流程: 需求分析 草拟一些项目的大致技术点和流程 架构设计 架构师(框架 语言 数据库 缓存数据库 ...
- 小福bbs——项目需求分析
# 一.简单了解 这个作业属于哪个课程 班级链接 这个作业要求在哪里 作业要求的链接 团队名称 小福bbs 这个作业的目标 第一个版本,根据项目预期情况形成 作业的正文 小福bbs--项目需求分析 其 ...
- nginx之location、inmp架构详解、BBS项目部署
本期内容概要 location lnmp架构 部署BBS项目 内容详细 1.location 使用Nginx Location可以控制访问网站的路径 但一个server可以有多个location配置 ...
- BBS项目(一)
目录 BBS项目(一) 项目开发流程 BBS项目 BBS表分析 自关联 表关系图示 BBS项目(一) 项目开发流程 项目分类 针对互联网用户:抖音,淘宝····· 针对公司内部:后台管理系统··· 针 ...
随机推荐
- 配置Spring框架编写XML的提示
1. 步骤一:先复制, http://www.springframework.org/schema/beans/spring-beans.xsd 2. 步骤二:搜索XML Catalog,点击Add按 ...
- Castle ActiveRecord学习(二)配置、引用、程序启动
来源:http://www.cnblogs.com/zxj159/p/4082987.html 配置数据库驱动: Model层引用:Castle.ActiveRecord.dll.NHibernate ...
- Connecting to MQSeries with .NET
By connecting to MQSeries withing a .NET application, first it has to be done is to install MQ Serie ...
- 嵌入式的SQL程序设计
嵌入式的SQL程序设计 sql语句大全之嵌入式SQL 2017-01-18 16:00 来源:未知 嵌入式SQL 为了更好的理解嵌入式SQL,本节利用一个具体例子来说明.嵌入式SQL允许程序连接数 ...
- laravel表单图片上传
1.视图 2.控制器
- jqueryAjax的使用
1. 导入等下我们要使用的文件AjaxMsgHelper.cs和DataHelper.cs他们的代码如下 using System;using System.Collections.Generic;u ...
- part1:7-Linux网络配置
1.虚拟机(Vmware)网络配置 VMware虚拟机对于不同的网络环境提供了三种网卡工作模式: Bridged:网桥模式: 在桥接模式下,计算机A充当路由器与虚拟机之间的“桥”,虚拟机通过计算机A的 ...
- 2018.08.30 NOIP模拟 wall(模拟)
[问题描述] 万里长城是中国强大的标志,长城在古代的用途主要用于快速传递军事消息和抵御 外敌,在长城上的烽火台即可以作为藏兵的堡垒有可以来点燃狼烟传递消息. 现在有一段 万里长城,一共有 N 个烽火台 ...
- 2018.08.09洛谷P3959 宝藏(随机化贪心)
传送门 回想起了自己赛场上乱搜的20分. 好吧现在也就是写了一个随机化贪心就水过去了,不得不说随机化贪心大法好. 代码: #include<bits/stdc++.h> using nam ...
- [转载][翻译]Go的50坑:新Golang开发者要注意的陷阱、技巧和常见错误[2]
Golang作为一个略古怪而新的语言,有自己一套特色和哲学.从其他语言转来的开发者在刚接触到的时候往往大吃苦头,我也不例外.这篇文章很细致地介绍了Golang的一些常见坑点,读完全篇中枪好多次.故将其 ...