cookie和session

关于http:

1、http是:无状态、短连接

2、http的请求生命周期:给服务端发送一个请起头,通过域名提取url,通过路由关系匹配,再通过函数+html进行模板加数据渲染,最后返回给用户(响应头+响应体)

3、http发送规定:

(1)请求:
    get请求:没有请求体、数据不能超过1k
    post:有请求体,数据大小没有要求
(2)响应:
    用户在页面看到的内容“字符串”

cookie:

1、cookie的诞生:

cookie不属于http协议范围,由于http协议无法保持状态,但实际情况,我们却又需要“保持状态”,因此cookie就是在这样一个场景下诞生。

2、cookie的工作原理是:

由服务器产生内容,浏览器收到请求后保存在本地;当浏览器再次访问时,浏览器会自动带上cookie,这样服务器就能通过cookie的内容来判断这个是“谁”了。

3、cookie

(1)、是保存在用户浏览器中的键值对(可以放很多)
(2)、服务端可以向用户浏览器写cookie
(3)、客户端每次请求时,会携带cookie

cookie虽然在一定程度上解决了“保持状态”的需求,但是由于cookie本身最大支持4096字节,以及cookie本身保存在客户端,可能被拦截或窃取,因此就需要有一种新的东西,它能支持更多的字节,并且他保存在服务器,有较高的安全性。这就是session。

问题来了,基于http协议的无状态特征,服务器根本就不知道访问者是“谁”。那么上述的cookie就起到桥接的作用。

我们可以给每个客户端的cookie分配一个唯一的id,这样用户在访问时,通过cookie,服务器就知道来的人是“谁”。然后我们再根据不同的cookie的id,在服务器上保存一段时间的私密资料,如“账号密码”等等。

4、cookie的应用:

(1)、投票
(2)、用户登录
补充:

(1)cookie可以设置超时时间

(2)总结而言:cookie弥补了http无状态的不足,让服务器知道来的人是“谁”;但是cookie以文本的形式保存在本地,自身安全性较差;所以我们就通过cookie识别不同的用户,对应的在session里保存私密的信息以及超过4096字节的文本。

(3)cookie和session其实是共通性的东西,不限于语言和框架

之前我们制作一个登陆页面,在验证了用户名和密码的正确性后跳转到后台的页面。但是测试后也发现,如果绕过登陆页面。直接输入后台的url地址也可以直接访问的。这个显然是不合理的。其实我们缺失的就是cookie和session配合的验证。有了这个验证过程,我们就可以实现和其他网站一样必须登录才能进入后台页面了。

先说一下这种认证的机制。每当我们使用一款浏览器访问一个登陆页面的时候,一旦我们通过了认证。服务器端就会发送一组随机唯一的字符串(假设是123abc)到浏览器端,这个被存储在浏览端的东西就叫cookie。而服务器端也会自己存储一下用户当前的状态,比如login=true,username=hahaha之类的用户信息。但是这种存储是以字典形式存储的,字典的唯一key就是刚才发给用户的唯一的cookie值。那么如果在服务器端查看session信息的话,理论上就会看到如下样子的字典

{'123abc':{'login':true,'username:hahaha'}}

因为每个cookie都是唯一的,所以我们在电脑上换个浏览器再登陆同一个网站也需要再次验证。那么为什么说我们只是理论上看到这样子的字典呢?因为处于安全性的考虑,其实对于上面那个大字典不光key值123abc是被加密的,value值{'login':true,'username:hahaha'}在服务器端也是一样被加密的。所以我们服务器上就算打开session信息看到的也是类似与以下样子的东西

{'123abc':dasdasdasd1231231da1231231}

借用一张别的大神画的图,可以更直观的看出来cookie和session的关系

cookie示例:

urls.py

from django.conf.urls import url
from django.contrib import admin from app01 import views urlpatterns = [
url(r'^admin/', admin.site.urls),
url(r'^login/', views.login),
url(r'^classes/', views.classes), ]

 views.py

from django.shortcuts import render,redirect,HttpResponse
import pymysql,json
def classes(request):
res=request.COOKIES.get("ticket")
print(res)
if not res:
return redirect("/login/")
else:
conn = pymysql.connect(host='127.0.0.1', port=3306, user='root', passwd='xyy123', db='day63',charset="utf8")
cursor = conn.cursor(cursor=pymysql.cursors.DictCursor)
cursor.execute("select cid,cname from class")
class_list = cursor.fetchall()
cursor.close()
conn.close()
return render(request,"classes.html",{"class_list":class_list}) def login(request):
if request.method=="GET":
return render(request,"login.html")
else:
username=request.POST.get("username")
password=request.POST.get("password")
if username=="xuyuanyuan" and password=="xyy123":
obj=redirect("/classes/")
obj.set_cookie("ticket","abcdefg")
return obj
else:
return render(request,"login.html")

