系统地讲解Django开发的基础知识, 高阶知识。关注微信公众号[薯条编程],领取该教程的PDF电子书:《Python web开发-django从入门到精通》。
10.2.1 django中的会话
django提供了以下四种方式来对用户进行会话管理:
(1) 基于数据库的会话
(2) 基于缓存的会话
(3) 基于文件的会话
(4) 基于cookie的会话
在django中启用会话,需要使用会话管理中间件。打开settings.py,找到与中间件配置相关的全局变量MIDDLEWARE:
MIDDLEWARE = [ 'django.middleware.security.SecurityMiddleware', 'django.contrib.sessions.middleware.SessionMiddleware', 'django.middleware.common.CommonMiddleware', 'django.middleware.csrf.CsrfViewMiddleware', 'django.contrib.auth.middleware.AuthenticationMiddleware', 'django.contrib.messages.middleware.MessageMiddleware', 'django.middleware.clickjacking.XFrameOptionsMiddleware', ]
MIDDLEWARE列表中的元素django.contrib.sessions.middleware.SessionMiddleware, 代表的正是会话管理中间件,这也说明了django默认启动了会话管理。
10.2.2 基于数据库的会话
基于数据库的会话,是指将用户的session保存在数据库中。在项目中使用基于数据库的会话,同样需要在settings.py中进行配置。与该项配置相关的全局变量为INSTALLED_APPS,配置的值为:'django.contrib.sessions'。打开settings.py,INSTALLED_APPS更新后的值为:
INSTALLED_APPS = [ 'django.contrib.admin', 'django.contrib.auth', 'django.contrib.contenttypes', # 配置使用基于数据库的会话 'django.contrib.sessions', 'django.contrib.messages', 'django.contrib.staticfiles', 'chipscoco', ]
在配置完成以后,需要通过manage.py中的migrate子命令来进行模型迁移。
10.2.3 基于缓存的会话
顾名思义,基于缓存的会话,是将用户的session信息保存在内存缓存中,与使用基于文件系统的数据库相比,使用基于缓存的会话时,可以提升查询性能。在django中使用基于缓存的会话,需要先安装并运行相应的缓存组件,同时在settings.py中进行配置。以缓存系统Memcached为例,其在django中的配置值为: django.core.cache.backends.memcached.MemcachedCache,打开settings.py,可以按以下格式进行缓存的配置:
CACHES = { 'default': { 'BACKEND': 'django.core.cache.backends.memcached.MemcachedCache', 'LOCATION': '127.0.0.1:11211', } }
键名BACKEND表示配置的缓存组件,LOCATION表示memcached运行的ip地址和端口。配置完缓存组件以后,接下来需要配置session信息的存储方式,在settings.py中与缓存存储方式相关的全局变量为SESSION_ENGINE。对session信息进行存储,可以直接存储在内存中,其对应的配置为:
SESSION_ENGINE='django.contrib.sessions.backends.cache'
也可以将缓存的session进行持久化,其对应的配置为:
SESSION_ENGINE='django.contrib.sessions.backends.cache_db'
将缓存的数据进行持久化,是指将数据再写回到数据库中,这要求在django中进行数据库的配置。
10.2.4 基于文件的会话
基于文件的会话,是指将session信息保存在服务端的文件中。在settings.py中的配置为
SESSION_ENGINE='django.contrib.sessions.backends.file'
10.2.5 基于cookie的会话
在django中使用基于cookie的会话,需要在settings.py中作如下配置:
设置SESSION_ENGINE的值为django.contrib.sessions.backends.signed_cookies。
10.2.6 在视图中使用session对象
在settings.py中对会话进行相关配置以后,在视图的request(HttpRequest对象)参数中,会包含一个类似于字典的session属性。session对象的常用方法:
方法名 | 描述
|
使用[]操作符访问session中的键值时会执行该方法 | |
__setitem__(key) | 使用[]操作符设置session中的键值时会执行该方法 |
__delitem__(key) | 使用del语句删除session中的键值时会执行该方法 |
__contains__ | 使用in操作符来查询session中的键名时会执行该方法 |
get(key,default=None) | 获取session对象中key所对应的value |
pop(key,default=None) | 删除session对象中的key |
clear() | 清空session对象中的所有key |
set_expire(value) | 设置session或cookie的有效期。value的类型可为整型,表示多少秒以后过期,也可以为日期时间类型,表示过期的绝对值。value值为0时表示用户关闭浏览器以后才过期,设置 为None时表示采用默认的过期策略。 |
set_test_cookie() | 设置一个测试cookie |
test_cookie_worked() | 返回值为布尔类型,指示浏览器是否启用了cookie |
delete_test_cookie() | 删除测试cookie |
clear_expired | 删除已过期的session对象 |
在登录视图中使用会话的代码实例:
# 导出User模型 from django.contrib.auth.models import User from django.contrib.auth import authenticate, login class Login(View): def post(self, request): """ 通过查询form表单中的name,可以获取用户 在表单中的输入值 """ username = request.POST.get('username', '') password = request.POST.get('password', '') prompt = "用户登录成功" user = authenticate(username=username, password=password) if not user: prompt = "用户的账号或密码无效" else: # 判断session中的uid是否与 用户对象的id值相等 if request.session.get("uid") == user.id: prompt = "你已经登录过了" else: # 在session中添加自定义字段uid,将其设置为user对象的id值 request.session["uid"] = user.id login(request, user) return render(request, "login.html",{"prompt": prompt}) def get(self, request): # 如果为get请求,则直接对登录页面进行渲染 return render(request, "login.html")
用户登出时的代码实例:
class Logout(View): def post(self, request): try: # 使用del语句来删除session中的uid del request.session['uid'] except KeyError: pass return HttpResponse("您已经退出系统") def get(self, request): # 如果为get请求,则直接对登出页面进行渲染 return render(request, "logout.html")
10.2.7 在视图中使用cookie对象
若浏览器支持cookie,则通过request参数的COOKIES对象可以获取已设置的cookie值。COOKIE对象是一个类似于字典的对象,可以通过get等方法来对COOKIE值进行访问和操作。通过HttpResponse对象的set_cookie方法可以设置cookie,对于set_cookie函数的用法,可参考3.2 节函数类型视图中的内容。在视图中使用cookie的代码实例:
from django.http import HttpResponse from django.shortcuts import render from django.contrib.auth import authenticate class Login(View): def post(self, request): username = request.POST.get('username', '') password = request.POST.get('password', '') # 测试浏览器是否启用了cookie if request.session.test_cookie_worked(): request.session.delete_test_cookie() if request.COOKIES.get('username') == username: response = HttpResponse("您已经登录") else: user = authenticate(username=username, password=password) if not user: response = HttpResponse("账号或密码错误") else: response = HttpResponse("登录成功") # 将用户名添加至cookie中 response.set_cookie('username',username) return response else: return HttpResponse("浏览器不支持或禁止了cookie") def get(self, request): # 创建测试cookie request.session.set_test_cookie() return render(request, 'login.html')
关注微信公众号:薯条编程,公众号后台回复"Python资料",免费领取Python电子书,以及学习Python视频课程。