Day22-session

Posted momo8238

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Day22-session相关的知识,希望对你有一定的参考价值。

 

1. cookie: 保存在用户浏览器端的一个键值对。基于cookie做用户验证的时候,不适合把敏感信息放到cookie中。例如我们可以把user_id这个不敏感的信息放到cookie中,然后基于user_id这个不敏感的信息再在session中做一次数据库查询,再查询到敏感信息(账户余额,密码等)。这样就把保存敏感信息的任务交给了服务器端,也提高了安全性

session:保存在服务器端的键值对,还得依赖于cookie。session在内部维护的就是一个大的字典。

下面这些信息保存在服务器端的内存里面,下次用户来的时候只需提供随机字符串,与服务器端的进行匹配。匹配成功,就可以提取此用户的敏感信息了。

 

 

 

 

 

2. 基于session来实现用户登录。搭建环境请参考:http://www.cnblogs.com/momo8238/p/7508677.html

3.  写 login.html, index.html 2个页面备用。

login.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
    <form action="/login/" method="POST" >
        <input type="text" name="user" placeholder="user"/>
        <input type="text" name="pwd" placeholder="pwd"/>
        <input type="submit" value="提交"/>
    </form>
</body>
</html>

 views.py

from django.shortcuts import render,HttpResponse,redirect
# Create your views here.
def login(request):
    if request.method==\'GET\':
        return render(request,\'login.html\')
    elif request.method==\'POST\':
        user=request.POST.get(\'user\')
        pwd=request.POST.get(\'pwd\')
        if user==\'root\' and pwd==\'123\':
            return redirect(\'/index/\')
        else:
            return render(request,\'login.html\')
def index(request):
    return HttpResponse(\'OK\')

 此时没有加任何验证信息,所以直接访问index页面也是可以的。无需登录

 

 

4. 增加验证信息。

 

4.1 说明:

request.session[\'username\']=user   表示设置值

 

request.session.setdefault(\'username\',123)=user   表示如果值不存在,则设置默认值;如果值已经存在的话,那就不设置了。

 

request.session[\'username\']  后面没有等号,表示去session中获取值,如果不存在的话,则会报错。

request.session.get(\'username\',None)  后面没有等号,表示去session中获取值,如果不存在的话,则返回None,不会报错。

 

del request.session[\'k1\']  表示删除值

 

 

 

 

在Django内部运行session之前,一定要先运行以下两句生成表。

python manage.py makemigrations

python manage.py migrate

 

 

 

 

4.2 运行server,如果用户名和密码正确,在浏览器端就能生成Cookies。

 

 

 

同时,在服务器端生成了session,Django里面的session默认是保存在数据库中的(还可以保存在文件,缓存,内存中)。打开数据库就可以看到了。后面的字符串是经过加密了的。

 

 

 

4.3  用户相关的信息都放到request.session里面了。如果登录成功,就在index页面显示用户名。

from django.shortcuts import render,HttpResponse,redirect
# Create your views here.
def login(request):
    if request.method==\'GET\':
        return render(request,\'login.html\')
    elif request.method==\'POST\':
        user=request.POST.get(\'user\')
        pwd=request.POST.get(\'pwd\')
        if user==\'root\' and pwd==\'123\':
            #在session里面设置值
            request.session[\'username\']=user
            request.session[\'is_login\']=True
            return redirect(\'/index/\')
        else:
            return render(request,\'login.html\')
def index(request):
    #获取当前用户的随机字符串
    #根据随机字符串获取对应的信息
    #去session中获取值,如果登录成功,显示用户名
    if request.session[\'is_login\']:
        return HttpResponse(request.session[\'username\'])
    else:
        return HttpResponse(\'滚\')

 效果:

 

程序粘贴:

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\'^index/$\', views.index),
]

 views.py

from django.shortcuts import render,HttpResponse,redirect
# Create your views here.
def login(request):
    if request.method==\'GET\':
        return render(request,\'login.html\')
    elif request.method==\'POST\':
        user=request.POST.get(\'user\')
        pwd=request.POST.get(\'pwd\')
        if user==\'root\' and pwd==\'123\':
            #在session里面设置值
            request.session[\'username\']=user
            request.session[\'is_login\']=True
            return redirect(\'/index/\')
        else:
            return render(request,\'login.html\')
def index(request):
    #获取当前用户的随机字符串
    #根据随机字符串获取对应的信息
    #去session中获取值,如果登录成功,显示用户名
    if request.session[\'is_login\']:
        return HttpResponse(request.session[\'username\'])
    else:
        return HttpResponse(\'滚\')

 login.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
    <form action="/login/" method="POST" >
        <input type="text" name="user" placeholder="user"/>
        <input type="text" name="pwd" placeholder="pwd"/>
        <input type="submit" value="提交"/>
    </form>
</body>
</html>

 

4.4 添加“注销“的功能:request.session.clear()

把服务器端里面的随机字符串清除掉,用户再登录的时候,就无法匹配了。

常用语法:

    def index(request):
        # 获取、设置、删除Session中数据
        request.session[\'k1\'] #如果不存在,则报错。
        request.session.get(\'k1\',None) #如果不存在,则返回None
        request.session[\'k1\'] = 123 #对它进行设置值,如果不存在则创建,如果存在则更新。
        request.session.setdefault(\'k1\',123) # 存在则不设置

 


        del request.session[\'k1\']  #删除

  request.session.delete("session_key") # 删除当前用户的所有Session数据
 
        # 所有 键、值、键值对
        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")
 
  del request.session[\'k1\']  #删除掉某一条数据
        request.session.clear() #注销的时候,执行这句
   request.session.delete("session_key") # 删除当前用户的所有Session数据
   request.session.delete("request.session.session_key") # 删除当前用户的所有Session数据

 

示例效果:

 

需要说明的地方:

request.session.clear()-------清空session中的所有数据
request 包含了用户发来的所有数据,可以通过
<h1>欢迎登录:{{request.session.username}}</h1> 直接在前端获取到username的值

views.py
from django.shortcuts import render,HttpResponse,redirect
# Create your views here.
def login(request):
    if request.method==\'GET\':
        return render(request,\'login.html\')
    elif request.method==\'POST\':
        user=request.POST.get(\'user\')
        pwd=request.POST.get(\'pwd\')
        if user==\'root\' and pwd==\'123\':
            #生成随机字符串,写到浏览器cookie中,保存在session中。在随机字符串对应的字典中设置相关内容...
            # 在session里面设置值
            request.session[\'username\']=user
            request.session[\'is_login\']=True
            return redirect(\'/index/\')
        else:
            return render(request,\'login.html\')
def index(request):
    #获取当前用户的随机字符串
    #根据随机字符串获取对应的信息
    #去session中获取值,如果登录成功,显示用户名
    if request.session.get(\'is_login\',None):
        #return HttpResponse(request.session[\'username\'])
        return render(request,\'index.html\',{\'username\':request.session[\'username\']})
    else:
        return HttpResponse(\'滚\')
def logout(request):
    request.session.clear()
    return redirect(\'/login/\')

index.html
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
    <h1>欢迎登录:{{username}},{{request.session.username}}</h1>
    <a href="/logout/">注销</a>
</body>
</html>

 login.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
    <form action="/login/" method="POST" >
        <input type="text" name="user" placeholder="user"/>
        <input type="text" name="pwd" placeholder="pwd"/>
        <input type="submit" value="提交"/>
    </form>
</body>
</html>

 

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\'^index/$\', views.index),
    url(r\'^logout/$\', views.logout),
]

 


4.5 给sessionid 设置超时时间。

在django里面默认session的超时时间是2周,

 

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

 人为设置超时时间的效果:

 

 代码:

views.py

from django.shortcuts import render,HttpResponse,redirect
# Create your views here.
def login(request):
    if request.method==\'GET\':
        return render(request,\'login.html\')
    elif request.method==\'POST\':
        user=request.POST.get(\'user\')
        pwd=request.POST.get(\'pwd\')
        if user==\'root\' and pwd==\'123\':
            #生成随机字符串,写到浏览器cookie中,保存在session中。在随机字符串对应的字典中设置相关内容...
            # 在session里面设置值
            request.session[\'username\']=user
            request.session[\'is_login\']=True
            if request.POST.get(\'remember\',None)==\'1\': #设置超时时间
                request.session.set_expiry(10)
            return redirect(\'/index/\')
        else:
            return render(request,\'login.html\')
def index(request):
    #获取当前用户的随机字符串
    #根据随机字符串获取对应的信息
    #去session中获取值,如果登录成功,显示用户名
    if request.session.get(\'is_login\',None):
        #return HttpResponse(request.session[\'username\'])
        return render(request,\'index.html\',{\'username\':request.session[\'username\']})
    else:
        return HttpResponse(\'滚\')
def logout(request):
    request.session.clear()
    return redirect(\'/login/\')

 index.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
    <h1>欢迎登录:{{username}},{{request.session.username}}</h1>
    <a href="/logout/">注销</a>
</body>
</html>

 login.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
    <form action="/login/" method="POST" >
        <input type="text" name="user" placeholder="user"/>
        <input type="text" name="pwd" placeholder="pwd"/>
        <input type="checkbox" name="remember" value="1"/> 10秒免登录
        <input type="submit" value="提交"/>
    </form>
</body>
</html>

 

修改默认超时时间---在setting里面做修改。

每次用户发来请求的时候,都需要更新一下超时时间。超时时间的起点应该是每次用户操作完开始计算,而不应该是第一次登录的时间点为起点。

SESSION_SAVE_EVERY_REQUEST = False            # 是否每次请求都保存Session,默认修改之后才保存(默认)。最后一次操作10秒后再失效。

 

 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过期(默认)
    set_cookie(\'k\',123)                                      #没有写超时时间,默认情况下就是关闭浏览器,cookie失效。
 SESSION_SAVE_EVERY_REQUEST = False                       # 是否每次请求都保存Session,默认修改之后才保存(默认)

 

 

 

5.session的基本操作

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

  • 数据库(默认) #把session存在数据库中
  • 缓存
  • 文件
  • 缓存+数据库
  • 加密cookie

数据库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")

 

缓存session

 

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

 

文件session

配置 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. 使用
 
    同上

 

缓存+数据库Session

数据库用于做持久化,缓存用于提高效率。先去数据库中找,找到的话,直接用;找不到的话,到数据库中去找,然后再在缓存中放一份。

a. 配置 settings.py
 
    SESSION_ENGINE = \'django.contrib.sessions.backends.cached_db\'        # 引擎
 
b. 使用
 
    同上

 

 

加密cookie Session

a. 配置 settings.py
     
    SESSION_ENGINE = \'django.contrib.sessions.backends.signed_cookies\'   # 引擎
 
b. 使用

 

以上是关于Day22-session的主要内容,如果未能解决你的问题,请参考以下文章

day06-jsp

[code] PTA 胡凡算法笔记 DAY039

list(), if 和短路评估

DAY9-字符串笔记整理2018-1-19

微信小程序代码片段

VSCode自定义代码片段——CSS选择器