10、flask-會話-session

little小新發表於2024-07-07

session會話

是一種伺服器端的會話技術、依賴於cookie
特點:
- 服務端的會話技術
- 所有資料儲存在伺服器中
- 預設儲存在記憶體中
- 儲存結構也是key-value形式的鍵值對
- session是離不開cookie的

Flask中的session是全域性物件

常用操作:
- 設定seesion:
    - seesion['key'] = value
- 獲取seesion:
    - seesion.get(key, default=None)    #根據鍵獲取會話的值
- 刪除seesion:
    - session.pop(key) 刪除某一個值
    - session.clear()    清除所有的session

cookie與session的區別:
- cookie
    - 在瀏覽器儲存
    - 安全性較低
    - 可以減輕伺服器壓力
- seesion:
    - 在伺服器段儲存
    - 安全性高
    - 對伺服器要求較高
    - 依賴cookie

__init__.py

#__init__.py: 初始化檔案、用來建立flask應用
import datetime

from flask import Flask
from .views import blue     #藍圖

def create_app():
    app = Flask(__name__)   #建立flask應用

    #註冊藍圖
    app.register_blueprint(blueprint=blue)

    # session配置
    print(app.config)
    '''
    <Config {'
    DEBUG': False, 
    'TESTING': False, 
    'PROPAGATE_EXCEPTIONS': None, 
    'SECRET_KEY': None, 
    'PERMANENT_SESSION_LIFETIME': datetime.timedelta(days=31), 
    'USE_X_SENDFILE': False, 
    'SERVER_NAME': None, 
    'APPLICATION_ROOT': '/', 
    'SESSION_COOKIE_NAME': 'session', 
    'SESSION_COOKIE_DOMAIN': None, 
    'SESSION_COOKIE_PATH': None, 
    'SESSION_COOKIE_HTTPONLY': True, 
    'SESSION_COOKIE_SECURE': False, 
    'SESSION_COOKIE_SAMESITE': None, 
    'SESSION_REFRESH_EACH_REQUEST': True, 
    'MAX_CONTENT_LENGTH': None, 
    'SEND_FILE_MAX_AGE_DEFAULT': None, 
    'TRAP_BAD_REQUEST_ERRORS': None, 
    'TRAP_HTTP_EXCEPTIONS': False, 
    'EXPLAIN_TEMPLATE_LOADING': False, 
    'PREFERRED_URL_SCHEME': 'http', 
    'TEMPLATES_AUTO_RELOAD': None, 
    'MAX_COOKIE_SIZE': 4093}>
    
    '''

    # session配置
    # SECRET_KEY: session加密的金鑰 將aa123456作為金鑰
    app.config['SECRET_KEY'] = 'aa123456'
    app.config['PERMANENT_SESSION_LIFETIME'] = datetime.timedelta(days=8)    #session過期時間


    return app

views.py

# 路由 + 檢視函式
import datetime

from flask import request, redirect, session

from flask import Blueprint, render_template
# from models import *

#藍圖
# 建立藍圖物件
# 第一個引數:藍圖的名字
# 第二個引數:藍圖的包名
blue = Blueprint('user', __name__,)


#首頁
@blue.route('/')        # 路由
@blue.route('/home/')
def home():
    # 獲取session
    username = session.get('user')

    return render_template('home.html', username=username)


#登入頁面
@blue.route('/login/', methods=['GET', 'POST'])
def login():

    # 判斷請求方式、如果是get請求,則返回登入頁面
    if request.method == 'GET':
        return render_template('login.html')

    # 如果是post請求,則進行登入操作
    elif request.method == 'POST':
        pass
        #1. 獲取前端提交的資料
        username = request.form.get('username') #post提交使用form、這裡的username要和html中的name屬性一致
        password = request.form.get('password') #這裡的password要和html中的name屬性一致

        #2. 實現登入功能, 驗證賬號密碼是否正確
        if username == 'xiaoxin' and password == '123456':
            #登入成功、跳轉到首頁
            response = redirect('/home/')

            # 設定session
            session['user'] = username
            session.permanent = True    # 設定session的過期時間, 預設是31天、如果__init__.py中設定過,則這裡可以不用設定

            return response
        else:
            return '登入失敗,使用者名稱或密碼錯誤'

# 登出
@blue.route('/logout/')
def logout():

    #先跳轉到首頁(重新整理)
    response = redirect('/home/')

    # 刪除session
    session.pop('user')
    # session.clear()   #清除所有的session

    return response

home.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>首頁</title>
</head>
<body>

    <h2>首頁</h2>
    <hr>

    {% if username %}
        <p>你已經登入了,歡迎你:{{ username }}</p>
        <a href="/logout/">登出</a>
    {% else %}
        {#跳轉到登入頁面,注意這裡要從後端路由去跳轉#}
        <a href="/login/">登入</a>
    {% endif %}


</body>
</html>

login.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>登入</title>
</head>
<body>

    <h2>登入</h2>
    <hr>

    {#登入表單#}
{#    <form action="" method="post">#}
{#    <form action="{{ url_for('user.login') }}" method="post">#}
    <form action="/login/" method="post">
        <p>使用者名稱:<input type="text" name="username"></p>
        <p>密碼:<input type="password" name="password"></p>
        <p><input type="submit" value="登入"></p>
    </form>

</body>
</html>

app.py

from App import create_app

app = create_app()

if __name__ == '__main__':
    app.run(debug=True)

相關文章