Django(cookie和session)
一.cookie
1.cookie的简单认识
http是无状态的,Cookies是作为http的一个扩展诞生的,其主要用途是弥补http的无状态特性。提供了一种保持客户端与服务器端之间状态的途径。
在程序中,会话跟踪是很重要的事情。理论上,一个用户的所有请求操作都应该属于同一个会话,而另一个用户的所有请求操作则应该属于另一个会话,二者不能混淆。
2.cookie原理
浏览器访问服务端,带着一个空的cookie,然后由服务器产生内容(set_cookie),浏览器收到相应后保存在本地(也就是本地磁盘);当浏览器再次访问时,浏览器会自动带上Cookie,这样服务器就能通过Cookie的内容来判断这个是“谁”了。
3.Djanog设置cookie实例
<form action="/login/" method="POST"> <p>用户名<input type="text" name="username"></p> <p>密码<input type="password" name="password"></p> <p><input type="submit"></p> </form> -------------index.html <h1>hhhhh</h1> {{ user }} -------------urls.py urlpatterns = [ path('admin/', admin.site.urls), path('login/',views.login), path('index/',views.index), ] --------------views.py def login(req): if req.method=="POST": user=req.POST.get("username") pwd=req.POST.get("password") if user=="root" and pwd=="root": rep=redirect("/index") #redirect参数是找urls.py中的url rep.set_cookie("username",user,max_age=10) #设置cookie return rep #返回index.html界面 return render(req,"login.html") def index(req): user=req.COOKIES.get("username") #从cookie中取数据,如果cookie已经存在,在浏览器直接输入127.0.0.1:8000/index就会直接返回index.html界面 if user: #如果cookie中有数据就返回index.html界面 return render(req,"index.html",{"user":user}) else: return redirect("/login") 一般我们都是从登陆界面输入账号密码后进入index.html界面,这时已经创建好了cookie,在index函数中直接取cookie就行了,但是如果cookie已经存在(login函数执行过了),在浏览器直接输入127.0.0.1:8000/index就会直接返回index.html界面
获取cookie
request.COOKIES['key']
设置cookie
设置的cookie是针对于同一域名:端口的当前项目而言的,设置时注意参数path和domain,拿path举例:当path="/index",只有在/index对应的函数下才可获取到设置的cookie,其他视图函数是无法获取到的。domain="www.xxx.com"也是同理,只有此域名下的所有视图函数可获取到前端传来的cookie。从这里也可看到cookie不能跨域使用
rep = HttpResponse(...) rep = render(request, ...) rep.set_cookie(key,value,...) rep.set_signed_cookie(key,value,salt='加密盐', max_age=None, ...)
删除cookie
def logout(request): rep = redirect("/login/") rep.delete_cookie("user") # 删除用户浏览器上之前设置的usercookie值 return rep
4.通过js设置cookie
document.cookie = "k1=wyxx;path=/"
5.通过jquery设置cookie
1.引入jquery.js
<script src="//cdn.bootcss.com/jquery/1.12.4/jquery.js"></script>
2.引入jquery cookie插件
<script src="//cdn.bootcss.com/jquery-cookie/1.4.1/jquery.cookie.min.js"></script>
3.调用插件封装好的方法
a)设置新的cookie:
$.cookie('name','dumplings'); //设置一个值为'dumplings'的cookie
设置cookie的生命周期
$.cookie('key', 'value', { expires: 7 }); //设置为7天,默认值:浏览器关闭
设置cookie的域名:
$.cookie('name','dumplings', {domain:'qq.com'}); //设置一个值为'dumplings'的在域名'qq.com'的cookie
设置cookie的路径:
$.cookie('name','dumplings', {domain:'qq.com',path:'/'});
//设置一个值为'dumplings'的在域名'qq.com'的路径为'/'的cookie
b)删除cookie
$.removeCookie('name',{ path: '/'}); //path为指定路径,直接删除该路径下的cookie
$.cookie('name',null,{ path: '/'}); //将cookie名为‘openid’的值设置为空,实际已删除
c)获取cookie
$.cookie('name') //dumplings
二.session
1.简单认识
Session是另一种记录客户状态的机制,不同的是Cookie保存在客户端浏览器中,而Session保存在服务器上。客户端浏览器访问服务器的时候,服务器把客户端信息以某种形式记录在服务器上。这就是Session。客户端浏览器再次访问时只需要从该Session中查找该客户的状态就可以了。
2.实现本质
3.Django设置session实例
from django.shortcuts import render,redirect # Create your views here. def login(req): if req.method == "POST": username = req.POST.get("user") password = req.POST.get("pwd") if username == "alex" and password =="alex123": req.session['user_name'] = "jjjj" req.session['user_pwd'] = "xxww" return redirect("/index/") return render(req,"login.html") def index(req): if req.session['user_name'] == 'jjjj': #if req.session。get('user_name') == 'jjjj': return render(req,"index.html") else: return render(req,"login.html")
获取session
request.session['k1'] request.session.get('k1',None) #request.session这句是帮你从浏览器的cookies里面将sessionid的值fgs423td取出来,将django-session表里面session_key字段的值为此fgs423td的对应那条记录中的session-data字段的数据给你拿出来(并解密),get方法就取出k1这个键对应的值
设置session
#设置值的时候生成随机字符串(假设为fgs423td),默认在django-session表中添加三个字段值(session_key,session_data,expire_date)分别为(fgs423td,加密后的{k1:123},过期时间),将随机字符串以{sessonid:fgs423td}形式返回给浏览器 request.session['k1'] = 123 request.session.setdefault('k1',123) # 存在则不设置
删除session
del request.session['k1'] #django-session表里面同步删除 request.session.flush()
其他操作
# 所有 键、值、键值对 request.session.keys() request.session.values() request.session.items() # 会话session的key session_key = request.session.session_key 获取sessionid的值 # 将所有Session失效日期小于当前日期的数据删除,将过期的删除 request.session.clear_expired() # 检查会话session的key在数据库中是否存在 request.session.exists("session_key") #session_key就是那个sessionid的值 # 删除当前会话的所有Session数据 request.session.delete() # 删除当前的会话数据并删除会话的Cookie。 request.session.flush() #常用,清空所有cookie---删除session表里的这个会话的记录, 这用于确保前面的会话数据不可以再次被用户的浏览器访问 例如,django.contrib.auth.logout() 函数中就会调用它。 # 设置会话Session和Cookie的超时时间 request.session.set_expiry(value) * 如果value是个整数,session会在些秒数后失效。 * 如果value是个datatime或timedelta,session就会在这个时间后失效。 * 如果value是0,用户关闭浏览器session就会失效。 * 如果value是None,session会依赖全局session失效策略。
4.Django中session配置
1. 数据库Session SESSION_ENGINE = 'django.contrib.sessions.backends.db' # 引擎(默认) 2. 缓存Session SESSION_ENGINE = 'django.contrib.sessions.backends.cache' # 引擎 SESSION_CACHE_ALIAS = 'default' # 使用的缓存别名(默认内存缓存,也可以是memcache),此处别名依赖缓存的设置 3. 文件Session SESSION_ENGINE = 'django.contrib.sessions.backends.file' # 引擎 SESSION_FILE_PATH = None # 缓存文件路径,如果为None,则使用tempfile模块获取一个临时地址tempfile.gettempdir() 4. 缓存+数据库 SESSION_ENGINE = 'django.contrib.sessions.backends.cached_db' # 引擎 5. 加密Cookie Session SESSION_ENGINE = 'django.contrib.sessions.backends.signed_cookies' # 引擎 其他公用设置项: SESSION_COOKIE_NAME = "sessionid" # Session的cookie保存在浏览器上时的key,即:sessionid=随机字符串(默认) SESSION_COOKIE_PATH = "/" # Session的cookie保存的路径(默认) SESSION_COOKIE_DOMAIN = None # Session的cookie保存的域名(默认) SESSION_COOKIE_SECURE = False # 是否Https传输cookie(默认) SESSION_COOKIE_HTTPONLY = True # 是否Session的cookie只支持http传输(默认) SESSION_COOKIE_AGE = 1209600 # Session的cookie失效日期(2周)(默认) SESSION_EXPIRE_AT_BROWSER_CLOSE = False # 是否关闭浏览器使得Session过期(默认) SESSION_SAVE_EVERY_REQUEST = False # 是否每次请求都保存Session,默认修改之后才保存(默认)
5.session缺陷
当服务端设置了负载均衡,可能首次登录session保存在服务A端,再次请求时请求的是服务B,服务B端无存储的session
三.cookie、session、token区别
token认识结合:https://www.cnblogs.com/gaoyukun/articles/11801822.html#_label7
三者区别参考:https://baijiahao.baidu.com/s?id=1705430412910145531&wfr=spider&for=pc
首先知道三者产生的原因:
cookie:因为http是无状态协议,cookie是为了保持会话技术而产生
session:cookie保存在浏览器端不安全,因此产生了session,session是放在服务端的,基于cookie。
token:平常我们会把session存放在一个公共的库中,这样设置集群时,都去请求这个公共库即可,但是每个浏览器携带一个sessionid,公共库中就不止了,再一个原因如果公共库挂了,所有用户需要重新登,因此产生了token,token不会在服务端保存,只是提供了对应的算法,每次浏览器请求时携带token,服务端都会进行计算从而来对照得到的值是否相同,这是以cpu的计算能力来取代session的存储空间。
区别:
cookie不支持跨域(服务端设置cookie也不可能同时设置多个域名或path)
token支持跨域