Flask基础(常规)

1.Flask最核心的WerkZeug和Jinja2

使用Werkzeug来作路由分发(URL请求和视图函数之间的对应关系)
使用Jinja2来渲染模板
复制代码

2.Flask扩展包

Flask-SQLalchemy:操做数据库;
Flask-migrate:管理迁移数据库;
Flask-Mail:邮件;
Flask-WTF:表单;
Flask-script:插入脚本;
Flask-Login:认证用户状态;
Flask-RESTful:开发REST API的工具;
Flask-Bootstrap:集成前端Twitter Bootstrap框架;
Flask-Moment:本地化日期和时间;
复制代码

3.Flask程序运行过程

客户端发送http请求,web服务器使用WSGI协议,把来自客户端的全部请求都交给Flask程序实例(WSGI是为 Python 语言定义的Web服务器
和Web应用程序之间的一种简单而通用的接口,它封装了接受HTTP请求、解析HTTP请求、发送HTTP,响应等等的这些底层的代码和操做,使开发
者能够高效的编写Web应用)
程序实例使用Werkzeug来作路由分发(URL请求和视图函数之间的对应关系)。根据每一个URL请求,找到具体的视图函数。 在Flask程序中,路由
的实现通常是经过程序实例的route装饰器实现。route装饰器内部会调用add_url_route()方法实现路由注册调用视图函数,获取响应数据后,
把数据传入HTML模板文件中,模板引擎负责渲染响应数据,而后由Flask返回响应数据给浏览器,最后浏览器处理返回的结果显示给客户端。
复制代码

4.状态码,重定向(redirect),render_template(),url_for,flash

a.自定义状态码,在返回的响应的后边
@app.route('/')
def hello_itcast():
    return 'hello itcast',500

b.重定向
@app.route('/')
def hello_itcast():
    return redirect("http://www.baidu.com")

c.url_for的用法
1.url_for()函数是以视图函数名为参数,返回对应的url
2.加载静态参数
  <link rel='stylesheet' href="{{ url_for('static',filename='css/index.css')}}">
  <li>{{ book.name }} <a href="{{ url_for('delete_book',book_id=book.id) }}">删除</a></li>
复制代码

5.错误页面的自定义以及模板上下文处理函数

a.自定义404页面(捕获异常)
@app.errorhandler(404)  # 传入要处理的错误代码
def page_not_found(e):  # 接受异常对象做为参数
    user = User.query.first()
    return render_template('404.html', user=user), 404  # 返回模板和状态码
b.模板上下文处理函数(因为多个模板都须要用到user这个变量,直接在这个函数里面取出)
@app.context_processor
def inject_user():  # 函数名能够随意修改
    user = User.query.first()
    return dict(user=user)  # 须要返回字典,等同于return {'user': user}
复制代码

6.url的自定义

from flask import Flask
from werkzeug.routing import BaseConverter

class Regex_url(BaseConverter):
    def __init__(self,url_map,*args):
        super(Regex_url,self).__init__(url_map)
        self.regex = args[0]

app = Flask(__name__)
app.url_map.converters['re'] = Regex_url

@app.route('/user/<re("[a-z]{3}"):id>')
def hello_itcast(id):
    return 'hello %s' %id
复制代码

7.abort函数的使用

若是在视图函数执行过程当中,出现了异常错误,咱们可使用abort函数当即终止视图函数的执行,若是abort函数被触发,其后面的语句将不会执行
from flask import Flask,abort
@app.route('/')
def hello_itcast():
    abort(404)
    return 'hello itcast',999

注意abort里面的状态码必须就是HTTP状态码,不能本身随便写。常见状态码以下:
状态代码有三位数字组成,第一个数字定义了响应的类别,共分五种类别:
1xx:指示信息--表示请求已接收,继续处理
2xx:成功--表示请求已被成功接收、理解、接受
3xx:重定向--要完成请求必须进行更进一步的操做
4xx:客户端错误--请求有语法错误或请求没法实现
5xx:服务器端错误--服务器未能实现合法的请求
常见状态码:
复制代码

8.请求钩子

Flask的请求钩子指的是在执行视图函数先后执行的一些函数,咱们能够在这些函数里面作一些操做。Flask利用装饰器给咱们提供了四种钩子函数。css

before_first_request:在处理第一个请求前执行。好比连接数据库操做 before_request:在每次请求前执行。好比权限校验 after_request:每次请求以后调用,前提是没有未处理的异常抛出 teardown_request:每次请求以后调用,即便有未处理的异常抛出html

from flask import Flask

app = Flask(__name__)


@app.route('/')
def index():
    print('视图函数执行')
    return 'index page'


# 在第一次请求以前运行.
@app.before_first_request
def before_first_request():
    print('before_first_request')


