Пользовательские действия по обновлению в RESTful Services - PullRequest
2 голосов
/ 20 марта 2019

Мой API требует много различных типов обновлений, которые могут выполняться различными типами ролей.В билете могут быть обновлены данные, заявка может быть утверждена (которая включает некоторую информацию), заявка может быть отклонена, заявка может быть заархивирована (состояние, в котором заявка не может быть обновлена) и т. Д.

Я недавно начал работать как бэкэнд-разработчик, и я действительно не знаю, каков наиболее правильный подход к этой ситуации, но я имею в виду две идеи:

  • Одна конечная точка обновления (например,/api/tickets/:id), который принимает поле действия с типом обновления, которое требуется выполнить для этого файла;
  • Несколько конечных точек пользовательских действий (например, /api/tickets/:id/validate, /api/tickets/:id/accept и т. Д.)

Какой из них является лучшим подходом к ситуации, когда речь идет об архитектуре REST?Если оба являются неправильными, когда дело доходит до REST, что будет наиболее правильным подходом?Я не смог найти ни одного поста на SO, который ответил бы на мой вопрос, поэтому я решил создать свой собственный.Спасибо!

Ответы [ 4 ]

1 голос
/ 20 марта 2019

На самом деле все сводится к вкусу.В промышленности часто наблюдается наличие статических параметров в URL (например: /tickets/update, /users/add, /admin/accounts) и переменных параметров в запросе (например: идентификаторы, сообщения, имена).Это позволяет иметь фиксированное количество конечных точек.

Я вижу, что вы используете NodeJS, поэтому вы, вероятно, используете Express и в Express, получить параметры url и параметры тела одинаково легко:

// supposing you're using a JSON-based API with body-parser for JSON parsing
app.get('/some/path/:someParam', (req, res) => {
    console.log(req.params.someParam);
    console.log(req.body.someOtherParam);
    res.send();
}
1 голос
/ 20 марта 2019

REST - это все ресурсов . И состояние ресурсов должно управляться с использованием представлений (таких как JSON, XML, как вы его называете) на вершине связи без состояния между клиентом и сервером.

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

Выполнение частичных обновлений

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

Существует несколько форматов, которые можно использовать для описания набора изменений, которые будут применены к ресурсу:

JSON Merge Patch

Он определен в RFC 7396 и может применяться, как описано ниже:

Если предоставленное исправление слияния содержит элементы, которые не отображаются внутри цели, эти элементы добавляются. Если цель содержит член, значение заменяется. Нулевые значения в патче слияния имеют особое значение для обозначения удаления существующих значений в целевом объекте.

Таким образом, запрос на изменение status заявки может выглядеть следующим образом:

PATCH /api/tickets/1 HTTP/1.1
Host: example.org
Content-Type: application/merge-patch+json

{
  "status": "valid"
}

JSON Patch

Он определен в RFC 6902 и выражает последовательность операций, которые должны применяться к целевому документу JSON. Запрос на изменение status билета может выглядеть так:

PATCH /api/tickets/1 HTTP/1.1
Host: example.org
Content-Type: application/json-patch+json

[
  {
    "op": "replace",
    "path": "/status",
    "value": "valid"
  }
]

path - это значение указателя JSON, как описано в RFC 6901 .

1 голос
/ 20 марта 2019

REST означает Передачу состояния представления, что означает, что клиент и сервер влияют на состояние друг друга, обмениваясь представлениями ресурсов.

Клиент может GET представить билет так:

GET /api/tickets/123 HTTP/1.1

HTTP/1.1 200 OK
Content-Type: application/json

{
    "id": 123, 
    "state": "new",
    "archived": false,
    "comments": []
}

Теперь клиент может PUT новое представление (заменяя его оптом) или PATCH определенные части существующего:

PATCH /api/tickets/123 HTTP/1.1
Content-Type: application/json-patch+json

[
    {"op": "replace", "path": "/state", "value": "approved"},
    {"op": "add", "path": "/comments", "value": {
        "text": "Looks good to me!"
    }}
]


HTTP/1.1 200 OK
Content-Type: application/json

{
    "id": 123,
    "state": "approved",
    "archived": false,
    "comments": [
        {"author": "Thomas", "text": "Looks good to me!"}
    ]
}

Обратите внимание, как обновление выражается в терминах , что необходимо изменить в представлении JSON , используя стандартный формат JSON Patch . Клиент может использовать тот же подход для обновления любого ресурса, представленного в JSON. Это способствует единому интерфейсу , отделяющему клиента от конкретного сервера.

Конечно, сервер не должен поддерживать произвольные обновления:

PATCH /api/tickets/123 HTTP/1.1
Content-Type: application/json-patch+json

[
    {"op": "replace", "path": "/id", "value": 456}
]


HTTP/1.1 422 Unprocessable Entity
Content-Type: text/plain

Cannot replace /id.

Тем не менее, это может потребовать большей сложности на сервере, чем выделенные операции, такие как «утверждение», «отклонение» и т. Д. Возможно, вы захотите использовать библиотеку для реализации JSON Patch. Если вы обнаружите, что вам нужно много пользовательских действий, которые трудно выразить в терминах представления, архитектура RPC может подойти вам лучше, чем REST.

1 голос
/ 20 марта 2019

Попробуйте либо

  • Сделка с одним объектом -> api/v1/tickets/1
  • Работа со списком объектов -> api/v1/tickets/.

Затем попытайтесь зафиксировать все действия как действия CRUD.

  • Создать объект (ы) -> HTTP POST
  • Получить объект (ы) -> HTTP GET
  • Обновить объект (ы) -> HTTP PATCH
  • Удалить объект (ы) -> HTTP DELETE

А также:

  • Сохранить объект (ы) полностью -> HTTP PUT

Когда вы меняете статусы, а это только атрибуты в заявке. Я бы отправил запрос PATCH, например. Если мне нужно изменить статус билета № 1 на «отклоненный», я бы отправил что-то вроде PATCH api/v1/tickets/1 с полезной нагрузкой, например:

{
    "status": "rejected"
}

У ОТДЫХА есть много лучших практик, но не все в камне. Может быть, этот урок: https://restfulapi.net может помочь вам?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...