Narrative content
endpoint
- which corresponds django endpoint alias may be used to reverse analysis url
- Mapping routing address and endpoint - routing address and view function Mapping endpoint can not appear in the same app repeatedly, the default value is a view of the function name (a decorative decorator multiple functions, endpoint as otherwise an error can not be named, the route can not be the same, otherwise The second match less)
from flask import Flask,redirect app = Flask(__name__) def warp(func): def inner(*args,**kwargs): return redirect("/home") return inner @app.route("/temp1",endpoint="temp1") @warp def temp1(): return "I am temp1" @app.route("/temp2",endpoint="temp2") @warp def temp2(): return "I am temp2" @app.route("/home") def home(): return "I am home" if __name__ == '__main__': app.run(debug=True) #解析:多个装饰器装饰函数,从下往上执行,一个装饰器装饰多个函数,会报错,错误类型如下 AssertionError: View function mapping is overwriting an existing endpoint function: inner #视图函数正在覆盖现有的端点函数,如果加了endpoint等同于inner.__name__ = func.__name__ 其函数名字,但只是改了一下名字是不行的,Flask内部方法进行此类操作通过endpoint,具体详见源码解析
url_for
- Reverse get url address, the default view for the function name
from flask import url_for @app.route("/info",methods=["GET","POST"],endpoint="r_info") def student_info(): print(url_for("r_info"))#/info return "hello"
1. routing configuration:
Flask Routing
@app.route(配置路由)
rule
- For routing address
@app.route("/login") def login(): ... @app.route("/home") def home(): ...
methods
- Allowing the requesting way into view function
@app.route("/home",methods=["GET","POST"]) def home(): ...
defaults
- The default routing parameters
from flask import Flask,redirect app = Flask(__name__) @app.route("/h",defaults={"count":20}) # 传入参数,否则报错 def home(count): return f"200 OK {count}" if __name__ == '__main__': app.run()
strict_slashes
- Whether or not strictly follow the routes matching rules, url address ending character "/" control False, the path "/" exists can be accessed, True: the end must not be "/" is True to add '/'
#访问地址:/info @app.route("/info",strict_slashes=True) def student_info(): return "hello old boy info" #访问地址:/infos 或 /infos/ @app.route("/infos",strict_slashes=False) def student_infos(): return "hellos"
redirect_to
- Permanent redirect response code: 301,308 Moved Permanently
from flask import Flask,redirect app = Flask(__name__) @app.route("/h",defaults={"count":20}) def home(count): return f"200 OK {count}" @app.route("/res",redirect_to="/h") def res(): return "hello" if __name__ == '__main__': app.run()
Dynamic routing parameters 1
@app.route("/temp/<page>_<id>_<type>",endpoint="temps") def temp(page,id,type): print(page,id,type) return "%s_%s_%s"%(page,id,type) if __name__ == '__main__': app.run() #浏览器输入http://127.0.0.1:5000/temp/23_32_43 #返回:23 32 43
Dynamic routing parameters 2
@app.route("/get_img/<filename>") def get_img(filename): file_path = os.path.join("img",filename) return send_file(file_path) if __name__ == '__main__': app.run(debug=True)
from flask import url_for
def hmoea():
print(url_for('homea'))
rule "/login" 路由地址
methods 允许进入视图函数的请求方式
endpoint Mapping路由地址和endpoint - 路由地址和视图函数Mapping endpoint 在同一个app中不能出现重复,默认值是视图函数
@app def app endpoint=app ❌❌❌
defaults 默认路由参数
stric_slashes 是否严格遵循路由匹配规则
redirect_to 永久重定向 308
动态参数路由: "/get_muisc/<filename>" def get_music(filename)可以分页,获取文件,解决分页,解决正则路由问题
2.Flask initial configuration
- Arrangement positions: App = the Flask (
__name__
)
template_folder 模板文件存放目录
static_folder 静态文件存放目录 默认值 是 static 默认值static
static_url_path 静态文件访问路径 默认值 是 / + static_folder
当修改template_folder="img" ----> 自动修改成static_url_path='/img'。除非重新自动修改成static_url_path="static"
- Example 1:
import os
from flask import Flask,render_template,send_file
app = Flask(__name__,template_folder="./templates",static_folder="static",static_url_path="/static")
@app.route("/")
def index():
return render_template("index.html")
#前端index.html页面
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<img src="/static/2.jpg" alt="">
</body>
</html>
#静态文件存放目录是static, 静态文件访问路径static_url_path="/static"
#前端通过/static/2.jpg,找到静态文件存放目录,并提取里面文件
static_url_path 用于放静态文件路径
static_folder 用于存放静态文件目录
- Example 2:
import os
from flask import Flask,render_template,send_file
app = Flask(__name__,template_folder="templates",static_folder="img",static_url_path="/static")
@app.route("/")
def index():
return render_template("index.html")
@app.route("/img/<filename>")
def get_img(filename):
filepath = os.path.join("img",filename)#用static_folder.
return send_file(filepath)
if __name__ == '__main__':
app.run(debug=True)
#前端index.html页面
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<img src="/static/1.jpg" alt="">#用static_url_path
</body>
</html>
- Example 3:
@app.route("/img/<filename>")
def get_img(filename):
print(filename)
filepath = os.path.join("img",filename)#通过static_folder拼接图片地址。并返回send_file
return send_file(filepath)
3.Flask instance configuration
- the app.config (django of similar configuration setting)
Parameter Description:
ENV 当前运行虚拟环境 debug 编辑模式 testing 测试,日志打印 propaagate_exceptions secret_key 密钥 permanent_session_lifetime session默认时间 配置的时候写的是秒 server_name 配置服务所处于的域名(Nginx自己匹配) session_cookie_name 存储在浏览器session名字 session_cookie_Path JSONIFY_MIMETYPE 设置jsonify 的content-type
Create a file settings.py
import hashlib,time
class DebugConfig(object):
"""调试模式"""
DEBUG = True
SECRET_KEY = "#$#sdrer"
PERMANENT_SESSION_LIFETIME = 3600
SESSION_COOKIE_NAME = "hello"
class TestConfig(object):
"""线上测试"""
TESTING = True
SECRET_KEY = hashlib.md5(f"{time.time()}asdg3#¥#@#{time.time()}".encode("utf8")).hexdigest()
PERMANENT_SESSION_LIFETIME = 3600
SESSION_COOKIE_NAME = "BBADASD@#@#@$##!$@"
- Import module configured to setting app
from setting import DebugConfig
app = Flask(__name__)
app.config.from_object(DebugConfig)#匹配配置
4.Flask in blueprint
- Flask in the blueprint Blueprint (app01)
不能被run的Flask 实例 不存在config
1. Create a Blueprint 2
"""
class Blueprint
def __init__(
self,
name,
import_name,
static_folder=None,
static_url_path=None,
template_folder=None,
url_prefix=None,
subdomain=None,
url_defaults=None,
root_path=None,
cli_group=_sentinel,
):
"""
#blue_pic1.py
from flask import Blueprint
bp = Blueprint("app01",__name__)
@bp.route("/add_user")
def add_user():
return "添加用户"
@bp.route("/find_user")
def find_user():
return "查看用户"
@bp.route("/drop_user")
def drop_user():
return "删除用户"
@bp.route("/up_user")
def up_user():
return "修改用户"
#blue_pic2.py
from flask import Blueprint
car_bp = Blueprint("app02",__name__,url_prefix="/car")
#url_prefix 可指定url前缀
@car_bp.route("/add_user")
def add_user():
return "car添加用户"
@car_bp.route("/find_user")
def find_user():
return "car查看用户"
@car_bp.route("/drop_user")
def drop_user():
return "car删除用户"
@car_bp.route("/up_user")
def up_user():
return "car修改用户"
- Import function
from flask import Flask
from setting import DebugConfig
from blue_pic1 import bp
from blue_pic2 import car_bp
app = Flask(__name__,template_folder="template")
app.config.from_object(DebugConfig)
app.register_blueprint(bp)#注册蓝图
app.register_blueprint(car_bp)#注册蓝图
if __name__ == '__main__':
app.run()
- Enter the browser: url find the corresponding URL
- Small practice: url_for in application blueprint
from flask import Blueprint, url_for, redirect
bp = Blueprint("app01",__name__)
@bp.route("/bps",endpoint="bps")
def bps():
return redirect(url_for("app01.dd"))
#通过url_for("蓝图标识.endpoint值")可以获得其他视图函数的rule(url路径),通过redirect(url_for("app01.dd")),可以重定向网页
@bp.route("/bpdd",endpoint="dd")
def bpdd():
return "this is bpdd..."
5. Special decorator (similar middleware)
- @ App.before_request () before entering the view request function, to make a deal
- After @ app.after_request () returns the response to the client before the end view of the function
- be + af request lifecycle:
- Normal: be1-> be2-> vf-> af2-> af1
- Abnormal: be1-> af2-> af1
- Return as long as there is a response, af overall response
@ App.errorhandler (404) Error Handling
特殊装饰器实例:类似于django中间件
from flask import Flask, send_file,session
from setting import DebugConfig
from blue_pic1 import bp
from blue_pic2 import car_bp
app = Flask(__name__,template_folder="template")
app.config.from_object(DebugConfig)
app.register_blueprint(bp)
app.register_blueprint(car_bp)
@app.before_request
def be1():
print("I am Be1")
@app.before_request
def be2():
print("I am Be2")
@app.after_request
def af1(res):
print("I am af1")
return res
@app.after_request
def af1(res):
print("I am af2")
return res
@app.errorhandler(404)
"""监听错误,出现404错误,直接跳转baidu页面"""
def error404(error_message):
print(error_message)
return send_file("https://www.baidu.com/")
@app.route("/set_session")
def set_session():
print("舞曲")
session["key"] = "1234556775465"
return "session创建"
@app.route("/get_session")
def get_session():
print(session.get("key"))
return "session获取"
if __name__ == '__main__':
app.run()
#I am Be1
#I am Be2
#1234556775465
#I am af2
#I am af1
be + af 请求生命周期:
- 正常:be1->be2->vf->af2->af1
- be1异常:be1->af2->af1
6.源码解析:
6.1解析route装饰器源码
pic1:
pic2:
6.2解析route中methods方法
pic1