Статьи

Создание RESTful API с помощью Flask: ORM с помощью SQLAlchemy

В первой части этой серии из трех частей мы увидели, как сами писать RESTful API, используя Flask в качестве веб-фреймворка. Предыдущий подход обеспечивал большую гибкость, но также включал в себя написание большого количества кода, которого иначе можно было бы избежать в более общих случаях.

В этой части мы будем использовать расширение Flask Flask-Restless , которое просто генерирует API RESTful для моделей баз данных, определенных с помощью SQLAlchemy. Я возьму тот же пример приложения, что и в последней части этой серии, чтобы сохранить контекст и преемственность.

Продолжая работу с приложением из первой части, нам нужно установить только одну зависимость:

1
$ pip install Flask-Restless

Flask-Restless упрощает добавление интерфейсов API RESTful к моделям, написанным с использованием SQLAlchemy. Сначала добавьте REST APIManager из расширения flask.ext.restless в файл конфигурации приложения.

1
2
3
from flask.ext.restless import APIManager
 
manager = APIManager(app, flask_sqlalchemy_db=db)

Достаточно просто добавить вышеупомянутую пару строк в существующий код.

Этот файл содержит основную часть изменений из предыдущей части. Ниже приведен полный переписанный файл.

01
02
03
04
05
06
07
08
09
10
11
12
from flask import Blueprint
from my_app import manager
from my_app.catalog.models import Product
 
catalog = Blueprint(‘catalog’, __name__)
 
@catalog.route(‘/’)
@catalog.route(‘/home’)
def home():
    return «Welcome to the Catalog Home.»
 
manager.create_api(Product, methods=[‘GET’, ‘POST’])

Это довольно очевидно, как работает приведенный выше код. Мы только что импортировали manager , созданный в предыдущем файле, и он используется для создания API для модели Product с помощью перечисленных methods . Мы можем добавить больше методов, таких как DELETE , PUT , PATCH и т. Д. По мере необходимости.

Давайте протестируем это приложение, создав несколько продуктов и перечислив их. Конечной точкой, созданной этим расширением по умолчанию, является http://localhost:5000/api/product .

Как и в предыдущей части этого урока, я протестирую это с помощью библиотеки requests через терминал.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
>>> import requests
>>> import json
>>> res = requests.get(‘http://127.0.0.1:5000/api/product’)
>>> res.json()
{u’total_pages’: 0, u’objects’: [], u’num_results’: 0, u’page’: 1}
>>> d = {‘name’: u’iPhone’, ‘price’: 549.00}
>>> res = requests.post(‘http://127.0.0.1:5000/api/product’, data=json.dumps(d), headers={‘Content-Type’: ‘application/json’})
>>> res.json()
{u’price’: 549.0, u’id’: 1, u’name’: u’iPhone’}
>>> d = {‘name’: u’iPad’, ‘price’: 649.00}
>>> res = requests.post(‘http://127.0.0.1:5000/api/product’, data=json.dumps(d), headers={‘Content-Type’: ‘application/json’})
>>> res.json()
{u’price’: 649.0, u’id’: 2, u’name’: u’iPad’}
>>> res = requests.get(‘http://127.0.0.1:5000/api/product’)
>>> res.json()
{u’total_pages’: 1, u’objects’: [{u’price’: 549.0, u’id’: 1, u’name’: u’iPhone’}, {u’price’: 649.0, u’id’: 2, u’name’: u’iPad’}], u’num_results’: 2, u’page’: 1}

Действительно удобно автоматически создавать API-интерфейсы RESTful, но каждое приложение имеет некоторую бизнес-логику, которая требует настройки, проверки и умной / безопасной обработки запросов по мере необходимости.

Здесь на помощь приходят запросы preprocessors и postprocessors . Как видно из названий, методы, назначенные в качестве препроцессоров, выполняются до обработки запроса, а методы, назначенные в качестве постпроцессоров, запускаются после обработки запроса. create_api() — это место, где они определены как словари типа запроса ( GET , POST и т. д.), а методы — как список, который будет выполнять роль препроцессора или постпроцессора по указанному запросу. Ниже приведен пример шаблона:

01
02
03
04
05
06
07
08
09
10
11
12
manager.create_api(
    Product,
    methods=[‘GET’, ‘POST’, ‘DELETE’],
    preprocessors={
        ‘GET_SINGLE’: [‘a_preprocessor_for_single_get’],
        ‘GET_MANY’: [‘another_preprocessor_for_many_get’],
        ‘POST’: [‘a_preprocessor_for_post’]
    },
    postprocessors={
        ‘DELETE’: [‘a_postprocessor_for_delete’]
    }
)

Запросы GET , PUT и PATCH могут быть запущены как для одной, так и для нескольких записей; следовательно, у них есть два типа каждый. В приведенном выше коде обратите внимание на GET_SINGLE и GET_MANY для запросов GET .

Препроцессоры и постпроцессоры принимают разные параметры для каждого типа запроса и работают без какого-либо возвращаемого значения. Это оставлено для вас, чтобы попробовать самостоятельно.

В этой части этой серии руководств мы увидели, как создать RESTful API с помощью Flask, просто добавив пару строк в модель на основе SQLAlchemy.

В следующей и последней части этой серии я расскажу, как создать RESTful API с использованием другого популярного расширения Flask, но на этот раз API будет независимым от инструмента моделирования, используемого для базы данных.