login.html

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<form method="post" action="/login/">
<input type="text" name="username" ><br>
<input type="text" name="password"><br>
<input type="submit" value="提交">
</form>
</body>
</html>

classes.html

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<table border="1px" class="table table-striped table-bordered table-hover">
<thead>
<tr>
<th>班级ID</th>
<th>班级名称</th>
</tr>
</thead>
<tbody>
{% for i in class_list %}
<tr>
<td>{{ i.cid }}</td>
<td>{{ i.cname }}</td>
</tr>
{% endfor %}
</tbody>
</table>
</body>
</html>

其结果展示:

cookie and session设置过期时间示例:

设置过期时间参数语法:

views.py

from django.shortcuts import render,redirect

# Create your views here.

import datetime

def login(request):
print("COOKIES",request.COOKIES)
print("SESSION",request.session)
if request.method=="POST":
name=request.POST.get("user")
pwd=request.POST.get("pwd")
if name=="xuyuanyuan" and pwd=="xyy123": ret = redirect("/index/")
#设置过期时间,max_age 和 expires 时间要设置的一样。
# ret.set_cookie("username", {"11": "22"})
ret.set_cookie("username", {"11":"22"},max_age=10,expires=datetime.datetime.utcnow()+datetime.timedelta(days=3))
return ret #COOKLE SESSION
# request.session["is_login"]=True
# request.session["user"]=name
# return redirect("/index/") return render(request,"login.html") def index(request): if request.COOKIES.get("username",None):
name = request.COOKIES.get("username",None)
return render(request, "index.html", locals()) # if request.session.get("is_login",None):
# name=request.session.get("user",None)
# return render(request,"index.html",locals()) else:
return redirect("/login/")

  

Session简介:

一、session原理:
客户端来登录,服务端随机生成一个字符串,给客户端一份,服务端保留一份,下次客户端再带上随机的字符串来访问时,服务端则根据这个随机的字符串,反馈给客户端这个字符串所对应的values值(当程序需要为某个客户端的请求创建一个session的时候,服务器首先检查这个客户端的请求里是否已包含了一个session标识 - 称为 session id,如果已包含一个session id则说明以前已经为此客户端创建过session,服务器就按照session id把这个 session检索出来使用(如果检索不到,可能会新建一个),如果客户端请求不包含session id,则为此客户端创建一个session并且生成一个与此session相关联的session id,session id的值应该是一个既不会重复,又不容易被找到规律以仿造的字符串,这个 session id将被在本次响应中返回给客户端保存。 )

应用:依赖cookie
作用:保持会话(Web网站)
好处:敏感信息不会直接给客户端

二、术语session 
session,中文经常翻译为会话,其本来的含义是指有始有终的一系列动作/消息,

1、login页面正确登录的话,后台页面可以获取到浏览器携带的cookie的。

2、第一行的sessionid其实就是cookie值

3、session的内容是加密的,从客户端获取不到session的内容

4、服务端可以通过预设的key值取出session的内容并打印到前段

5、django的session默认是存储在数据库里的,我们再到数据库查看一下真正session内容

示例:

基于session做用户登录:

urls.py

urlpatterns = [
# ========app01里的内容=========
url(r'^admin/', admin.site.urls),
url(r'^login.html$', views.login),
url(r'^index.html$', views.index), ]

views.py

from django.shortcuts import render,redirect,HttpResponse
from app01 import models
def login(request):
if request.method=="GET":
return render(request,"login.html")
else:
username=request.POST.get("uname")
password=request.POST.get("pwd")
obj=models.Userinfo.objects.filter(username=username,pwd=password).first()
if obj:
# 1. 生成随机字符串
# 2. 通过cookie发送给客户端
# 3. 服务端保存
# {
# 随机字符串1: {'username':'alex','email':x''...}
# }
request.session['username'] = obj.username
return redirect('/index.html')
else:
return render(request,"login.html",{"msg":"用户名或密码有误"}) def index(request):
# 1. 获取客户端端cookie中的随机字符串
# 2. 去session中查找有没有随机字符
# 3. 去session对应key的value中查看是否有 username
v = request.session.get('username')
if v:
return HttpResponse('登录成功:%s' %v)
else:
return redirect('/login.html')

