Проблема
http-api отдаётся статичным моком prism (bin/start.sh, запуск без -d). Такой мок возвращает пример из спецификации дословно и всегда один и тот же, поэтому не умеет двух вещей.
Не применяет skip и limit. Оба запроса дают идентичный ответ:
$ curl -s 'https://http.hexlet.app/http-api/tasks?skip=5&limit=10'
{"tasks":[{"id":1,...},{"id":2,...},{"id":3,...}],"total":3,"skip":0,"limit":30}
$ curl -s 'https://http.hexlet.app/http-api/tasks'
{"tasks":[{"id":1,...},{"id":2,...},{"id":3,...}],"total":3,"skip":0,"limit":30}
Не отбирает записи по пути. GET /tasks/2 возвращает не задачу 2, а тот же единственный пример модели Task:
$ curl -s https://http.hexlet.app/http-api/tasks/2
{"id":1,"title":"Опубликовать курс по основам JavaScript",...}
То же касается /users/{id}, /posts/{id} и /users/1/posts (последний отдаёт тот же список, что /posts, поэтому в примерах спецификации все посты пришлось приписать автору 1, иначе списки противоречат друг другу).
Почему это важно
Курс HTTP API учит на этом сервере, и уроки приходится подгонять под ограничение мока вместо того, чтобы показывать нормальное поведение API.
250-example просит студента выполнить запрос со skip и limit, а затем сравнить ответ. Пришлось прямо написать, что сервер эти параметры не применяет — иначе одинаковый ответ читается как поломка.
400-kinds сравнивает REST и RPC на одной задаче. Пришлось перевести RPC-запросы на задачу 1, потому что по REST любой /tasks/{id} отдаёт задачу 1. Взять задачу 2 нельзя: REST вернул бы не её.
До статичного мока обе проблемы существовали тоже, просто прятались за случайными данными faker'а: ответы различались, но случайным образом и вне спецификации (отрицательные id при объявленном uint16).
Предлагаемое решение
Забрать /tasks у prism и реализовать в custom-server, на том же наборе данных, что уже использует JSON-RPC (custom-server/src/data/tasks.js). Тогда REST и RPC будут делить не только текст задач, но и логику, а /tasks/2 начнёт отдавать задачу 2.
В Caddyfile для этого нужен handle /http-api/tasks* на порт приложения (4010) перед общим handle_path /http-api/* на prism (4011).
Обязательное условие: сохранить коды ответов, на которых построены самостоятельные. Сейчас их даёт prism из спецификации, при переносе их придётся воспроизвести руками:
| Запрос |
Код |
GET /tasks |
200 |
GET /tasks/1 |
200 |
GET /tasks/999 |
404 |
POST /tasks с телом {} |
422 |
DELETE /tasks |
405 |
DELETE /tasks/1 |
204 |
Проверка этих кодов уже есть в bin/smoke-test.js, то есть регресс поймается на make test.
Дальше по той же схеме можно перенести /users, /posts и /comments, но начинать имеет смысл с /tasks: на них опираются два урока.
После починки
Правки в courses/ru/http_api_course, помеченные там скрытыми комментариями со ссылкой на этот issue:
250-example/self_study.md — убрать оговорку про то, что skip и limit не применяются;
400-kinds/self_study.md — можно вернуть сравнение на задаче 2, если так удобнее автору.
Обнаружено по FEEDBACK-36, при проверке #15.
Проблема
http-apiотдаётся статичным моком prism (bin/start.sh, запуск без-d). Такой мок возвращает пример из спецификации дословно и всегда один и тот же, поэтому не умеет двух вещей.Не применяет
skipиlimit. Оба запроса дают идентичный ответ:Не отбирает записи по пути.
GET /tasks/2возвращает не задачу 2, а тот же единственный пример моделиTask:То же касается
/users/{id},/posts/{id}и/users/1/posts(последний отдаёт тот же список, что/posts, поэтому в примерах спецификации все посты пришлось приписать автору 1, иначе списки противоречат друг другу).Почему это важно
Курс HTTP API учит на этом сервере, и уроки приходится подгонять под ограничение мока вместо того, чтобы показывать нормальное поведение API.
250-exampleпросит студента выполнить запрос соskipиlimit, а затем сравнить ответ. Пришлось прямо написать, что сервер эти параметры не применяет — иначе одинаковый ответ читается как поломка.400-kindsсравнивает REST и RPC на одной задаче. Пришлось перевести RPC-запросы на задачу 1, потому что по REST любой/tasks/{id}отдаёт задачу 1. Взять задачу 2 нельзя: REST вернул бы не её.До статичного мока обе проблемы существовали тоже, просто прятались за случайными данными faker'а: ответы различались, но случайным образом и вне спецификации (отрицательные
idпри объявленномuint16).Предлагаемое решение
Забрать
/tasksу prism и реализовать вcustom-server, на том же наборе данных, что уже использует JSON-RPC (custom-server/src/data/tasks.js). Тогда REST и RPC будут делить не только текст задач, но и логику, а/tasks/2начнёт отдавать задачу 2.В
Caddyfileдля этого нуженhandle /http-api/tasks*на порт приложения (4010) перед общимhandle_path /http-api/*на prism (4011).Обязательное условие: сохранить коды ответов, на которых построены самостоятельные. Сейчас их даёт prism из спецификации, при переносе их придётся воспроизвести руками:
GET /tasksGET /tasks/1GET /tasks/999POST /tasksс телом{}DELETE /tasksDELETE /tasks/1Проверка этих кодов уже есть в
bin/smoke-test.js, то есть регресс поймается наmake test.Дальше по той же схеме можно перенести
/users,/postsи/comments, но начинать имеет смысл с/tasks: на них опираются два урока.После починки
Правки в
courses/ru/http_api_course, помеченные там скрытыми комментариями со ссылкой на этот issue:250-example/self_study.md— убрать оговорку про то, чтоskipиlimitне применяются;400-kinds/self_study.md— можно вернуть сравнение на задаче 2, если так удобнее автору.Обнаружено по FEEDBACK-36, при проверке #15.