Django会话
Django完全支持也匿名会话,简单说就是使用跨网页之间可以进行通讯,比如显示用户名,用户是否已经发表评论。session框架让你存储和获取访问者的数据信息,这些信息保存在服务器上(默认是数据库中),以 cookies 的方式发送和获取一个包含 session ID的值,并不是用cookies传递数据本身(除非使用了基于cookie的会话)。
启用session
想要启动Django的会话功能需要:
- 确保在
MIDDLEWARE
中添加了'django.contrib.sessions.middleware.SessionMiddleware'
- 在
INSTALLED_APPS
添加'django.contrib.sessions'
应用
默认创建的项目是包含这会话服务的,如果确定不需要使用会话功能,也可以移除这两项,为服务器减少开支。
配置session
默认情况下,Django会将会话存储在数据库中(使用模型django.contrib.sessions.models.Session
)虽然这很方便,但在某些设置中,将会话数据存储在其他位置的速度更快,因此可以将Django配置为在文件系统或缓存中存储会话数据。
使用数据库存储会话
这是默认设置,只要在INSTALLED_APPS
添加'django.contrib.sessions'
就可以。
执行manage.py migrate
命令时,就会在数据库创建会话表:
使用Cache存储会话
使用基于缓存后端的会话能获取更好的性能。首先确保项目设置好了缓存,缓存配置。
如果在CACHES
定义了多种缓存,Django会使用默认的缓存存储会话。可以用
SESSION_CACHE_ALIAS
指定使用的缓存后端。缓存配置完成后,有2中方式使用缓存存储会话:
- 简单直接地将
SESSION_ENGINE
设置为'django.contrib.sessions.backends.cache'
,这样会话会直接存储在缓存中。但是,会话数据可能不是持久性的:如果缓存填满或缓存服务器重新启动,缓存数据就会被逐出。 - 对于要持久性的缓存会话数据,将
SESSION_ENGIN
设置为'django.contrib.sessions.backends.cached_db'
,这使用了直写高速缓存:每次写入高速缓存的数据也将会写入数据库。如果数据已经不在缓存中,则只会用数据库读取会话。
两个会话存储都非常快,但使用简单的缓存更快,因为它忽略了持久性。在大多数情况下,cached_db后端速度足够快。但如果需要最后一点性能,并且愿意让会话数据不时被清除,则简单的缓存后端更适合。
如果使用cached_db会话后端,则还需要遵循使用数据库支持的会话的配置说明。
Warning
只有在使用基于Memcached
的缓存后端时,才能使用缓存存储会话。 数据在本地内存缓存后端保存的时间不够长,并且直接使用文件
或数据库
会话比通过文件或数据库缓存后端
发送所有内容会更快。 此外,本地内存缓存后端不是多进程安全的,因此可能不适合生产环境。
使用文件存储会话
使用基于文件的会话,需要将SESSION_ENIGN
设置为'django.contrib.sessions.backends.file'
。还可以设置SESSION_FILE_PATH
,来控制Django存储会话文件的位置,需要检查Web服务器是否有读取和写入该文件的权限。
使用cookie存储会话
使用基于cookie的会话,需要设置SESSION_ENIGN
设置为'django.contrib.sessions.backends.signed_cookies
。会话数据将使用Django的加密签名工具和SECRET_KEY设置进行存储。同时建议设置SESSION_COOKIE_HTTPONLY
为True,防止JS脚本访问存储的数据。
注意:如果SECRET_KEY
没有保密并且正在使用PickleSerializer
,则可能导致任意远程代码执行。
在视图函数中启用session
当SessionMiddleware
被激活时, 每个HttpRequest(每个视图函数的第一个参数)都会有一个类似python 字典表的session
属性。request.session
可以在视图中任何地方使用。
默认情况下,Django使用JSON格式序列化session。可以用SESSION_SERIALIZER
选择其他方式或是自定义的序列化方式,但强烈推荐使用默认的JSON方式。
# 创建或修改 session:
request.session[key] = value
# 获取 session:
request.session.get(key,default=None)
# 删除 session
del request.session[key] # 不存在时报错
session的属性和方法可以查看其基类。
session的使用指南:
- 在request.session上使用普通的Python字符串作为字典键。 这更像是一种惯例而非硬性规则。
- 以下划线开头的会话字典键保留供Django内部使用。
- 不要使用新对象覆盖request.session,也不要访问或设置其属性。 像Python字典一样使用它。
例如使用session来完成最简单的登录、退出功能:
def login(request):
m = Member.objects.get