Cookie&&Session:
cookie常见使用
from django.urls import path
from django.shortcuts import HttpResponse
def x1(request):
# 包含:响应体、响应头、状态码等信息
obj = HttpResponse("x1", status=201, reason="OK")
# 设置响应头
obj['name'] = "admin"
# 设置cookie
# import datetime
# ctime = datetime.datetime.now() + datetime.timedelta(seconds=10)
obj.set_cookie("v3", "root", max_age=10, path="/")
obj.set_cookie("v2", "hello")
obj.set_signed_cookie("info", "qwe123") # 签名
return obj
def x2(request):
print(request.COOKIES)
xx = request.get_signed_cookie("info") # 用户不能自己修改cookie的内容
print(xx)
# print(request.COOKIES.get('v1'))
# print(request.COOKIES.get('v2'))
return HttpResponse("x2")
urlpatterns = [
path('x1/', x1, name='x1'),
path('x2/', x2, name='x2'),
]
Cookie的实现:
#HttpResponse的父类
class HttpRequest:
def __setitem__(self, header, value):
self.headers[header] = value
def set_cookie(self,key,value="",...):
self.cookies[key] = value
def get_signed_cookie(self, key, default=RAISE_ERROR, salt="", max_age=None):
cookie_value = self.COOKIES[key]
value = signing.get_cookie_signer(salt=key + salt).unsign(cookie_value, max_age=max_age)
return value
class WSGIRequest(HttpRequest):
def __init__(self, environ):
self.environ = environ
...
@cached_property
def COOKIES(self):
raw_cookie = get_str_from_wsgi(self.environ, "HTTP_COOKIE", "")
return parse_cookie(raw_cookie)
回到入口的call方法:
status = '%d %s' % (response.status_code, response.reason_phrase)
#将字典的数据打散传进去
#在response中读取所有的请求头
#读取所有cookie
response_headers = [
*response.items(),
*(('Set-Cookie', c.output(header='')) for c in response.cookies.values()),
]
v1 = {"name": "张三", "salary": 8000}
print(v1.items())
response_headers = [*v1.items()]
print(response_headers)
WSGIRequest,请求
class WSGIHandler(base.BaseHandler):
request_class = WSGIRequest
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.load_middleware()
def __call__(self, environ, start_response):
set_script_prefix(get_script_name(environ))
signals.request_started.send(sender=self.__class__, environ=environ)
request = self.request_class(environ)
class HttpRequest:
def get_signed_cookie(self, key, default=RAISE_ERROR, salt="", max_age=None):
cookie_value = self.COOKIES[key]
value = signing.get_cookie_signer(salt=key + salt).unsign(cookie_value, max_age=max_age)
return value
class WSGIRequest(HttpRequest):
def __init__(self, environ):
self.environ = environ
...
@cached_property
def COOKIES(self):
raw_cookie = get_str_from_wsgi(self.environ, "HTTP_COOKIE", "")
return parse_cookie(raw_cookie)
Session
############
# SESSIONS #
############
# Session存储在哪里?
SESSION_ENGINE = "django.contrib.sessions.backends.db"
# 如果存储到文件中,文件的路径。
SESSION_ENGINE = "django.contrib.sessions.backends.file"
SESSION_FILE_PATH = None
# 存储到缓存
SESSION_ENGINE = "django.contrib.sessions.backends.cache"
SESSION_CACHE_ALIAS = "default"
# 存储到缓存 + 数据库
SESSION_ENGINE = "django.contrib.sessions.backends.cache_db"
SESSION_CACHE_ALIAS = "default"
# 存储到cookie
SESSION_ENGINE = "django.contrib.sessions.backends.signed_cookies"
# class to serialize session data
SESSION_SERIALIZER = "django.contrib.sessions.serializers.JSONSerializer"
# -------------------------------
# Cookie name. This can be whatever you want.
SESSION_COOKIE_NAME = "sessionid"
# Age of cookie, in seconds (default: 2 weeks).
SESSION_COOKIE_AGE = 60 * 60 * 24 * 7 * 2
# A string like "example.com", or None for standard domain cookie.
SESSION_COOKIE_DOMAIN = None
# Whether the session cookie should be secure (https:// only).
SESSION_COOKIE_SECURE = False
# The path of the session cookie.
SESSION_COOKIE_PATH = "/"
# Whether to use the HttpOnly flag.
SESSION_COOKIE_HTTPONLY = True
# Whether to set the flag restricting cookie leaks on cross-site requests.
# This can be 'Lax', 'Strict', 'None', or False to disable the flag.
SESSION_COOKIE_SAMESITE = "Lax"
# Whether to save the session data on every request.
SESSION_SAVE_EVERY_REQUEST = False
# Whether a user's session cookie expires when the web browser is closed.
SESSION_EXPIRE_AT_BROWSER_CLOSE = False
- 注意:如果是非数据库,可以主调用app的注册代码部分。
- 请求=登录,生成Session、Cookie。
- 再次请求,默认携带cookie,根据Cookie中的凭证,去找到Session中原本存储的数据。
演示
MIDDLEWARE = [
'django.middleware.security.SecurityMiddleware',
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
]
django启动,加载
class SessionMiddleware(MiddlewareMixin):
# RemovedInDjango40Warning: when the deprecation ends, replace with:
# def __init__(self, get_response):
def __init__(self, get_response=None):
super().__init__(get_response)
engine = import_module(settings.SESSION_ENGINE)
self.SessionStore = engine.SessionStore
请求发出:
```python
def process_request(self, request):
# 1.去Cookie中读取凭证 mid="123456"
session_key = request.COOKIES.get(settings.SESSION_COOKIE_NAME)
# 2.实例化
request.session = self.SessionStore(session_key)
这里我用数据库
SESSION_ENGINE = "django.contrib.sessions.backends.db"
mysql
create database temp_session charset utf8 collate utf8_general_ci;
#settings.py
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.mysql',
'NAME': 'temp_session', # 数据库名字
'USER': 'root',
'PASSWORD': 'root123',
'HOST': '127.0.0.1', # 那台机器安装了MySQL
'PORT': 3306,
}
}
#urls.py
from django.urls import path
from django.shortcuts import HttpResponse
def x1(request):
request.session['id'] = 999
# 类中的__setitem__
request.session['name'] = 'admin'
request.session['age'] = '25'
return HttpResponse("x1")
urlpatterns = [
path('x1/', x1, name='x1'),
]
随便访问一个路由