Flask扩展系列1--Restful

2021-02-20  本文已影响0人  jinjin1009

1、首先了解什么是restful架构?

rest:representational state transfer表现层状态转化

资源:网络上的一个实体,或者说一个具体的信息。每种资源对应一个特定的URI,要获取这个资源,就是访问这个URI就可以

表现层:representation 把资源呈现出来的形式,叫做表现层,在HTTP请求的头信息中用Accept和Content-Type字段指定,是对“表现层”的描述

状态转化:客户端想要操作服务器,必须通过某种手段,让服务器发生状态转化,有GETPOSTPUTDELETE四种方式,其中GET是用来获取资源,POST是用来新建资源(也可以进行更新资源),PUT用来更新资源,DELETE用来删除资源

所以restful架构是:
1)每一个URI代表一个资源;
2)客户端和服务器之间,传递这种资源的某种表现层;
3)客户端通过四个HTTP动词,对服务器端资源进行操作,实现“表现层状态转化”;

误区:最常见的一种设计错误,就是URI中包含动词。因为“资源”表示一种实体,所以应该是名词,URI不应该有动词,动词应该放到HTTP协议中

2、Flask-RESTful基本请求

from flask import Flask, request
from flask_restful import Api, Resource

app = Flask(__name__)
api = Api(app)

USER_LIST = {
    '1': {'name': 'Michael'},
    '2': {'name': 'Tom'}
}

class UserList(Resource):
    def get(self):
        return USER_LIST

    def post(self):
        user_id = int(max(USER_LIST.keys())) + 1
        user_id = str(user_id)
        USER_LIST[user_id] = {'name': request.form['name']}
        return USER_LIST

api.add_resource(UserList, '/users')

if __name__ == '__main__':
    app.run(host='0.0.0.0', debug=True)

其中一个接口有两种请求方式,一个是get,另一个是post。
get返回USER_LIST这个json数据;
post需要传一个参数,然后返回整个USER_LIST,请求一次post方法就会多添加一次数据,如果post请求中找不到name字段,则返回“400 Bad Request”错误;
由于类UserList没有定义put()和delete()函数,所以在”PUT”或”DELETE”请求时会返回”405 Method Not Allowed”错误。
其中在postman中是这么进行传递的
GET请求

image.png

POST请求

image.png
image.png

另外,路由支持多个路径,比如:

api.add_resource(UserList, '/userlist', '/users')

访问userlist和users两个路径的效果完全一样

3、带参数的请求
上面的例子中我们都是针对USER_LIST这个列表的,如果我们需要针对具体的user进行操作呢,就需要传递具体的user_id了,这时候,我们就需要路由支持带参数。

from flask import Flask, request
from flask_restful import Api, Resource

app = Flask(__name__)
api = Api(app)

USER_LIST = {
    '1': {'name': 'Michael'},
    '2': {'name': 'Tom'}
}

class User(Resource):
    def get(self, user_id):
        return USER_LIST[user_id]

    def delete(self, user_id):
        del USER_LIST[user_id]
        return ''

    def post(self, user_id):
        USER_LIST[user_id] = {'name': request.form['name']}
        return USER_LIST

api.add_resource(User, '/users/<user_id>')

if __name__ == '__main__':
    app.run(host='0.0.0.0', debug=True)

在User类的get(),post(),put()等成员函数中,记得加上参数user_id来获取传入的变量值

4、参数解析
在“POST”和“PUT”请求中,直接访问form表单并验证的工作有些麻烦,Flask-RESTful提供了 reqparse库来简化,可以通过parser.add_argument()方法来定义form表单字段,并指定其类型,然后在put或者post函数中调用parser.parse_args()来获取表单内容,并返回一个字典,该字典就包含表单的内容。parser.parse_args()方法会自动验证数据类型,返回400错误,还可以添加strict参数,如parser.parse_args(strict=True),此时出现为定义的参数,也会返回400错误

from flask import Flask
from flask_restful import Api, Resource, reqparse, abort

app = Flask(__name__)
api = Api(app)

USER_LIST = {
    '1': {'name': 'Michael'},
    '2': {'name': 'Tom'}
}

parser = reqparse.RequestParser()
parser.add_argument('name', type=str)

def abort_if_not_exist(user_id):
    if user_id not in USER_LIST:
        abort(404, message='User {} does not exist'.format(user_id))

class User(Resource):
    def get(self, user_id):
        abort_if_not_exist(user_id)
        return USER_LIST[user_id]

    def delete(self, user_id):
        abort_if_not_exist(user_id)
        del USER_LIST[user_id]
        return '', 204

    def post(self, user_id):
        args = parser.parse_args(strict=True)
        USER_LIST[user_id] = {'name': args['name']}
        return USER_LIST, 201

class UserList(Resource):
    def get(self):
        return USER_LIST

    def post(self):
        args = parser.parse_args(strict=True)
        user_id = str(int(max(USER_LIST.keys())) + 1)
        USER_LIST[user_id] = {'name': args['name']}
        return USER_LIST, 201

api.add_resource(User, '/users/<user_id>')
api.add_resource(UserList, '/users')

if __name__ == '__main__':
    app.run(host='0.0.0.0', debug=True)
上一篇下一篇

猜你喜欢

热点阅读