Skip to content

rinnothing/simple-jwt

Repository files navigation

simple-jwt

Условия

В этом проекте я создал сервис jwt-аутентификации по этому тз:

Задание

Необходимо реализовать часть сервиса аутентификации. Сервис должен предоставлять четыре конечные точки API:

  • на получение пары токенов (access и refresh) для пользователя с идентификатором (GUID) указанным в параметре запроса;
  • на обновление пары токенов;
  • на получение GUID текущего пользователя (роут должен быть защищен);
  • на деавторизацию пользователя (поле выполнения этого запроса с access токеном, пользователю больше не должен быть доступен роут на получение его GUID и операция обновления токенов).

Требования

Требования к access токену:

  1. Формат токена - JWT,
  2. Алгоритм для подписи токена - SHA512,
  3. Хранить токен в базе строго запрещено.

Требования к refresh токену

  1. Формат токена - произвольный.
  2. Передаваться токен должен только в формате base64.
  3. Хранить токен в базе строго в виде bcrypt хеша.
  4. Токен должен быть защищен от повторного использования.
  5. Токен должен быть защищен от изменений на стороне клиента.

Требования к операции refresh

  1. Операцию refresh можно выполнить только той парой токенов, которая была выдана вместе.
  2. Необходимо запретить операцию обновления токенов при изменении User-Agent. При этом, после неудачной попытки выполнения операции, неоходимо деавторизовать пользователя, который попытался выполнить обновление токенов.
  3. При попытке обновления токенов с нового IP необходимо отправить POST-запрос на заданный webhook с информацией о попытке входа со стороннего IP. Запрещать операцию в данном случае не нужно.

Реализация и комментарии

Увидеть ручки и их краткое описание можно в api/openapi.yaml
Я реализовал jwt по описанию с википедии, а вот для refresh я придумал кое-что своё, чтобы обеспечить работу пары токенов только вместе я убрал из refresh header, а payload заменил на sha512 кеш access, чтобы защитить ключ от изменения я добавил к нему подпись, а потом перевёл в base64 (не в base64url, т.к. в условии говорилось именно про base64)
Также в условии ничего не говорилось про хранение ключей, но я посчитал, что если уж мы храним данные в бд, то нам будет полезно сохранять не только сессии, но и ключи, чтобы продолжать с ними работать
Для демонстрации работы у меня написан интеграционный тест (без проверки вебхуков и проверки user-agent), но для его работы нужно откомментировать несколько строчек в docker-compose.yml и поменять хост в конфиге с db на localhost
(я написал его, как и половину Makefile для себя, поэтому оно не обязано работать по одной кнопке)

About

No description, website, or topics provided.

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published