zoukankan      html  css  js  c++  java
  • cookie与session

    cookie 与 session:

    cookie 与 session 原理:
    
    ​	1.保存客户端的用户状态
    
    ​	2.产生原因 : HTTP协议是无状态的(不会保存用户的状态)
    
    cookie介绍 ;
    	指的是一段小信息,它是服务器发送出来存储在浏览器上的一组组键值对,下次访问服务器时浏览器会自动携带这些键值对,以便服务器提取有用信息
    
    cookie查看 : 在浏览器上开发者模式,Network--->all---> Cookie
    
    优点 :  服务端不用存储用户数据,减轻了服务器的压力
    
    缺点 :  信息保存在客户端,信息不安全性增加(web领域内没有一定的安全)
    
    

    django内操作Cookie

    django内操作Cookie:
        #获取cookie : 
        request.COOKIES['key']    获取普通版cookie
        
    	加盐版cookie (加密)
    	request.get_signed_cookie(key,default=RAISE_ERROR,salt='',max_age=None)
        
        参数 : default :默认值  salt: 加密盐('')  max_age : 后台控制过期时间(单位:秒)
    
    	#设置Cookie :
        1.方式一 : 在view.py中给返回给客户端的响应数据中设置Cookie
        rep = HttpResponse(...)  #获取 HttpResponse对象
    	rep = render(request,...)   
    	rep.set_cookie(key,value....)   #键值对形式
    
    	2.方式二 :在view.py中给返回给客户端的响应数据中设置Cookie
        rep = HttpResponse(....)
    	rep = render(request,...)
    	rep.set_signed_cookie(key,value,salt='添加加密盐',....) 
    
    	#删除cookie :
        def logout(request):
            rep = redirect('/login/')
            rep.delete_cookie('user')   # 清除客户端的cookie数据
            return rep
    
    参数:
    	key : 键   value : 值   
    	path = '/': Cookie生效的路径,/ 表示根路径,根路径的cookie可以被任何url的页面访问
    	demain = None , Cookie生效的域名
        secure = False, http传输
        httponly = False 只能http协议传输,无法被JavaScript获取
    

    设置超时时间:

    #设置超时时间:
      max_age 与 expires的区别:
    	max_age = 秒    (不支持IE 浏览器)
        expires = 秒    (支持IE   浏览器)
        
        
        max_age : 超时时间 
        request.session.set_expiry(value)
        value : 整数 , datetime , none (django内的时间为准), 0 (关闭页面消失)
    	request.session.set_expiry(value)
    				* 如果value是个整数,session会在些秒数后失效。
    				* 如果value是个datatime或timedelta,session就会在这个时间后失效。
    				* 如果value是0,用户关闭浏览器session就会失效。
    				* 如果value是None,session会依赖全局session失效策略。
    注意:在django内默认的expire_data : 超时时间(2周)
    

    cookie版登录:

    from  functools import wraps
    def check_login(func):
        @wraps(func)
        def inner(request,*args,**kwargs):
            next_url = request.get_full_path()
            if request.get_signed_cookie('login',salt='sss',default=None) == 'yes':
                return func(request,*args,**kwargs)
            else:
                return redirect("login/?next={}".format(next_url))
        return inner
    
    
    def login(request):
        if request.method == 'POST':
            username = request.POST.get('username')
            password = request.POST.get('password')
            if username == 'jason' and password == "123":
                next_url = request.GET.get('next')
                if next_url and next_url!= '/logout/':
                    response = redirect(next_url)
                else:
                    response = redirect('class_list')
                response.set_signed_cookie('login','yes',salt='sss')
                return response
        return render(request,'login.html')
    
    request.path_info   #只获取 url
    request.get_full_path()  # 获取url + get 请求参数
    

    session:

    session介绍:
    
    -cookie 的缺陷 : Cookie本身最大支持4096字节,以及Cookie本身保存在客户端,可能被拦截或窃取
    
    -session : 保存私密的信息以及超过4096字节的文本。保存在服务端
        	  --》工作机制需要依赖于cookie,在限定时间内 同一种上浏览器的session值相同,且在django内自动创建(django_session表 --需手动同步数据库),一种浏览器就对应一条数据
    
     创建session所发生的事件:
        1.djang内部自动帮你调用算法生成一个随机的字符串
        2.在django_session添加数据(数据也是加密处理)
        随机字符串         加密之后的数据           失效时间
        ashdjsad(key)         jsadsada(value)       set_expiry(value) 默认2周
        3.将产生的随机字符串返回给客户端浏览器 让浏览器保存
        sessionid:随机字符串
    

    session相关方法:

    #1. 获取 , 设置 , 删除 session内的数据
    request.session['k1']= v1
    .... 注意 : 先执行同步数据库命令生成django_session表;
    
    request.session.get('k1')  
    
    #删除: 
    request.session.delete()    删除双方的所有session(只删除单个浏览器上的对应的数据) 
    request.session.flush()    删除客服端 (推荐)
    
    #2.所有 键、值、键值对
    request.session.keys()
    request.session.values()
    request.session.items()
    request.session.iterkeys()
    request.session.itervalues()
    request.session.iteritems()
    
    # 会话session的key
    request.session.session_key
    
    # 将所有Session失效日期小于当前日期的数据删除
    request.session.clear_expired()
    
    # 检查会话session的key在数据库中是否存在
    request.session.exists("session_key")
    
    # 删除当前会话的所有Session数据
    request.session.delete()
      
    # 删除当前的会话数据并删除会话的Cookie。
    request.session.flush() 
        这用于确保前面的会话数据不可以再次被用户的浏览器访问
        例如,django.contrib.auth.logout() 函数中就会调用它
    
    注意: django session 创建数据的时候,针对的是浏览器(创建数据的数据)
    -->服务端数据只识别浏览器,不识别客服端的操作者!!!
    

    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,默认修改之后才保存(默认)
    
    

    session版登录验证:

    from  functools import wraps
    
    def check_login(func):
        @wraps(func)
        def inner(request,*args,**kwargs):
            next_url = request.get_full_path()
            if request.session.get('user'):
                return func(request,*args,**kwargs)
            else:
                return redirect('/login/?next={}'.format(next_url))
    
    def login(request):
        if request.method == 'POST':
            user = request.POST.get('user')
            pwd = request.POST.get('pwd')
    
            if user == 'jason' and pwd == '123':
    
                request.session['user'] =  user
                next_url = request.GET.get('next')
    
                if next_url:
                    return redirect(next_url)
    
                else:
                    return redirect(request,'login/html')
    
    @check_login
    def logout(request):
        request.session.delete()
    
        return redirect('/login')
    @check_login
    def index(request):
        current_user = request.session.get('user',None)
        return render(request,'index.html',locals())
    
    

    token

    -能够作为数据库 : 
    	1. 数据库软件 (关系型 , 非关系型)
        2. 文件 , 内存
        
        
     --》多用户下处理认证的最佳方式。
    
    产生原因 :
        1.Seesion:每次认证用户发起请求时,服务器需要去创建一个记录来存储信息。当越来越多的用户发请求时,内存的开销也会不断增加。
    
        2.可扩展性:在服务端的内存中使用Seesion存储登录信息,伴随而来的是可扩展性问题。
    
        3.CORS(跨域资源共享):当我们需要让数据跨多台移动设备上使用时,跨域资源的共享会是一个让人头疼的问题。在使用Ajax抓取另一个域的资源,就可以会出现禁止请求的情况。
    
        4.CSRF(跨站请求伪造):用户在访问银行网站时,他们很容易受到跨站请求伪造的攻击,并且能够被利用其访问其他的网站。
       
    Token的优点 :
         1.无状态 ,可扩展 :客户端存储的Tokens是无状态的,并且能够被扩展
    
         2.安全性 :请求中发送token而不再是发送cookie能够防止CSRF(跨站请求伪造)
    
         3.可扩展性 :能够创建与其它程序共享权限的程序
    
         4.多平台跨域  :用户有一个通过了验证的token,数据和资源就能够在任何域上被请求到。
    
    流程:
        1.用户登录校验,校验成功后就返回Token给客户端。
    
        2.客户端收到数据后保存在客户端
    
        3.客户端每次访问API是携带Token到服务器端。
    
        4.服务器端采用filter过滤器校验。校验成功则返回请求数据,校验失败则返回错误码
    
    
  • 相关阅读:
    POJ 1611 The Suspects
    POJ 2001 Shortest Prefixes(字典树)
    HDU 1251 统计难题(字典树 裸题 链表做法)
    G++ C++之区别
    PAT 乙级 1013. 数素数 (20)
    PAT 乙级 1012. 数字分类 (20)
    PAT 乙级 1009. 说反话 (20)
    PAT 乙级 1008. 数组元素循环右移问题 (20)
    HDU 6063 17多校3 RXD and math(暴力打表题)
    HDU 6066 17多校3 RXD's date(超水题)
  • 原文地址:https://www.cnblogs.com/shaozheng/p/11985012.html
Copyright © 2011-2022 走看看