login.html

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<h1>用户登录</h1>
<form method="post" action="/login.html">
{% csrf_token %}
<div>
用户名:<input type="text" name="uname">
</div>
<div>
密 码:<input type="password" name="pwd"><br>
</div>
<input type="submit" value="登录">{{ mag }} </form>
</body>
</html>

index.html

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<h1>登录成功</h1>
</body>
</html>

Django中默认支持Session,其内部提供了5种类型的Session供开发者使用:

  • 数据库(默认)
  • 缓存
  • 文件
  • 缓存+数据库
  • 加密cookie

1、数据库Session

Django默认支持Session,并且默认是将Session数据存储在数据库中,即:django_session 表中。

a. 配置 settings.py

    SESSION_ENGINE = 'django.contrib.sessions.backends.db'   # 引擎(默认)

    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,默认修改之后才保存(默认) b. 使用 def index(request):
# 获取、设置、删除Session中数据
request.session['k1']
request.session.get('k1',None)
request.session['k1'] = 123
request.session.setdefault('k1',123) # 存在则不设置
del request.session['k1'] # 所有 键、值、键值对
request.session.keys()
request.session.values()
request.session.items()
request.session.iterkeys()
request.session.itervalues()
request.session.iteritems() # 用户session的随机字符串
request.session.session_key # 将所有Session失效日期小于当前日期的数据删除
request.session.clear_expired() # 检查 用户session的随机字符串 在数据库中是否
request.session.exists("session_key") # 删除当前用户的所有Session数据
request.session.delete("session_key") request.session.set_expiry(value)
* 如果value是个整数,session会在些秒数后失效。
* 如果value是个datatime或timedelta,session就会在这个时间后失效。
* 如果value是0,用户关闭浏览器session就会失效。
* 如果value是None,session会依赖全局session失效策略。

2、缓存Session

a. 配置 settings.py

    SESSION_ENGINE = 'django.contrib.sessions.backends.cache'  # 引擎
SESSION_CACHE_ALIAS = 'default' # 使用的缓存别名(默认内存缓存,也可以是memcache),此处别名依赖缓存的设置 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,默认修改之后才保存 b. 使用 同上

3、文件Session

a. 配置 settings.py

    SESSION_ENGINE = 'django.contrib.sessions.backends.file'    # 引擎
SESSION_FILE_PATH = None # 缓存文件路径,如果为None,则使用tempfile模块获取一个临时地址tempfile.gettempdir() # 如:/var/folders/d3/j9tj0gz93dg06bmwxmhh6_xm0000gn/T 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,默认修改之后才保存 b. 使用 同上

4、缓存+数据库Session

数据库用于做持久化,缓存用于提高效率

a. 配置 settings.py

    SESSION_ENGINE = 'django.contrib.sessions.backends.cached_db'        # 引擎

b. 使用

    同上

5、加密cookie Session

a. 配置 settings.py

    SESSION_ENGINE = 'django.contrib.sessions.backends.signed_cookies'   # 引擎

b. 使用

    同上

  

总结一下cookie和session的知识

一、操作Cookie

  获取cookie:request.COOKIES[key]

  设置cookie:response.set_cookie(key,value)

二、操作Session(session默认在服务器端保存15天)

  获取session:request.session[key]

  设置session:reqeust.session[key] = value

  删除session:del request.session[key]

(这个删除其实就是把数据库的session_data更新为一个其他的值了,并没有立即删除)

request.session.set_expiry(value)
* 如果value是个整数,session会在些秒数后失效。
* 如果value是个datatime或timedelta,session就会在这个时间后失效。
* 如果value是0,用户关闭浏览器session就会失效。
* 如果value是None,session会依赖全局session失效策略。

  

