Интерфейс REST для нахождения среднего

Предположим, я хочу создать интерфейс REST, чтобы найти среднее значение списка чисел. Предположим, что числа передаются по одному. Как бы вы это сделали?

  1. ОТПРАВИТЬ номер на https://example.com/api/average
  2. Если это первое число, будет возвращен хэш
  3. ОТПРАВИТЬ номер на https://example.com/api/average/hash ... .
  4. ПОЛУЧИТЕ https://example.com/api/average/hash, чтобы найти среднее значение
  5. УДАЛИТЕ https://example.com/api/average/hash, так как нам не нужно это больше

Это правильный способ сделать это? Какие-либо предложения?


person Community    schedule 10.01.2009    source источник
comment
Не могли бы вы дать немного больше контекста? Например, какой язык программирования вы используете для диспетчеризации?   -  person Evan Fosmark    schedule 10.01.2009
comment
Выбор языка программирования не обязательно влияет на дизайн REST API.   -  person Peter Hilton    schedule 10.01.2009


Ответы (4)


Имеет больше смысла думать о списке чисел как о ресурсе. Предположим, что URL-адрес ресурса каждого списка — /list/{id}, где {id} — это заполнитель для идентификатора списка. Потом:

  1. POST /list создает новый список, сервер генерирует идентификатор списка (или «хэш») и указывает /list/{id} URL-адрес в заголовке Location ответа.
  2. POST /list/{id} добавляет номер в список
  3. GET /list/{id}/average возвращает среднее
  4. DELETE /list/{id} удаляет список.

Альтернативой GET /list/{id}/average может быть GET /list/{id} для возврата списка в виде структурированных данных, например. XML, который включает среднее значение в качестве сгенерированного свойства.

person Peter Hilton    schedule 10.01.2009
comment
кажется хорошим ответом, но когда или как служба должна определить, когда удалить {id}, если клиент забудет? - person kenny; 10.01.2009
comment
Лично я просто настроил задачу таймера на удаление «старых» списков один раз в день. Если списки не очень большие или частые, вы можете хранить годовой объем. - person Peter Hilton; 10.01.2009

То, о чем вы говорите, - это преобразование без сохранения состояния представления запроса (список чисел) в представление ответа (один номер).

Давайте классифицируем ваш ресурс:

  • Без сохранения состояния. Запрос не имеет состояния, как и ресурс. Он должен иметь возможность принимать ваш запрос, обрабатывать его и возвращать ответ без сохранения какого-либо внутреннего состояния. Дальнейшее обсуждение ниже.
  • Маловероятно, что их можно кэшировать - здесь я делаю предположение, что ваши списки чисел никогда/редко не совпадают.
  • Идемпотент — запросы не имеют побочных эффектов. Это связано с тем, что ресурс не имеет состояния.

Теперь давайте рассмотрим различные методы HTTP:

  • GET — получает состояние ресурса. Поскольку ваш ресурс не имеет состояния, он не подходит для вашей ситуации. (идемпотентный, кэшируемый)
  • DELETE — удаляет ресурс или очищает его состояние. Также не подходит для вашей ситуации. (не идемпотентный, не кешируемый)
  • PUT — используется для установки состояния ресурса (или его создания, если он не существует). (идемпотентный, не кэшируемый)
  • POST — используется для обработки запросов, которые могут изменить или не изменить состояние ресурса. Может создавать другие ресурсы. (нет гарантии идемпотентности - зависит от того, является ли ресурс с сохранением состояния или без состояния, а не кэшируемым)

Как вы видите в других ответах, POST чаще всего используется как синоним слова «создать». Хотя это нормально, POST не ограничивается просто «созданием» в REST. Марк Бейкер хорошо объясняет это здесь: http://www.markbaker.ca/2001/09/draft-baker-http-resource-state-model-01.txt (раздел 3.1.4).

Хотя POST не имеет идеального семантического сопоставления с вашей проблемой, это лучший из всех методов HTTP для того, что вы пытаетесь сделать. Это также приводит к простому, не сохраняющему состояние и масштабируемому решению, которое является точкой REST.

В общем, ответ на ваш вопрос:

  • Метод: ПОСТ
  • Запрос: представление списка чисел
  • Ответ: Представление одного числа (среднее значение списка)

Хотя это может выглядеть как вызов веб-службы в стиле SOAP, это не так. Не позволяйте своей внутренней реакции на SOAP омрачать использование метода POST и накладывать на него ненужные ограничения.

ПОЦЕЛУЙ (Будь проще, глупый).

person user11087    schedule 17.01.2009

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

person aehlke    schedule 21.07.2009

Чтобы максимизировать философию REST, я бы сделал следующее

Сделайте PUT это, чтобы указать новую структуру, которая будет генерировать хэш, который не основан на переданном числе. Просто "случайный" хэш. Затем каждое последующее сообщение будет включать id-хэш с возвращаемым хэшем результата отправленных номеров. Затем, когда на нем представлено получение, вы можете кэшировать результаты.

1. PUT    /api/average/{number} //return id-hash
2. POST   /api/average/{id-hash}/{number} // return average-hash
3. GET    /api/average/{average-hash}
4. DELETE /api/average/{id-hash}

Затем вы можете кэшировать получение среднего хэша, даже если вы можете получить результат по-разному или разные серверы получают одно и то же среднее значение.

person null    schedule 10.01.2009