title: Django项目学习
date: 2017-12-13 19:32:03
tags: [网页,Django]
category: [编程学习,网页制做]
---css
本文主要来自于mooc公开课Django课程html
pip install virtualenv
,而后使用virtualenv 虚拟环境名
创建一个虚拟环境,在windows下面的激活方法是前端
cd django_virtual cd Script activate
在linux下只须要将最后一步换位source activatepython
在PyCharm创建程序时,直接选择Django程序,选择解释器为virtualenv创建的django环境,便可创建django项目mysql
项目创建以后,咱们获得了以下的目录结构,紫色的被标记为了templet目录,这样就能智能提示,若是你想要在import的时候不须要加入绝对路径,那么就能够mark as source root
linux
接下来咱们先尝试运行该项目,点击run,运行这个Django项目,能够看到运行在了本机的8000端口,点击该地址便可访问:git
若是要配置监听全部ip,那么咱们须要经过run-Edit configurations
,将监听端口改成0.0.0.0github
安装好Navicat以后,打开软件,创建链接,以后创建表,设计表的字段,设计完以后按ctrl+s
保存,以后就能够插入数据条目,这就是简单的使用方法,具体使用会在以后用到的时候详细介绍。下载地址请点击web
首先看看以前提到的创建django以后的目录结构,windows使用tree \F .
获得以下结构,linux中使用apt-get install tree
,而后tree .便可获得
:sql
├mooc_web │ manage.py ├─mooc_web │ │ settings.py │ │ urls.py │ │ wsgi.py │ │ __init__.py └─templates
经过pycharm当中的tools-run manage.py task
,此时能够在shell中执行Django命令:
startapp message
此时就有了一个名为message的文件夹,将其拖入apps文件夹,自动生成了一个__init__.py
文件,这样就让apps变成一个能够导入的包,为了方便导入,那么咱们须要将apps文件夹remark成source root,这样每次引用的时候就不须要import apps.message.view 而是能够直接 import message.view
这样在pycharm中引用变得方便了,可是在使用命令行运行的时候就会出错,此时咱们须要在settings.py中将apps加入到根搜索路径(BASE_DIR)中
├── apps │ ├── __init__.py │ └── message │ ├── admin.py │ ├── apps.py │ ├── __init__.py │ ├── migrations │ │ └── __init__.py │ ├── models.py │ ├── tests.py │ └── views.py ├── db.sqlite3 ├── log ├── manage.py ├── media ├── mooc_web │ ├── __init__.py │ ├── settings.py │ ├── urls.py │ └── wsgi.py ├── static └── templates
创建log文件夹用于存放日志,media用于存放用户的上传文件,创建static存放静态css和js文件
当app比较多的时候,就创建一个apps文件夹,将新创建的app拖进去
将html模板放入template文件夹,在static文件夹中创建css文件夹,并放入style.css文件
由于Django默认用的是sqlite数据库,咱们要改为mysql数据库,打开项目的settings.py,找到DATABASES,将其中的:
django.db.backends.mysql
testDjango
DATABASES = { 'default': { 'ENGINE': 'django.db.backends.mysql', 'NAME': 'testDjango', 'USER': 'root', 'PASSWORD': 'root', 'HOST': '127.0.0.1' } }
经过tools-Run manage.py Task
来链接数据库,首先须要安装mysqlclient,用pip install mysqlclient
安装:
> makemigrations # 用于生成一个基于你对模型改变的迁移,在这里就是数据库类型从sqlite迁移到mysql > migrate # 用于应用改变
此时Django自动生成了一大堆数据库表,在Navicat中能够看到表的名称:
此时能够点击run运行整个系统,能够在127.0.0.1:8000上访问该网址
可是此时的style.css没法被找到,咱们要在settings.py中配置一下static文件夹的地址,由于STATICFILES_DIRS
可能不止一个,因此用list的形式进行赋值,其中BASE_DIR是项目文件的根目录:
STATICFILES_DIRS = [ os.path.join(BASE_DIR,'static') ]
在urls.py中添加新的页面,页面的处理函数要在apps-message-views.py
中新增,首先咱们在view.py
中构造以下函数,直接return render的模板,其中request参数是Django的请求,每一个views函数都得有:
def getform(request): return render(request, template_name='course-comment.html')
总体来讲,先设置数据库和STATICFILES_DIRS,以后这一块再也不动,主要就是views.py写后端逻辑,urls.py写页面地址url配置
普通的数据库调用方法,链接(connect),生成cursor,excute sql语句,cursor.fetchall( )
orm就是把一个表映射成一个类,好比要找出name只须要调用book.name
下面咱们开始使用orm进行设计数据库:
找到message下面的models.py文件,在其中定义一个UserMessage类,用于存放咱们须要的数据,全部model都要继承models.Model类:
class UserMessage(models.Model): name = models.CharField(max_length=20, verbose_name='用户名') email = models.EmailField(verbose_name='邮箱') address = models.CharField(max_length=100, verbose_name='地址') message = models.CharField(max_length=500, verbose_name='留言信箱') class Meta: verbose_name = '用户留言信息' verbose_name_plural = verbose_name ordering = '-id' # 排序方式为反向的id db_table = 'my_table' #设置table的名字
其中每个字段都定义一个类型,经常使用的有CharField,EmailField,DateTimeField, IntergerField, ForeignKey, IPAddressField, FileField, ImageField
其中max_length表示最大长度,verbose_name表示别名.
本身定义的model还有一个内部类Meta,用于存放全部不是Field的字段,好比排序的顺序,数据表的名称等等
点击Tools-Run manage.py
,执行命令,发现找不到message这个model,全部咱们要去settings.py中INSTALLED_APPS
加入'app.message'
再次执行
> makemigrations message > migragate message
先引入model对象,from apps.message.models import UserMessage
,,利用model对象的objects方法,对数据进行操做
all_message = UserMessage.objects.all() #这个是能够循环的 for message in all_messages: print(message.name) filterd_data = UserMessage.objects.filter(name='jeffrey',address='beijing') #filter方法能够对数据进行过滤,中间的逗号表示多个条件,这里是取出的name为jeffrey,address为北京的值 for message in filterd_data: print(message.name)
这里的all就是取出全部值,filter就是取出特定条件的值
定义一个新的对象,并对其各个field赋值
user_message = UserMessage() user_message.name = 'a' user_message.message = 'a@a.com' user_message.message = 'aaaaa' user_message.save()
这样每次访问form页面的时候均可以存入一条记录
在html文件中须要进行以下更改:
<form action="/form/" method="post" class="smart-green"> 在action中填入网页地址
须要加入CSRF安全机制,
还能够经过页面的表单提交增长新的数据,request的POST属性中,以字典的形式存储了表单中提交的值,能够用python的get方法获取这些值,get的第二个参数为获取不到时候的默认值:
if request.method == 'POST': name = request.POST.get('name','') email = request.POST.get('email', '') message = request.POST.get('message', '') user_message = UserMessage() user_message.name = 'a' user_message.email = 'a@a.com' user_message.message = 'aaaaa' user_message.save()
直接先查找到对象,而后用delete方法就能够删除对象
all_message = UserMessage.objects.fileter(name='bob') all_message.delete()
在view.py中,咱们能够先取出数据,而后在render的时候,把须要传入的参数以一个dict的形式,传递给context,这样咱们就能够在html文件中进行调用
def getform(request): message = None all_message = UserMessage.objects.filter(name='boobytest') if all_message: message = all_message[0] return render(request, template_name='course-comment.html',context={'message':message,})
在HTML文件中调用参数的方法是两个大括号,input就输入在value里面,textarea就输入在两个标签之间:
<input id="email" type="email" value={ { message.email } } name="email" placeholder="请输入邮箱地址"/> <textarea id="message" name="message" placeholder="请输入你的建议">{ { message.message } }</textarea>
在HTML文件中,使用python逻辑的方法是大括号加百分号,{ % python expression % }
if和end if成对出现
<input id="name" type="text" value="{% if not message.name == 'boobytest' %} boobyhastest{% else %}booby no test {% endif %}" name="name" class="error" placeholder="请输入您的姓名"/>
好比在HTML中使用if和else的方法如上,固然if a==b 也可使用 ifequal a b代替,取前五位也可使用message.name|split:'5'
{% ifequal a b%} {% endif %}#用于表示等于
Django提供了不少内置的方法,具体能够查看Django template built-in tags
url在配置过程当中可能会改变,所以咱们须要为url设置一个不变的名字供HTML调用
在url.py中:
url(r'^form/$', getform,name='form')
在comment.html中:
<form action="{% url 'form' %}" method="post" class="smart-green">
注意,在url配置中必定要加上/$
表示以/
结尾,否则再进行正则匹配的时候可能会匹配到别的网页
必须在url前面加上^
,后面加上/$
,这样不会匹配出错
mkvirtualenv mooc cd mooc/Script activate pip install Django mysqlclient
经过pycharm创建Django项目,名字为MxOnline,首先在settings.py中更改数据库引擎
DATABASES = { 'default': { 'ENGINE': 'django.db.backends.mysql', 'NAME': 'mxonline', 'USER': 'root', 'PASSWORD': 'root', 'HOST': '127.0.0.1', } }
经过Tools-run manage.py task
来生成数据库的表
makemigrations migragate
首先startapp users
,在models当中,新建一个UserProfile
,继承django.contrib.auth.models.AbstractUser
,加入你须要的自定义字段,并定义好meta信息中的verbose_name
from django.db import models from django.contrib.auth.models import AbstractUser # Create your models here. class UserProfile(AbstractUser): nick_name = models.CharField(max_length=50,verbose_name='昵称',default='') birthday = models.DateField(verbose_name='生日',null=True,blank=True) gender = models.CharField(max_length=5,choices=(('male','男'),('female','女')),default='') address = models.CharField(max_length=100,default='') mobile = models.CharField(max_length=11, null=True, blank=True) image = models.ImageField(upload_to='image/%Y/%m',default='image/default.png') class Meta: verbose_name = '用户信息' verbose_name_plural = verbose_name
而后run manage.py,经过makemigrations users
和migragate users
生成新的user表,可能会报错,报错时只须要将以前生成的全部表删除后从新生成便可
避免交叉引用,否则会出错,使用上层app引用下层app
class EmailVerifyRecord(models.Model): code = models.CharField(max_length=20, verbose_name='验证码') email = models.EmailField(max_length=50, verbose_name= '邮箱') send_type = models.CharField(choices=(('register','注册'),('forget','找回密码')),max_length=10) send_time = models.DateTimeField(default=datetime.now) #记得去掉datetime.now的括号,否则只会记录class生成的时间 class Meta: verbose_name = '邮箱验证码' verbose_name_plural = verbose_name class Banner(models.Model): title = models.CharField(max_length=100, verbose_name='标题') image = models.ImageField(upload_to='banner/%Y/%m', verbose_name='轮播图') url = models.URLField(max_length=500, verbose_name='访问地址') index = models.IntegerField(default=100, verbose_name='顺序') add_time = models.DateTimeField(default=datetime.now, verbose_name='添加时间') class Meta: verbose_name = '轮播图' verbose_name_plural = verbose_name
Course -- 课程基本信息 Lesson -- 章节信息 Video -- 视频 CourseResource -- 课程资源
一共有上述四张表
from django.db import models from datetime import datetime # Create your models here. class Course(models.Model): name = models.CharField(max_length=50, verbose_name='课程名称') desc = models.CharField(max_length=300, verbose_name='课程描述') detail = models.TextField(verbose_name='课程详情') degree = models.CharField(choices=(('cj','初级'),('zj','中级'),('gj','高级')),verbose_name='课程难度',max_length=2) learn_time = models.IntegerField(default=0, verbose_name='学习时长(分钟数)') students = models.IntegerField(default=0, verbose_name='学习人数') fav = models.IntegerField(default=0, verbose_name='收藏人数') image = models.ImageField(upload_to='courses/%Y/%m', verbose_name='封面图', max_length=100) click_num = models.IntegerField(default=0, verbose_name='点击数') add_time = models.DateTimeField(default=datetime.now, verbose_name='添加时间') class Meta: verbose_name='课程' verbose_name_plural = verbose_name class Lesson(models.Model): course = models.ForeignKey(Course, verbose_name='课程') name = models.CharField(max_length=100, verbose_name='章节名') add_time = models.DateTimeField(default=datetime.now, verbose_name='添加时间') class Meta: verbose_name = '章节' verbose_name_plural = verbose_name class Video(models.Model): lesson = models.ForeignKey(Lesson, verbose_name='章节') name = models.CharField(max_length=100, verbose_name='视频名') add_time = models.DateTimeField(default=datetime.now, verbose_name='添加时间') class Meta: verbose_name = '视频' verbose_name_plural = verbose_name class CourseResource(models.Model): course = models.ForeignKey(Course, verbose_name='课程') download = models.FileField(upload_to='courses/resource/%Y/%m',max_length=100) name = models.CharField(max_length=100, verbose_name='资源名称') add_time = models.DateTimeField(default=datetime.now, verbose_name='添加时间') class Meta: verbose_name = '课程资源' verbose_name_plural = verbose_name
CourseOrg -- 课程机构基本信息 Teacher -- 教师基本信息 CityDict -- 城市信息
添加以下
from django.db import models from datetime import datetime # Create your models here. class CourseOrg(models.Model): city = models.ForeignKey(CityDict,verbose_name='所在城市') name = models.CharField(max_length=50,verbose_name='机构名称') desc = models.TextField(verbose_name='机构描述') click_nums = models.IntegerField(default=0, verbose_name='点击数') fav_nums = models.IntegerField(default=0, verbose_name='收藏数') image = models.ImageField(upload_to='org/%Y/%m',verbose_name='封面图') address = models.CharField(max_length=150,verbose_name='地址') add_time = models.DateTimeField(datetime.now, verbose_name='添加时间') class Meta: verbose_name = '课程机构' verbose_name_plural = verbose_name class CityDict(models.Model): name = models.CharField(max_length=20,verbose_name='城市') desc = models.CharField(max_length=200, verbose_name='描述') add_time = models.DateTimeField(datetime.now, verbose_name='添加时间') class Meta: verbose_name = '城市' verbose_name_plural = verbose_name class Teacher(models.Model): org = models.ForeignKey(CourseOrg, verbose_name='所属机构') name = models.CharField(max_length=20,verbose_name='教师名') work_years = models.IntegerField(default=0, verbose_name='工做年限') work_company = models.CharField(max_length=50,verbose_name='就任公司') work_position = models.CharField(max_length=50,verbose_name='公司职位') points = models.CharField(max_length=50, verbose_name='教学特色') click_nums = models.IntegerField(default=0, verbose_name='点击数') fav_nums = models.IntegerField(default=0, verbose_name='收藏数') add_time = models.DateTimeField(datetime.now, verbose_name='添加时间') class Meta: verbose_name = '教师' verbose_name_plural = verbose_name
UserAsk -- 用户咨询 CourseComments -- 用户评论 UserFavorite -- 用户收藏 UserMessage -- 用户消息 UserCourse -- 用户学习的课程
添加以下:
from django.db import models from datetime import datetime from users.models import UserProfile from courses.models import Course from organization.models import CourseOrg # Create your models here. class UserAsk(models.Model): name = models.CharField(max_length=20,verbose_name='姓名') mobile = models.CharField(max_length=11, verbose_name='手机') course_name = models.CharField(max_length=50,verbose_name='课程名称') add_time = models.DateTimeField(datetime.now, verbose_name='添加时间') class Meta: verbose_name = '用户咨询' verbose_name_plural = verbose_name class CourseComments(models.Model): user = models.ForeignKey(UserProfile, verbose_name='用户') course = models.ForeignKey(Course, verbose_name='课程') comments = models.CharField(max_length=500,verbose_name='评论') add_time = models.DateTimeField(datetime.now, verbose_name='添加时间') class Meta: verbose_name = '课程评论' verbose_name_plural = verbose_name class UserFavorite(models.Model): user = models.ForeignKey(UserProfile, verbose_name='用户') fav_id = models.IntegerField(default=0, verbose_name='数据id') fav_type = models.IntegerField(choices=((1,'课程'),(2,'课程机构'),(3,'讲师')),default=1,verbose_name='收藏类型') add_time = models.DateTimeField(datetime.now, verbose_name='添加时间') class Meta: verbose_name = '用户收藏' verbose_name_plural = verbose_name class UserMessage(models.Model): user = models.IntegerField(default=0,verbose_name='接收用户')# 不用外键,由于有多是发给全部人的消息,用0表示发送给全部人的消息,用int表示用户的id message = models.CharField(max_length=500, verbose_name='消息内容') add_time = models.DateTimeField(datetime.now, verbose_name='添加时间') has_read = models.BooleanField(default=False,verbose_name='是否已读') class Meta: verbose_name = '用户消息' verbose_name_plural = verbose_name class UserCourse(models.Model): user = models.ForeignKey(UserProfile, verbose_name='用户') course = models.ForeignKey(Course, verbose_name='课程') add_time = models.DateTimeField(datetime.now, verbose_name='添加时间') class Meta: verbose_name = '用户课程' verbose_name_plural = verbose_name
创建new python package, 把全部的app放到apps这个包下面,注意选择不改相对引用,并mark apps为source root
将apps这个文件夹加入到settings当中
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) sys.path.insert(0, os.path.join(BASE_DIR,'apps'))
直接在run manage.py task中输入createsuperuser
,输入用户名,邮箱和密码就能够登陆
更改语言和时区:
LANGUAGE_CODE = 'zh-hans' #将语言改成中文 TIME_ZONE = 'Asia/Shanghai' #将时区改成上海 USE_TZ = False # 系统使用本地时间而不是utc时间
由于咱们更改了admin的auth.user的model,所以须要注册user的model,在users
库中的admin.py文件中注册:
from users.models import UserProfile # Register your models here. class UserProfileAdmin(admin.ModelAdmin): #userprofile的管理器 pass admin.site.register(UserProfile,UserProfileAdmin) #admin和model的关联注册
登陆http://127.0.0.1:8000/admin
就能够对用户进行修改
ctrl+shift+f
使用xadmin,由于我安装的Django 2.0.1版本,因此须要安装专门的xadmin for Django2.0
pip install git+git://github.com/sshwsfc/xadmin.git@django2
在url.py中引入xadmin
import xadmin urlpatterns = [url(r'^xadmin/', xadmin.site.urls),]
在settings.py中注册xadmin和crispy_forms:
INSTALLED_APPS = [ 'django.contrib.admin', ....... 'xadmin', 'crispy_forms', ]
接下来同步xadmin的表:
> makemigrations > migragate
再打开http://127.0.0.1:8000/xadmin就能够访问xadmin的后台管理了
在管理用户信息的时候,会出现错误,这是因为咱们用的Django是2.0.1版本,而教程中用到的是1.0+,根据pycharm报错的最后一条,打开widget.py文件,在74行修改以下
input_html = [ht for ht in super(AdminSplitDateTime, self).render(name, value, attrs).split('/><') if ht != ''] if (len(input_html) > 1): input_html[0] = input_html[0] + "/>" input_html[1] = "<" + input_html[1]
在mxonline下创建一个python package文件夹extra_apps,下载xadmin并解压,拷贝其中的xadmin文件夹到其中,并把extra_apps mark as source root,这样引入xadmin的时候就会从相对文件引入
同时在settings.py中把xadmin文件夹加入根搜索路径
注册方法相似于admin的注册方式,只不过不是在admin.py中注册,而是要新建adminx.py,而且admin继承的是object
import xadmin from users.models import EmailVerifyRecord class EmailVerifyRecordAdmin(object): pass xadmin.site.register(EmailVerifyRecord, EmailVerifyRecordAdmin) # 注册方法
修改显示的邮件验证码存储记录的str名称:
class EmailVerifyRecord(models.Model): code = models.CharField(max_length=20, verbose_name='验证码') email = models.EmailField(max_length=50, verbose_name= '邮箱') ....... def __str__(self): return '{0}({1})'.format(self.code,self.email)
class Model名+Admin
在其中加入list_display(显示列), search_fields(搜索域), list_filter(过滤器)
class LessonAdmin(object): list_display = ['course','name','add_time'] search_fields = ['course','name','add_time'] list_filter = ['course','name','add_time']
若是要使用外键进行搜索,能够用两个下划线表示
class LessonAdmin(object): list_filter = ['course__name','name','add_time']
将全站的配置放在user app的admix.py中,新建一个class BaseSetting,用于配置主题
from xadmin import views class BaseSettings: enable_themes = True #容许使用主题 use_bootswatch = True #容许多主题 xadmin.site.register(views.BaseAdminView,BaseSettings)
创建一个class GlobalSettings配置标题名称和footer名称
class GlobalSettings: site_title = '慕学后台管理系统' site_footer = '慕学在线网' menu_style = 'accordion' #折叠model xadmin.site.register(views.CommAdminView,GlobalSettings)
在每一个model文件夹中的apps.py文件中加入verbose_name
from django.apps import AppConfig class CoursesConfig(AppConfig): name = 'courses' verbose_name = '课程'
而后在__init__.py
中加入default_app_config
default_app_config = 'courses.apps.CoursesConfig'
首先将前端给的Index.html(首页)文件和login.html(登陆页)文件放入templates文件夹中
在根目录下创建static文件夹,存放css,images,js,media文件,并在settings.py中声明STATICFILES_DIRS=[os.path.join(BASE_DIR,'static')]
,注意:这里的STATICFILES_DIRS必须设置为list或者tuple形式,不然会报错
此时,将html文件中的全部css,js的文件路径修改成/static/css
和/static/js
接下来配置url,在url.py中引入TemplateView
from django.views.generic import TemplateView urlpatterns = [ url(r'^xadmin/', xadmin.site.urls), url(r'^$',TemplateView.as_view(template_name='index.html'),name='index'), url(r'^login/', TemplateView.as_view(template_name='login.html'), name='login') ]
这样就完成了页面配置,重启项目后就能够访问首页和登陆页面
如今users模块中新建CustomBackend类,继承ModelBackend,重写其中的authenticate函数,用Q函数实现或操做
from django.contrib.auth.backends import ModelBackend from django.db.models import Q class CustomBackend(ModelBackend): def authenticate(self, request, username=None, password=None, **kwargs): try: user = UserProfile.objects.get(Q(username=username)|Q(email=username)) if user.check_password(password): return user except Exception as e: return None
写本身的login函数login,并将其写到urls.py中
views.py
def my_login(request): if request.method == 'POST': user_name = request.POST.get('username','') pass_word = request.POST.get('password','') user = authenticate(username=user_name,password=pass_word) if user: login(request, user) return render(request, 'index.html',{'userprofile':user}) else: return render(request,'login.html',{'msg':'用户名或密码错误'}) elif request.method == 'GET': return render(request, 'login.html', {})
urls.py
url(r'^login/', my_login, name='login')
在settings.py中加入AUTHENTICATION_BACKENDS=('users.views.CustomBackend',)
,将认证后台改成本身写的后台
在点击登录后,咱们须要跳转回首页或者是报告密码错误,此时request被传递到网页中,能够在跳转后显示本身的用户名
<dd>{{ request.POST.username }}<img class="down fr" src="/static/images/top_down.png"/></dd>
views.py中加入本身的类:
from django.views.generic import View class LoginView(View): def get(self, request): return render(request, 'login.html', {}) def post(self, request): user_name = request.POST.get('username','') pass_word = request.POST.get('password','') user = authenticate(username=user_name,password=pass_word) if user: login(request, user) return render(request, 'index.html',{'userprofile':user}) else: return render(request,'login.html',{'msg':'用户名或密码错误'})
在urls.py中将loginview注册:
url(r'^login/', LoginView.as_view(), name='login')
在users模块汇总创建forms.py用于检验表单
forms.py
from django import forms class LoginForm(forms.Form): username = forms.CharField(required=True) password = forms.CharField(required=True, min_length=5)
在views.py中加入loginform的验证,逻辑是若是有效,则提取表单中的username和password,验证成功后,用login函数登陆,返回index页面;若是验证失败,返回登陆页显示用户或密码错误;若是检测到form有错误,返回登陆页,显示错误类型
class LoginView(View): def get(self, request): return render(request, 'login.html', {}) def post(self, request): login_form = LoginForm(request.POST) #实例化一个login_form,传入参数为request.POST,自动验证其中的username和password,注意这里名字必须和login.html的form当中的name相同 if login_form.is_valid(): #这一步以后能够看到login_form的error类型,存为一个dict类型 user_name = request.POST.get('username','') pass_word = request.POST.get('password','') user = authenticate(username=user_name,password=pass_word) if user: login(request, user) return render(request, 'index.html',{'userprofile':user}) else: return render(request,'login.html',{'msg':'用户名或密码错误'}) else: return render(request,'login.html',{'login_form':login_form})
在login.html中显示错误类型:
<div class="error btns login-form-tips" id="jsLoginTips">{% for key, error in login_form.errors.items %} {{ error }}{% endfor %}{{ msg }}</div>
http自己是一种无状态协议,每次发送请求,服务器返回请求的数据,若是要记住登陆状态就须要cookies
django的cookie由session_key和session_data以及expire_data组成,实现是经过setings.py中的'django.contrib.sessions',
每一个域名之下的cookies是不能互相访问的
先拷贝register.html到template中,配置url,
url(r'^register/',RegisterView.as_view,name='register'),
而后在views.py
中加入RegisterView类
class RegisterView(View): def get(self, request): return render(request, 'register.html')
在HTML代码中修改指向
<a style="color:white" class="fr registerbtn" href="{% url 'register' %}">注册</a> <a style="color:white" class="fr loginbtn" href="{% url 'login' %}">登陆</a>
修改其css和js文件的地址,这里介绍第二种修改的方法
首先在html文件中输入{%load staticfiles%}
而后在须要修改地址的地方输入{%static '/css/reset.css'%}
pip install django-simple-captcha
urlpatterns += [ url(r'^captcha/', include('captcha.urls')), ]
而后在forms.py中加入一个新的register_form,在其中加入captchafiled
from django import forms from captcha.fields import CaptchaField class RegisterForm(forms.Form): email = forms.EmailField(required=True,error_messages={'invalid':'请输入一个有效的邮箱地址'}) password = forms.CharField(required=True,min_length=5,error_messages={'invalid':'密码至少6个字符','required':'请输入密码'}) captcha = CaptchaField(error_messages={'required': '验证码错误'})
在view.py
中加入registerview
class RegisterView(View): #get方法,先实例化一个RegisterForm,将register_form返回到html中用于获取验证码 def get(self, request): register_form = RegisterForm() return render(request, 'register.html',{'register_form':register_form}) def post(self, request): register_form = RegisterForm(request.POST) if register_form.is_valid(): user_name = request.POST.get('email', '') pass_word = request.POST.get('password', '') is_used = UserProfile.objects.filter(username=user_name) if not is_used: user = UserProfile() user.username = user_name user.email = user_name user.password = make_password(pass_word) user.save() send_register_email(user_name) return render(request, 'login.html',{}) else: return render(request, 'register.html', {'msg':'该用户名已经被占用','register_form':register_form}) else: return render(request, 'register.html',{'register_form':register_form})
修改register.html
<div class="tab-form"> <!--其中的action用于指定提交到哪一个页面--> <form id="email_register_form" method="post" action="{% url 'register' %}" autocomplete="off"> <input type='hidden' name='csrfmiddlewaretoken' value='gTZljXgnpvxn0fKZ1XkWrM1PrCGSjiCZ'/> <!--在class里面加入{%if register_form.email.errors %}errorput用于出错时高亮--> <div class="form-group marb20 {% if register_form.email.errors %}errorput{% endif %}"> <label>邮 箱</label> <!--将value填为上次填写的value,这样出错时不用用户每次手动填写value--> <input type="text" id="id_email" name="email" value="{{ register_form.email.value }}" placeholder="请输入您的邮箱地址"/> </div> <div class="form-group marb8 {% if register_form.errors.password %}errorput{% endif %}"> <label>密 码</label> <input type="password" id="id_password" name="password" value="{{ register_form.password.value }}" placeholder="请输入6-20位非中文字符密码"/> </div> <div class="form-group marb8 captcha1 {% if register_form.errors.password %}errorput{% endif %}"> <label>验 证 码</label> {{ register_form.captcha }} </div> <div class="error btns" id="jsEmailTips"> <!--用循环的方式将错误显示出来--> {% for key,value in register_form.errors.items %} {{ value }} {% endfor %} {{ msg }} </div> <div class="auto-box marb8"> </div> <input class="btn btn-green" id="jsEmailRegBtn" type="submit" value="注册并登陆"/> {# <input type='hidden' name='csrfmiddlewaretoken' value='5I2SlleZJOMUX9QbwYLUIAOshdrdpRcy'/>#} {% csrf_token %} </form> </div>