# 在每一次请求前都会执行
@app.before_request
def before_request():
    print('before_request')


# 在请求以后运行
@app.after_request
def after_request(response):
    # response: 就是前面的请求处理完毕以后, 返回的响应数据,前提是视图函数没有出现异常
    # 若是须要对响应作额外处理,能够再这里进行
    # json.dumps 配置请求钩子
    # response.headers["Content-Type"] = "application/json"
    print('after_request')
    return response


# 不管视图函数是否出现异常,每一次请求以后都会调用,会接受一个参数,参数是服务器出现的错误信息
@app.teardown_request
def teardown_request(error):
    print('teardown_request: error %s' % error)


if __name__ == '__main__':
    app.run(debug=True)
复制代码

9.request对象经常使用属性

10.文件上传

上传文件也是咱们常常用到的功能,前端上传一张文件,而后后端处理保存到服务器上。 文件这种类型属于多媒体类型资源。前端form表单里面须要加enctype="multipart/form-data"。咱们新建一个名upload.html模板 模板里面写以下代码:前端

<form action="" method="post" enctype="multipart/form-data">
    <input type="file" name="file">
    <input type="submit" value="上传">
</form>
复制代码

upload.py文件代码以下:(同级目录下建立media文件夹)web

from flask import Flask, request,render_template,redirect,url_for
from werkzeug.utils import secure_filename
import os
from flask import send_from_directory


app = Flask(__name__)

UPLOAD_FOLDER = 'media'
ALLOWED_EXTENSIONS = set(['txt', 'pdf', 'png', 'jpg', 'jpeg', 'gif'])
app.config['UPLOAD_FOLDER'] = UPLOAD_FOLDER

# 判断上传的文件是不是容许的后缀
def allowed_file(filename):
    return "." in filename and filename.rsplit('.', 1)[1].lower() in ALLOWED_EXTENSIONS



@app.route('/upload',methods=['GET','POST'])
def upload():
    '''文件上传'''
    if request.method == 'GET':
        return render_template('upload.html')

    else:
        print(request.files)
        print(type(request.files))
        if "file" not in request.files:
            return redirect(request.url)

        file = request.files.get('file')  # 获取文件
        print(type(file))

        if file.filename == '':
            return redirect(request.url)

        if file and allowed_file(file.filename):
            filename = secure_filename(file.filename)  # 用这个函数肯定文件名称是不是安全 (注意:中文不能识别)
            file.save(os.path.join(app.config['UPLOAD_FOLDER'], filename))  # 保存文件
            return redirect(url_for('show',filename=filename))

# 展现图片
@app.route('/show/<filename>')
def show(filename):
    # send_from_directory能够从目录加载文件
    return send_from_directory(app.config['UPLOAD_FOLDER'], filename)
复制代码

11.Flask框架上下文

参考:https://juejin.im/post/5ccd3670f265da0373719711
复制代码

12.Response

视图在接收HttpRequest并处理后,必须返回HttpResponse对象, 可使用make_response()函数而后再进行修改 示例代码:数据库

from flask import Flask, render_template, make_response

app = Flask(__name__)


@app.route('/setcookie', methods=['GET', 'POST'])  # 支持get、post请求
def setcookie():  # 视图函数
    resp = make_response(render_template('cookie.html'))  # 显式转换成HttpResponse对象
    return resp

app.config['DEBUG'] = True

if __name__ == '__main__':
    # 0.0.0.0表明任何能表明这台机器的地址均可以访问
    app.run(host='0.0.0.0', port=5000)  # 运行程序
复制代码

13.自定义响应信息

自定义响应信息,能够用make_response函数。make_response(),至关于Django中的HttpResponse,效果是同样的。json

from flask import Flask, abort, Response, make_response

app = Flask(__name__)


@app.route('/')
def index():
    # return ('自定义响应信息', 502, {"name": "xiaosong", "age": 12})

    # 能够不加括号,会自动组装成元组
    # return '自定义响应信息', 502, {"name": "xiaosong", "age": 12}

    # 自定义状态码 能够加上描述信息
    # return '自定义响应信息', '520 love error', {"name": "xiaosong", "age": 12}
    resp = make_response()
    resp.headers['name'] = 'xiaosong'
    resp.status = '520 love error'
    return resp


if __name__ == '__main__':
    # 0.0.0.0表明任何能表明这台机器的地址均可以访问
    app.run(host='0.0.0.0', port=5000, debug=True)  # 运行程序

复制代码

使用jsonfy返回响应信息和直接json.dumps(data)返回信息是不一样的,表如今响应头中的Content-Type字段flask

jsonify:后端

Content-Type: application/json浏览器

json.dumps(data):安全

Content-Type: text/html; charset=utf-8

相关文章
相关标签/搜索