Flask 作为一个轻量级的 Python 前端网页框架,正在逐渐壮大,而在一些近期的一些项目中,也常出现其身影,作为前端和后端相互结合的框架,适合我们去快速构建一个服务器端的服务应用,同时也方便了自己的维护,更重要的是构建起较为完善的技术栈。

环境配置

在本次的 Flask 的初步学习中采用的环境是:
Python 3.85 + VScode + Conda + Flask2.1

关于 VScode 配置

关于 Pycharm 还是 VScode,这里采用了 VScode,主要是觉得 Pycharm 有时打开时刻比较笨重,而且最近对于 Python 的开发比较少的在 VScode 中进行,希望能够因此而熟悉一下相关 操作。

VScode 的 Python 命令行配置
在编写完成一个 helloworld 的时候,我们想要使用 VScode 进行终端的操作,但是默认的 VScode 的终端操作是 Powershell(默认的前缀是 ps),不是很友好,而且对于 Conda 的适配不好,所以尽量更改为 cmd 环境。
在我们的 CMD 环境中,我们可以使用 Flask 命令进行更好的操作。

首先在右下角的终端处进行简单更多选项的箭头,选择默认配置文件

进而选择 Command Prompt(这里我更改过了,所以默认就是 cmd)

然而,在我们再次打开 VScode 的时候,cmd 并不会自动激活 conda 或者进入相关路径,这时,我们自己在右下角新建一个终端即可。这样 cmd 的配置就可以了,Conda 会自动激活当前环境,Python 的编译器会在左下角进行选择,而更多的关于 VScode 的 Python 的环境配置,可以在互联网中进行搜索解决。

Hello world

主要使用的文档是官方文档的 QuickStart
开始第一个 Demo 吧

from flask import Flask
app = Flask(__name__)  
@app.route("/")
def hello_world():
    return "A great world"

如果将自己的 Python 文件命名为 app.py 就不用去设置环境变量了
如果命名为其他的需要去 声明一个环境变量(根据不同的 终端环境进行设置)其中 hello 为自己无 py 后缀的文件名。

#在 cmdset FLASK_APP=hello
#在bash下
export FLASK_APP=hello

对于重启后出现 cannot import name ‘soft_unicode’ from ‘markupsafe’ 报错,如下

File "E:\python3.8\lib\site-packages\jinja2\filters.py", line 13, in <module>
    from markupsafe import soft_unicode
ImportError: cannot import name 'soft_unicode' from 'markupsafe' (E:\python3.8\lib\site-packages\markupsafe\__init__.py)

可以尝试去降级 MarkupSafe 以解决问题
pip install MarkupSafe==2.0.1

继续运行程序

flask run

单击或自行访问出现的 http://127.0.0.1:5000/ 即可查看到运行结果

可以看到在前面的 @app.route(“/“) 中引号内的内容,表示了 URL 路径。
我们可以添加一下代码,然后重新运行(需要关闭当前的 Flask 运行界面,然后重现 flask run)

@app.route("/apple")
def get_Apple():
    return "returned an apple!"

这样就实现了 API 的访问 (wow)
但是我们默认返回的是 String 字符串,这点需要注意。

如何使用其他的访问方式 如 post?

观察到我们命令行出现的提示信息:

127.0.0.1 - - [13/May/2022 19:45:15] "GET /apple HTTP/1.1" 200 -

采用的 获取方式都是 Get,一方面是因为 Flask 的默认方式 就是 Get,另一方面是因为采用浏览器访问,访问就是 Get 方式。

如何处理 post 请求,Flask 方面的解决办法是

添加模块
from flask import request
然后对比修改代码,如下:

@app.route("/",methods=['GET', 'POST'])
def hello_world():
    if request.method == 'POST':
        return "here is a post"
    else :
        return "A great world"

需要注意,对于模块的 import 如果大小写引入错误,将会无法正常运行,同样需要注意 method 和 methods 的区分

如何发送 post 请求

这里采用 postman 本地应用进行发送 post 请求

如何返回 JSON

JSON 是一个结构化的数据,可以方便我们进行数据的处理
对于 JSON 的返回值处理 ,我们根据文档可以看出,如果采用字典返回那么自动就会通过 一个方法jsonify转换成json

@app.route("/json")
def json():
    return dict(name = 'a',num = 100)

添加代码后,重启服务,访问 http://127.0.0.1:5000/json

可以看到, Firefox 浏览器自动将其解析为了 Json ,并进行了梅花,方便了阅读和处理。

如何从前端获取数据到后端

在 web 开发的过程中,从客户端获取信息到服务器上,就需要对于 Request 作出一定的处理:

在 URL 中添加 参数 信息

通常使用 get 进行操作
代码参考如下:

@app.route("/json_another")
def json_another():
    name = request.args.get('name','null')
    if (name == 'qaq'):
        return dict(check='true')
    else :
        return dict(check='flase')

如果在访问 http://127.0.0.1:5000/json_another 而不加任何参数的时候,就会获取不到相关的内容,进而判断失败。

如果 http://127.0.0.1:5000/json_another?name=qaq 输入正确的用户名和变量名称,那么就可以检测成功。

采用 body 的form 和 json 形式传输数据

而在文档上,也提供给了我们 form 的形式,通常我们如果需要发送数据到服务器上去,往往采用 post 和 put 这样比较规范的操作(据说使用get也可以,但是有的公司万物皆哈梭 get ,总是不太好,丧失了规范性)

有时同样的代码也会有一写小 bug,通过下面的一些代码,借由 Postman 软件进行发送 post 请求,进行测试


@app.route("/form",methods=['GET','POST'])
def form():
    if request.method == 'POST':
        print(request.form.get('name'))
        print(request.json)
        print(request.data)
        Fname = request.form.get('name','null')
        if (Fname == 'null'):
            Jname = request.json.get('name','null')
            if(Jname == 'qaq'):
                return dict(check = 'true')
        if(Fname == 'pap'):
            return dict(check='true')
        else :
            return dict(check = 'false')
    else :
        return "this is a get request"

可以看到,/form URL 路径仅仅对于 post 请求作出了回应,如果是其他类型的请求,直接返回 “this is a get request”
对于 post 请求,我们在里面放置了两种在 Body 里面的格式内容,分别是 form 和 json
这两种我们都将会去使用:为了避免冲突,所以将 json 和 form 的调试放在了有些不一样的 if 分支里面。
对于 form:

对于 json

部分参考链接:
Bilibili 视频