Flask 视图,中间件
视图
FBV
def index(nid):
"""
请求相关信息 request.method # 请求方式
request.args # get 方式的参数获取
request.form # post 方式的参数获取
request.values
request.cookies
request.headers
request.path # 请求资源路径
request.full_path # 请求全部资源漫画
request.script_root
request.url # 全部请求路径 (带协议带域名)
request.files # 请求文件
obj = request.files['the_file_name']
obj.save('/var/www/uploads/' + secure_filename(f.filename))
"""
dic = {"k1":"v1"}
"""
返回响应体的4种形式
字符串
jsonify
模板
跳转 url
""" # return "index"
# return jsonify(dic)
# return render_template("xxx.html",dic=dic) # 可带数据传递
# return redirect(url_for("index")) # 跳转通过 url_for 反向解析
"""
定制响应头的时候构造响应体用到 make_response
"""
# 如果想设置响应头和回显cookie,就需要用到make_response
# response = make_response(render_template('index.html'))
# response = make_response("字符串")
# response是flask.wrappers.Response类型
# response.delete_cookie('key')
# response.set_cookie('key', 'value')
# response.headers['X-Something'] = 'A value'
# return response
from flask import make_response,headers,set_cookie
obj = make_response(jsonify(dic))
obj.headers["xxxxx"] = ""
obj.set_cookie("key","value")
return obj
装饰器实现中间件功能
预备处理视图函数初始状态
@app.route('/index')
def index():
if not session.get('user'):
return redirect(url_for('login'))
return render_template('index.html',stu_dic=STUDENT_DICT)
视图级别加装,比较适用于对少量视图进行处理
import functools
def auth(func):
@functools.wraps(func)
def inner(*args,**kwargs):
if not session.get('user'):
return redirect(url_for('login'))
ret = func(*args,**kwargs)
return ret
return inner @app.route('/index')
@auth
def index():
return render_template('index.html',stu_dic=STUDENT_DICT)
全局级别加装
@app.before_request
def xxxxxx():
if request.path == '/login':
return None if session.get('user'):
return None return redirect('/login')
除了 before_request 以外还有其他特殊装饰器:
1. before_request 谁先定义谁先执行
执行多个 before 的时候如果再中间有返回值,对于after 的执行直接执行最后一次定义的那个 2. after_request 谁后定义谁执行 3. before_first_request 4. template_global 5. template_filter 6. errorhandler
from flask import Flask
app = Flask(__name__) @app.before_request
def x1():
print('before:x1')
return '滚' @app.before_request
def xx1():
print('before:xx1') @app.after_request
def x2(response):
print('after:x2')
return response @app.after_request
def xx2(response):
print('after:xx2')
return response @app.route('/index')
def index():
print('index')
return "Index" @app.route('/order')
def order():
print('order')
return "order" if __name__ == '__main__': app.run()
befor/after_request 示例
from flask import Flask
app = Flask(__name__) @app.before_first_request
def x1():
print('') @app.route('/index')
def index():
print('index')
return "Index" @app.route('/order')
def order():
print('order')
return "order" if __name__ == '__main__': app.run()
before_first_request 示例
@app.errorhandler(404)
def not_found(arg):
print(arg)
return "没找到"
errorhandler 示例
CBV
def auth(func):
def inner(*args, **kwargs):
result = func(*args, **kwargs)
return result
return inner # 继承自views.MethodView 采用CBV写法时,为了简单,都是采用继承MethodView的方式写的
class IndexView(views.MethodView):
# methods = ['POST'] #只允许POST请求访问
decorators = [auth,] #如果想给所有的get,post请求加装饰器,就可以这样来写,也可以单个指定 def get(self): #如果是get请求需要执行的代码
v = url_for('index')
print(v)
return "GET" def post(self): #如果是post请求执行的代码
return "POST" app.add_url_rule('/index', view_func=IndexView.as_view(name='index')) #name指定的是别名,会当做endpoint使用
def auth(func):
def inner(*args, **kwargs):
print('before')
result = func(*args, **kwargs)
print('after')
return result
return inner # 也可以再往上继承自View
class IndexView(views.View):
methods = ['GET']
decorators = [auth, ]
# 如果继承自View,就需要dispatch_request
def dispatch_request(self):
print('Index')
return 'Index!' app.add_url_rule('/index', view_func=IndexView.as_view(name='index')) # name=endpoint
文件上传
客户端
- 必须要在表单中上传
- 提交方式必须是 post
- enctype 属性必须是 multipart/form-data
<form action="/login" method="post" enctype="multipart/form-data">
上传文件: <input type="file">
</form>
服务端
文件会上传到缓存区, 通过 request.files 获取上传文件
拿到返回值可以调用 save , filename 方法
f = request.file['name'] # f.save('路径')
# f.filename # 得到文件原始名称 f.save('static/' + f.filename) # 如果不存在 static 会报错
此方法在上传重名文件的时候会覆盖, 因此需要自己设定绝不会重名的方式,比如用时间戳
中间件
首先要知道我们利用请求扩展里提供的装饰器也能够做一些中间件的事,我们这里说的是根据flask的源码流程进行自定义方法来实现中间件的操作
具体流程:
app.run会执行werkzeug(第三方WSGI模块)中的run_simple方法,继而执行inner方法,继续执行make_server方法,
make_sever方法就会返回一个BaseWSGIServer对象,主要是起socket,
当有请求过来时就会触发flask的call方法,继而执行wsgi_app方法
利用app.run中的wsgi_app方法可以自定义类,定义的_ _call_ _方法里就可以做一些中间件的事
from flask import Flask app = Flask(__name__) @app.route('/')
def index():
return 'Hello World!' class Md(object):
def __init__(self,old_wsgi_app):
self.old_wsgi_app = old_wsgi_app def __call__(self, environ, start_response):
print('开始之前')
ret = self.old_wsgi_app(environ, start_response)
print('结束之后')
return ret if __name__ == '__main__':
app.wsgi_app = Md(app.wsgi_app)
app.run()
Flask 视图,中间件的更多相关文章
- Flask视图函数报fmalformed url rule错误的原因
Flask视图函数报fmalformed url rule错误,原因可能是包含中文字符了 把标点符号都重新写一遍英文格式的,可能就不会报这个了
- Flask的“中间件”
特殊装饰器 from flask import Flask,render_template,request app = Flask(__name__) @app.before_request def ...
- Flask 视图
写个验证用户登录的装饰器:在调用函数前,先检查session里有没有用户 from functools import wraps from flask import session, abort de ...
- flask 视图函数的使用
flask框架 视图函数当中 各种实用情况简单配置 1 建立连接 2 路由参数 3 返回网络状态码 4 自定义错误页面 5 重定向 6 正则url限制 和 url 优化 7 设置和获取cookie # ...
- Flask视图函数与普通函数的区别,响应对象Response
视图函数与普通函数看似没什么区别,其实他们的返回值上有着很大的区别. from flask import Flask app = Flask(__name__) @app.route('/hello' ...
- Flask 视图,模板,蓝图.
https://www.cnblogs.com/wupeiqi/articles/7552008.html 1. 配置文件 from flask import Flask app =Flask(__n ...
- Flask视图函数与模板语法
1.Django中的CBV模式 2.Flask中的CBV和FBV def auth(func): def inner(*args, **kwargs): result = ...
- 3.flask视图进阶
1.add_url_rule和app.route原理剖析 from flask import Flask app = Flask(__name__) # 下面是我们定义一个路由和对应视图的常用方法 ' ...
- 1.flask视图和URL
1.第一个flask程序 from flask import Flask ''' Flask这个类是项目的核心,以后很多操作都是基于这个类的对象 注册URL等等,都是基于这个类 ''' app = F ...
随机推荐
- TS学习随笔(三)->接口
终于来到了比较重要的知识,接口,有多重要呢,反正是很重要好啵 在 TypeScript 中,我们使用接口(Interfaces)来定义对象的类型. 那什么是接口呢,在面向对象语言中,接口(Interf ...
- .net向文件写入字符串流内存溢出的问题
字符串过大导致抛出异常: exceptopm of type 'system.outOfmemoryexception' was thrown 解决方法:逐块写入可以避免这个问题
- c/c++ 头文件的血案
头文件的血案 不小心在一个头文件里,加了函数的定义,结果导致编译时,提示这个函数被重复定义:( Quote.h #ifndef __QUOTE_H__ #define __QUOTE_H__ #inc ...
- java反射(java.lang.reflect) ---普通单例模式唯一性问题
1. 普通的饱汉式.饿汉式 package org.bighead.test2; public class TestPrivate { private String str = "strPr ...
- es crul查询(一)
C:\Users\Administrator>elasticdump --input=D:\test --output=http://localhost:9200/logs_apipki_201 ...
- 《精通Spring+4.x++企业应用开发实战》读后感
引言 还记得大三时上培训班的是时候,当时的培训老师说自己是本地讲解spring最好的讲师,但是后来等我实习了看了<Spring 3.x 企业应用开发实战>以及后续版本<精通Sprin ...
- c# 日期函数DateTime.ToString()日期的各种格式
//c# datetime 格式化 DateTime dt = DateTime.Now; //2017/11/14 10:46:56 label1.Text = dt.ToString();//20 ...
- IDEA+循环语句 or 输出语句 快捷操作
IDEA+循环语句 or 输出语句 快捷操作:https://blog.csdn.net/shijiebei2009/article/details/44726433 for循环:仅输入fori然后回 ...
- Mac进行 usr/bin 目录下修改权限问题,operation not permitted
一般情况下我们在使用mac系统过程中下载一些文件.新建一些项目之后,这些文件都会默认是只读状态,这时我们只需要简单的一句权限设置命令就可以解决 你要修改文件上层目录的路径 但是我们在对 usr/bin ...
- EasyUI datagrid formatter 属性
easyui的formatter属性可以帮助我们更加灵活的显示数据库中的数据. 比如,我有一个启用禁用字段,使用数字表示,1表示启用,2表示禁用,展示给客户的时候我当然希望是中文的形式. 只需要写这么 ...