1.钩子函数
钩子函数是指在执行函数和目标函数之间挂载的函数,框架开发者给调用方提供一个point-挂载点,至于挂载什么函数由调用方决定,
大大提供了灵活性。
2.常用的钩子函数
@before_first_request
在对应用程序实例的第一个请求之前注册要运行的函数,只会运行一次
@before_request
在每个请求之前注册一个要运行的函数,每一次请求都会执行一次
@after_request
在每个请求之后注册一个要运行的函数,每次请求完成后都会执行。
需要接受一个Response对象作为参数,并返回一个新的Response对象,或者返回接收的Response对象
@teardown_request
注册在每一个请求的末尾,不管是否有异常,每次请求的最后都会执行。
@context_processor
上下文处理器,返回的字典可以在全部的模板中使用
@template_filter('xxxxxx')
增加模板过滤器,可以在模板中使用该函数,后面的参数是名称,在模板中用到
@errorhandler(400)
发生一些异常时,比如404,500,或者抛出异常(Exception)之类的,就会自动调用该钩子函数
1.发生请求错误时,框架会自动调用相应的钩子函数,并向钩子函数中传入error参数
2.如果钩子函数没有定义error参数,就会报错
3.可以使用abort函数来手动终止请求抛出异常,如果要是发生参数错误,可以abort(404)之类的
3.实例
a. app.py
def create_app():
_app = Flask(__name__)
# 加载flask配置
_app.config.from_object(config)
myprint('创建Flask对象')
return _app
app = create_app()
b. hooks.py
from flask_lesson2.app import app
from flask_lesson2.utils import myprint
from flask import session, render_template
myprint('hooks')
@app.before_first_request
def before_first_request():
"""
在第一次启动服务器时会被调用
"""
myprint('before_first_request')
@app.before_request
def before_request():
"""
每一次请求之前被调用到
"""
myprint('before_request')
@app.after_request
def after_request(resp):
"""
每一次请求之后被调用
:param resp: 这个参数是response对象
:return: 需要返回一个response对象,可以是新的,也可以是传入进入的
"""
myprint('after_request')
return resp
@app.teardown_appcontext
def teardown_appcontext(e):
"""
注册在每一个请求的末尾,不管是否有异常,每次请求的最后都会执行。
:param e:
"""
myprint('teardown_appcontext')
myprint(e)
@app.template_filter('uuuper')
def template_filter(s):
"""
自定义过滤器
上面uuuper就是过滤器名称,在模板中使用,例如{{username}uuuper}}就是把字符串全部大写
:param s: 传入进来的参数,可以有多个,根据你要的功能添加
:return: 返回处理后的数据
"""
myprint('template_filter')
return s.upper()
@app.context_processor
def context_processor():
"""
返回一个字典,字典中的值在模板任意地方都能使用,该函数被调用时在before_request之后
after_request之前
:return: 携带了需要的数据的字典
"""
myprint('context_processor')
context = {}
username = session.get('username')
context.update(username=username)
return context
@app.errorhandler(404)
def errorhandler(e):
"""
异常处理,可以根据不同的异常定制不同的处理方法
:param e: 异常信息
:return: 可以返回一个模板,例如404.html,告知用户错误信息等
"""
myprint('error_handler,404')
myprint(e)
return render_template('index.html'), 404
c. main.py
@app.route('/')
def index():
myprint('app.index')
# 存入一个数据到session中
session['username'] = 'ChenTao'
# 手动抛出一个404异常
abort(404)
return 'Hello'
if __name__ == '__main__':
app.run()
看别人的写法,创建hooks.py后,直接在该文件import app后,然后写钩子函数,在访问过程中钩子函数是生效,但我一直失败,没办法只能更改写法了。
先在app.py中创建app对象,然后在hooks.py中import app写好钩子函数,最后在main.py中import app时不再是从app.py中了,而是从hooks.py中import,那么在这个过程中hooks.py文件就加载了,钩子函数也就生效了。
纠正:
参照Flask项目的
__init__.py
文件写法。4.LOG打印
创建Flask对象
hooks
创建Flask对象
hooks
before_first_request # 在一次启动服务器运行过程中,只会执行一次
before_request # 访问主页是一次请求,在请求之前执行
app.index # 访问主页,打印LOG
error_handler,404 # 在主页函数中,abort(404)了,那么便会调用errorhandler的处理函数
404 Not Found: The requested URL was not found on the server. If you entered the URL manually please check your spelling and try again.
context_processor # 在该函数中,处理返回的数据
template_filter # 在模板中使用了该过滤器
after_request # 请求完成
teardown_appcontext
None # 没有异常
网友评论