Выйти Django Rest Framework JWT

Я хочу спросить, если это хорошая идея, чтобы выйти из системы, когда я использую JWT. Для входа в систему я отправляю почтовый запрос с именем пользователя и паролем, чтобы получить нужный токен (сохраненный в localStorage), что позволит мне отправлять дополнительные запросы в представления, для которых, разумеется, требуется токен.

Но я не уверен, как мне выйти из системы. Я могу очистить localStorage, но токен остается доступным.

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

заранее спасибо

4 ответа

Решение

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

class BlackListedToken(models.Model):
    token = models.CharField(max_length=500)
    user = models.ForeignKey(User, related_name="token_user", on_delete=models.CASCADE)
    timestamp = models.DateTimeField(auto_now=True)

    class Meta:
        unique_together = ("token", "user")


class IsTokenValid(BasePermission):
    def has_permission(self, request, view):
        user_id = request.user.id            
        is_allowed_user = True
        try:
            is_blackListed = BlackListedToken.objects.get(user=user_id, token=token)
            if is_blackListed:
                is_allowed_user = False
        except BlackListedToken.DoesNotExist:
            is_allowed_user = True
        return is_allowed_user

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

Вы не можете вручную истечь токен после того, как он был создан. Таким образом, вы не можете фактически выйти из JWT на стороне сервера, как вы делаете с сеансами.

JWT не имеет состояния, что означает, что вы должны хранить все, что вам нужно, в полезной нагрузке и пропустить выполнение запросов к БД для каждого запроса. Но если вы планируете иметь строгую функциональность выхода из системы, которая не может ожидать автоматического истечения срока действия токена, даже если вы очистили токен со стороны клиента, вам может понадобиться пренебречь логикой без сохранения состояния и выполнить некоторые запросы. так в чем же решение?

  • Установите разумное время истечения для токенов

  • Удалить сохраненный токен со стороны клиента при выходе

  • Запрос выдан токен против черного списка на каждый авторизованный запрос

Черный список

"Черный список" всех токенов, которые больше не действительны и еще не истек. Вы можете использовать базу данных с опцией TTL для документов, для которой будет задано время, оставшееся до истечения срока действия токена.

Redis

Redis - хороший вариант для черного списка, который позволяет быстро получить доступ к списку в памяти. Затем в промежуточном программном обеспечении, которое запускается при каждом авторизованном запросе, вы должны проверить, есть ли предоставленный токен в черном списке. Если это так, вы должны выдать несанкционированную ошибку. А если это не так, отпустите его, и проверка JWT обработает его и определит, истек ли он или все еще активен.

Каждый JWT, который вы выпускаете, должен иметь дату истечения срока действия, поэтому всякий раз, когда вы выходите из системы, вы должны удалить jwt-токен из файла cookie localalstorage.

но токен остается доступным.

Не уверен, что означает указанная выше строка, но вам не стоит беспокоиться о том, останется ли токен доступным для пользователя или нет после того, как вы очистите его от localstorage и cookie, потому что в любом случае он станет недействительным после истечения срока действия.

Более простым способом достижения этого будет использованиеrest_framework_simplejwtупаковка. Я полагаю, что вы также использовали тот же пакет для генерации JWT.

Пока пользователь выполняет выход из системы, вам необходимо очистить кеш на интерфейсе, а также добавить токен обновления в черный список на сервере.

Токены доступа недолговечны, и их не нужно заносить в черный список. Предпочтительно иметь минимальный срок жизни токенов доступа. Так что они в конечном итоге истекают.

rest_framework_simplejwt.token_blacklistпо умолчанию заносит в черный список только токены обновления.

Все, что вам нужно сделать, это добавить следующее приложение в ваш settings.py INSTALLED_APPS.

      INSTALLED_APPS = (
    'rest_framework_simplejwt.token_blacklist',
)

А также настройте urls.py дляTokenBlacklistView

      from rest_framework_simplejwt.views import TokenBlacklistView

    urlpatterns = [
      ...
      path('logout/', TokenBlacklistView.as_view(), name='token_blacklist'),
      ...
    ]

Источник: https://django-rest-framework-simplejwt.readthedocs.io/en/latest/blacklist_app.html .

Другие вопросы по тегам