目录
9.Flask会话技术Cookie原理图解
Cookie:
客户端的会话技术
cookie本身由浏览器保存,通过Response将cookie写到浏览器上,下一次访问,浏览器会根据不同的规则携带cookie 过来
特点:
1.客户端会话技术,浏览器的会话技术
2.数据全都是存储在客户端中
3.存储使用的键值对结构进行的存储
-特性
1.支持过期时间
2.默认会自动携带本网站的所有cookie
3.根据域名进行cookie存储
4.不能跨域名 -
5.不能跨浏览器
6.Cookie是通过服务器创建的Response来创建的
设置cookie:
response.set_cookie(key,value[,max_age=None,exprise=None])
max_age:整数,指定cookie过期时间
expries:整数,指定过期时间,可以指定一个具体日期时间
max_age和expries两个选一个指定
获取cookie:
request.cookie.get(key)
response.delete_cookie(key)
Cookie代码实现:
views.py
import datetime
# views.py: 路由 + 视图函数
from flask import Blueprint, render_template, request, redirect
from .models import *
# 蓝图
blue = Blueprint('user', __name__)
@blue.route('/')
@blue.route('/home/')
def home():
# 获取cookie
username = request.cookies.get('user')
return render_template('home.html', username=username)
# 登录
@blue.route('/login/', methods=['GET', 'POST'])
def login():
# 访问登陆页面
if request.method == 'GET':
return render_template('login.html')
# 实现登录功能
elif request.method == 'POST':
username = request.form.get('username')
password = request.form.get('password')
if username == 'lisi' and password == '123':
response = redirect('/home/')
# 设置cookie
# cookie不能用中文
# response.set_cookie('user', username) # 默认浏览器关闭则cookie失效
# 过期时间
# max_age:秒
# expires: 指定的datetime日期
# response.set_cookie('user',username, max_age=3600*24*7)
response.set_cookie('user', username, expires=datetime.datetime(2024,7,28))
return response
else:
return "输入用户名或密码错误"
# 注销
@blue.route('/logout/', methods=['GET', 'POST'])
def logout():
response = redirect('/home/')
# 删除cookie
response.delete_cookie('user')
return response
home.html--首页
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>首页</title>
</head>
<body>
<p>首页</p>
<hr>
{% if username %}
<p>
登录用户:{{ username }}
</p>
<p>
<a href="/logout/">注销</a>
</p>
{% 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">
<p>用户名:<input type="text" name="username">
</p>
<p>密码:<input type="password" name="password">
</p>
<p><button>提交</button>
</p>
</form>
</body>
</html>
10.模板语言Template基本语法
模板语法:
模板语法主要分为两种
变量
标签
模板中的变量{{var}}
视图传递给模板的数据
前面定义出来的数据
变量不存在,默认忽略
模板中的标签{% tag %}
控制逻辑
使用外部表达式
创建变量
宏定义
模板代码实现
views.py
# views.py: 路由 + 视图函数
from flask import Blueprint, render_template
from .models import *
# 蓝图
blue = Blueprint('user', __name__)
@blue.route('/')
def home():
pass
data = {
'name': 'ikun ikun ikun',
'age': 26,
'likes': ['ball', 'sing', 'dance', 'code']
}
return render_template('home.html', **data)
# return render_template('home.html', name='ikun', age=26)
home.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Home</title>
</head>
<body>
<h2>Home</h2>
<hr>
{# 模板语言的注释 #}
<h4>变量:</h4>
<p>name: {{ name }}</p>
<p>age: {{ age }}</p>
<p>likes: {{ likes }}</p>
<hr>
<h4>标签:</h4>
<h5>if语句</h5>
{% if age >= 18 %}
<p>{{ name }}已经成年了</p>
{% elif age >= 6 %}
<p>{{ name }}可以上学了</p>
{% else %}
<p>{{ name }} 还是小孩 </p>
{% endif %}
<h5>for循环</h5>
{% for like in likes %}
{% if loop.first %}
<p style="color: red;">{{ like }}</p>
{% elif loop.last %}
<p style="color: blue;">{{ like }}</p>
{% else %}
<p>{{ like }}</p>
{% endif %}
index: {{ loop.index }}, # 从1开始进行索引(1,2,3,4)
index0: {{ loop.index0 }}, # 从0开始进行索引
revindex: {{ loop.revindex }}, # 从1开始进行反向索引
revindex0: {{ loop.revindex0 }} # 从0开始进行反向索引
{% else %}
<b>else</b>
{% endfor %}
<br><br><br><br><br>
<br><br><br><br><br>
<br><br><br><br><br>
</body>
</html>
11.Template高级语法
结构标签
block 块操作
父模板挖坑,子模板填坑
{% block xxx%}
{%endblock%}
extends 继承
{%extendsXXX'%%}
继承后保留块中的内容
{{ super() }}
include
包含,将其他html包含进来
{% include''xxx'%}
marco【了解】
宏定义,可以在模板中定义函数,在其它地方调用
{%macro hello(name)%}
{{ name }}
{%endmacro }}
宏定义可导入
{%from 'xxx' import xxx%}
过滤器(扩展)
语法
{{变量|过滤器|过滤器...}}
capitalize
lower
upper
title
trim
reverse
striptags 渲染之前,将值中标签去掉
safe
default(1)
last
first
length
sum
sort
...
代码实现
base.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>父模板</title>
{# 通用css文件 #}
<link rel="stylesheet" href="{{ url_for('static', filename='css/base.css') }}">
{% block extcss %}
{% endblock %}
</head>
<body>
{% block head %}
{% endblock %}
<hr>
{% block content %}
{% endblock %}
<hr>
{% block foot %}
{% endblock %}
{# 通用的js文件 #}
<script src="{{ url_for('static', filename='js/base.js') }}"></script>
{% block extjs %}
{% endblock %}
</body>
</html>
child1.html
{% extends 'base.html' %}
{% block head %}
<div>
<p>千锋YYDS Head</p>
</div>
{% endblock %}
child2.html
{# 继承父模板 #}
{% extends 'child1.html' %}
{# super #}
{% block head %}
{{ super() }}
<p>Python</p>
{% endblock %}
{# include #}
{% block content %}
{% include 'child2_include.html' %}
<p>Flask Content</p>
{% endblock %}
{# 宏定义:Python函数 #}
{% macro person(name, age) %}
<b>姓名:{{ name }}, 年龄:{{ age }}</b>
{% endmacro %}
{% block foot %}
{{ person("坤坤", 25) }}
{# 过滤器 #}
<p>{{ name | capitalize }}</p>
<p>{{ name | title }}</p>
<p>{{ name | upper }}</p>
<p>{{ name | lower }}</p>
<p>{{ name | upper | first | lower }}</p>
<p>{{ name2 | default('kunkun') }}</p>
<p>...</p>
{% endblock %}
child2_include.html
<div>我是child2中include的内容</div>
12.模型基础
安装
前提:安装MySQL Workbench
# 安装flask-sqlalchemy(用于ORM)
pip install flask-sqlalchemy -i https://pypi.tuna.tsinghua.edu.cn/simple
# 安装 flask-migrate(用于数据迁移)
pip install flask-migrate -i https://pypi.tuna.tsinghua.edu.cn/simple
# 安装 pymysql(MySQL驱动)
pip install pymysql -i https://pypi.tuna.tsinghua.edu.cn/simple
创建模型:
# __init__.py
# __init__.py :初始化文件,创建Flask应用
from flask import Flask
from .views import blue
from .exts import init_exts
def create_app():
app = Flask(__name__)
# 注册蓝图
app.register_blueprint(blueprint=blue)
# 配置数据库
db_uri = 'sqlite:///splite3.db'
app.config['SQLALCHEMY_DATABASE_URI'] = db_uri # 配置连接数据库路径DB_URI
app.config['SQLALCHEMY_TRACK_MODIFCATIONS'] = False # 禁止对象追踪修改
# 初始化插件
init_exts(app=app)
return app
# models.py
# models.py : 模型,数据库
from .exts import db
# 模型 数据库
# 类 ==> 表结构
# 类属性 ==> 表字段
# 一个对象 ==> 表的一行数据
# 模型Model: 类
# 必须继承 db.Model
class User(db.Model):
# 表名
__tablename__ = 'tb_user'
# 定义表字段
id = db.Column(db.Integer, primary_key=True, autoincrement=True)
name = db.Column(db.String(30),unique=True, index=True)
age = db.Column(db.Integer, default=1)
sex = db.Column(db.Boolean, default=True)
salary = db.Column(db.Float, default=100000, nullable=False)
salary2 = db.Column(db.Float, default=100000, nullable=False)
# db.Column: 表示字段
# db.Integer: 表示整数
# primary_key=True:主键
# autoincrement=True: 自动增长
# db.String(30): varchar(30): 可变字符串
# unique=True:唯一约束
# index=True:普通索引
# default:默认值
# nullable=False: 是否允许为空
# exts.py
# exts.py 插件管理
# 扩展的第三方插件
# 1.导入第三方插件
from flask_sqlalchemy import SQLAlchemy
from flask_migrate import Migrate
# 2.初始化
db = SQLAlchemy() # ORM
migrate = Migrate() # 数据迁移
# 3.和app对象绑定
def init_exts(app):
db.init_app(app=app)
migrate.init_app(app=app, db=db)
模型Model-数据迁移
执行数据迁移命令:
1.现在cmd或Terminal进入项目目录(app.py所在目录):
2.然后输入命令:
flask db init 创建迁移文件夹migrates,只调用一次
flask db migrate 生成迁移文件
flask db upgrade 执行迁移文件中的升级
flask db downgrade 执行迁移文件中的降级