Django 简明教程
Django - Sessions
如前所述,我们可以使用客户端 cookie 为 Web 应用程序存储大量有用的数据。我们之前已经看到,我们可以使用客户端 cookie 为 Web 应用程序存储各种有用的数据。这会产生许多安全漏洞,具体取决于你想要保存的数据的重要性。
出于安全原因,Django 有一个会话框架,用于处理 cookie。会话用于抽象 cookie 的接收和发送,数据保存在服务器端(如在数据库中),并且客户端 cookie 只拥有一个用于标识的会话 ID。会话对于避免用户浏览器设置为“不接受”cookie 的情况也很有用。
Setting Up Sessions
在 Django 中,会话启用在你的项目 settings.py 中完成,通过向 MIDDLEWARE_CLASSES 和 INSTALLED_APPS 选项添加几行。这应该在创建项目时完成,但了解它总是好的,所以 MIDDLEWARE_CLASSES 应有:
'django.contrib.sessions.middleware.SessionMiddleware'
而 INSTALLED_APPS 应有:
'django.contrib.sessions'
默认情况下,Django 将会话信息保存在数据库中(django_session 表或集合),但你可以配置引擎以使用其他方式存储信息,如在 file 或 cache 中。
当会话启用时,每个请求(Django 中任何视图的第一个参数)都会有一个会话(dict)属性。
我们创建一个简单的示例,看看如何创建和保存会话。我们之前构建了一个简单的登录系统(请参阅 Django 表单处理章节和 Django Cookie 处理章节)。让我们将用户名保存在一个 cookie 中,因此如果不是注销,在访问登录页面时,你将看不到登录表单。基本上,让我们通过在服务器端保存 cookie 来使我们在 Django Cookie 处理中使用的登录系统更加安全。
为此,首先让我们更改登录视图以将我们的用户名 cookie 保存到服务器端:
def login(request):
username = 'not logged in'
if request.method == 'POST':
MyLoginForm = LoginForm(request.POST)
if MyLoginForm.is_valid():
username = MyLoginForm.cleaned_data['username']
request.session['username'] = username
else:
MyLoginForm = LoginForm()
return render(request, 'loggedin.html', {"username" : username}
然后,让我们为登录表单创建 formView 视图,如果设置了 cookie,我们不会显示表单:
def formView(request):
if request.session.has_key('username'):
username = request.session['username']
return render(request, 'loggedin.html', {"username" : username})
else:
return render(request, 'login.html', {})
现在,让我们更改 url.py 文件以更改该 URL,以便它与我们的新视图配对:
from django.conf.urls import patterns, url
from django.views.generic import TemplateView
urlpatterns = patterns('myapp.views',
url(r'^connection/','formView', name = 'loginform'),
url(r'^login/', 'login', name = 'login'))
当你访问 /myapp/connection 时,你将看到以下页面:
你将被重定向到以下页面:
现在,如果你再次尝试访问 /myapp/connection,你将直接被重定向到第二个屏幕。
我们创建一个简单的注销视图来抹除我们的 cookie。
def logout(request):
try:
del request.session['username']
except:
pass
return HttpResponse("<strong>You are logged out.</strong>")
并将其与 myapp/url.py 中的注销 URL 配对:
url(r'^logout/', 'logout', name = 'logout'),
现在,如果你访问 /myapp/logout,你将看到以下页面:
如果你再次访问 /myapp/connection,你将获得登录表单(屏幕 1)。