May 31, 2016

Примечание

Это статья из лекций http://lectureswww.readthedocs.io/6.www.sync/3.framework/pyramid/5.1.rest.html

REST API в Pyramid

REST API

REST API подразумевает под собой простые правила:

  • Каждый URL является ресурсом
  • При обращении к ресурсу методом GET возвращается описание этого ресурса
  • Метод POST добавляет новый ресурс
  • Метод PUT изменяет ресурс
  • Метод DELETE удаляет ресурс

Эти правила предоставляют простой CRUD интерфейс для других приложений, взаимодействие с которым происходит через протокол HTTP.

Соответствие CRUD операций и HTTP методов:

  • CREATE - POST
  • READ - GET
  • UPDATE - PUT
  • DELETE - DELETE

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

Pattern matching

Пример выше добавляет View с тремя методами, каждый из которых вызывается при соответствующем GET, POST, DELETE запросе. Ресурсом здесь является конкретный человек, получить которого можно по URL http://localhost:8080/api/v1/people/123

Результатом запроса будет:

{"get": {}, "id": "123", "method": "GET"}

Для отправки POST запроса воспользуемся консольной утилитой curl:

$ curl -X POST -d 'param1=value1&param2=value2' http://localhost:8080/api/v1/people/1

Результат запроса:

{"id": "1", "post": {"param1": "value1", "param2": "value2"}, "method": "POST"}

DELETE запрос выполняется по аналогии:

$ curl -X DELETE http://localhost:8080/api/v1/people/1

Результат запроса:

{"status": "success"}

Traversal

См.также

Метод URL диспетчеризации Traversal

В предыдущем примере показан только один ресурс - конкретный человек и в принципе все выглядит неплохо, пока не появится другой смежный ресурс, например список всех людей по адресу http://localhost:8080/api/v1/people

В этом случае, придется добавлять новый путь (rout), привязывать его к представлению (View) и самое неприятное менять само представление, или еще хуже писать новое. Таким образом с увеличением ресурсов, сложность REST API растет не пропорционально и в какой то момент код становится не читаемым из-за больших размеров и постоянно меняющейся логики во View.

Выход из данной ситуации - отделить ресурсы от представлений, тем самым вынести часть логики и сделать представления более универсальными.

Ресурсы

Ресурсы могут выглядеть так:

PeopleResource представляет список всех людей и будет доступен по адресу http://localhost:8080/api/v1/people. PeopleResource имеет метод __getitem__, что делает его похожим на словарь. При обращении к объекту ресурса как к словарю, он вызовет эту функцию и передаст ключ в параметр people_id, например:

foo = PeopleResource()
bar = foo[123]  # Вернет объект PersonResource(123)

Метод __json__ определяет каким образом преобразовывать ресурс в json.

PersonResource представляет конкретного человека и будет доступен по адресу http://localhost:8080/api/v1/people/{id}. Здесь отличительной особенностью является то, что метод __json__ наследует часть словаря из класса PeopleResource, при помощи конструкции super:

View

Перепишем View таким образом, что бы она возвращала только ресурс, а так-как ресурс уже содержит в себе информацию как отдавать json, то это представление будет универсальным как для PeopleResource, так и для PersonResource и возможно подойдет другим ресурсам которые мы будем писать в будущем.

Рендерер json по умолчанию ищет метод __json__ и если он есть то возвращает его результат вызова.

Route

Путь, в нашем случае, будет один, так-как вся структура вынесена в ресурсы (метод __getitem__).

config.add_route('rest_api', '/api/v1/*traverse', factory=rest_factory)

Полный пример


Comments

comments powered by Disqus