http 之cookie和session的更多相关文章

  1. Cookie和Session的总结

    1.开篇 在之前学习这一段的时候我一直有点没弄清楚,其实对Session这块的理解还可以,但是Cookie感觉始终还是欠缺点火候.之后的很长一段时间都基本上很少用Cookie了,渐渐的也淡忘了这一块的 ...

  2. java的会话管理:Cookie和Session

    java的会话管理:Cookie和Session 1.什么是会话 此处的是指客户端(浏览器)和服务端之间的数据传输.例如用户登录,购物车等 会话管理就是管理浏览器客户端和服务端之间会话过程产生的会话数 ...

  3. Cookie和Session的那些事儿

    Cookie和Session都是为了保持用户的访问状态,一方面为了方便业务实现,另一方面为了简化服务端的程序设计,提高访问性能.Cookie是客户端(也就是浏览器端)的技术,设置了Cookie之后,每 ...

  4. django的cookie和session以及内置信号、缓存

    cookie和session cookie和session的作用: cookie和session都记录了客户端的某种状态,用来跟踪用户访问网站的整个回话.两者最大的区别是cookie的信息是存放在浏览 ...

  5. Cookie和Session的区别

    前言 HTTP是一种无状态的协议,为了分辨链接是谁发起的,就需要我们自己去解决这个问题.不然有些情况下即使是同一个网站我们每打开一个页面也都要登录一下.而Session和Cookie就是为解决这个问题 ...

  6. 本地数据Store。Cookie,Session,Cache的理解。Timer类主要用于定时性、周期性任务 的触发。刷新Store,Panel

    本地数据Store var monthStore = Ext.create('Ext.data.Store', { storeId : 'monthStore', autoLoad : false, ...

  7. Cookie与Session

    再说Cookie与Session之前,先要了解一下http协议. 何为http协议: http协议即超文本传输协议,一种基于浏览器请求与服务器响应的协议,该协议主要的特点就是它是一种无状态的协议(只针 ...

  8. 【转】Cookie和Session区别和联系详解

    会话(Session)跟踪是Web程序中常用的技术,用来跟踪用户的整个会话.常用的会话跟踪技术是Cookie与Session.Cookie通过在客户端记录信息确定用户身份,Session通过在服务器端 ...

  9. 理解Cookie和Session机制(转)

    目录[-] Cookie机制 什么是Cookie 记录用户访问次数 Cookie的不可跨域名性 Unicode编码:保存中文 BASE64编码:保存二进制图片 设置Cookie的所有属性 Cookie ...

  10. cookie 和session 的区别详解

    这些都是基础知识,不过有必要做深入了解.先简单介绍一下. 二者的定义: 当你在浏览网站的时候,WEB 服务器会先送一小小资料放在你的计算机上,Cookie 会帮你在网站上所打的文字或是一些选择, 都纪 ...

随机推荐

  1. 【明哥报错簿】tomcat 安装时出现 Failed to install Tomcat7 service

    安装tomcat时提示 Failed to install Tomcat7 service 应该是卸载时直接删除目录导致的. Failed to install Tomcat7 service Che ...

  2. 【Java】使用CSVUtils生成文件并供下载

    package com.msk.ds.logic; import java.io.*; import java.util.List; /** * Created by Administrator on ...

  3. (转)【Java FTP及FTP服务器搭建】

    转至 http://blog.csdn.net/studyvcmfc/article/details/8147052 目录(?)[+] -[Java FTP及FTP服务器搭建] 一:本文采用apach ...

  4. BZOJ4896 THUSC2016补退选(trie)

    字符串扔进trie,vector记录每个前缀出现次数的最大值的更新记录即可. #include<iostream> #include<cstdio> #include<c ...

  5. CentOS 7下安装pptp服务端手记 ok

    主要配置步骤 1. 安装前检查系统支持 2. 安装必要包 3. 修改相关配置文件 4. 设置开机自动启动 pptpd, iptables 5. iptables配置网络 6. 阿里云ECS可能还需要几 ...

  6. C++操作Windows WIFI

    原文链接地址:https://blog.csdn.net/just_do_1122/article/details/78031024 实现功能     无线网卡列表     无线热点扫面     无线 ...

  7. 康托展开&康托逆展开 的写法

    康托展开 康托展开解决的是当前序列在全排序的名次的问题. 例如有五个数字组成的数列:1,2,3,4,5 那么1,2,3,4,5就是全排列的第0个[注意从0开始计数] 1,2,3,5,4就是第1个 1, ...

  8. HikariPool-1 - Connection is not available, request timed out after XXXXms.

    hikaripool-0-连接不可用,请求在30000ms之后超时.意思是池等待30000ms的免费连接,但是您的应用程序没有返回任何连接. 原因一:连接泄漏(在从池中借用之后连接没有关闭).解决方法 ...

  9. SQL通用优化方案(where优化、索引优化、分页优化、事务优化、临时表优化)

    SQL通用优化方案:1. 使用参数化查询:防止SQL注入,预编译SQL命令提高效率2. 去掉不必要的查询和搜索字段:其实在项目的实际应用中,很多查询条件是可有可无的,能从源头上避免的多余功能尽量砍掉, ...

  10. 洛谷P1078 文化之旅

    P1078 文化之旅 1.1K通过 3.6K提交 题目提供者洛谷OnlineJudge 标签NOIp普及组2012 难度普及+/提高 时空限制1s / 128MB 提交  讨论  题解 最新讨论更多讨 ...