简体   繁体   English

如何在重置密码时撤消刷新令牌?

[英]How to revoke refresh token on password reset?

I am using django-rest-framework-simplejwt to get access token and refresh token . 我正在使用django-rest-framework-simplejwt获取access tokenrefresh token

The problem is that refresh token is not becoming invalid if I change the password of the user. 问题是,如果我更改用户密码, refresh token不会变得无效。 Basically I can continue to send refresh token and get new access tokens even after user has changed password. 基本上,即使用户更改了密码,我也可以继续发送refresh token并获取新的访问令牌。

What I would like instead is to ask user to re-submit the username and new password to get a new pair of access and refresh tokens . 相反,我想让用户重新提交用户名和新密码,以获得一对新的accessrefresh tokens

How would I accomplish this? 我将如何完成?



PS: Just because I am curious, shouldn't this be the default behaviour of the library? PS:只是因为我很好奇,难道这不是图书馆的默认行为吗? In what case would we want to retain the refresh token after credentials have changed? 在哪种情况下,凭证更改后,我们要保留refresh token吗?

I figured how to get this working. 我想出了如何使它工作。
What I am did is put a signal that tracks if any required parameter has changed. 我所做的是放置一个信号,该信号跟踪是否更改了任何必需的参数。 If so, it blacklists all the refresh tokens associated with that user. 如果是这样,它将把与该用户关联的所有刷新令牌列入黑名单。
Here is the code: 这是代码:

First add 'rest_framework_simplejwt.token_blacklist' in installed apps. 首先在已安装的应用程序中添加'rest_framework_simplejwt.token_blacklist' Then: 然后:

@receiver(signals.pre_save, sender=User)
def revoke_tokens(sender, instance, update_fields, **kwargs):
    if not instance._state.adding: #instance._state.adding gives true if object is being created for the first time
        existing_user = User.objects.get(pk=instance.pk)
        if instance.password != existing_user.password or instance.email != existing_user.email or instance.username != existing_user.username:
        # If any of these params have changed, blacklist the tokens
              outstanding_tokens = OutstandingToken.objects.filter(user__pk=instance.pk)
              # Not checking for expiry date as cron is supposed to flush the expired tokens
              # using manage.py flushexpiredtokens. But if You are not using cron, 
              # then you can add another filter that expiry_date__gt=datetime.datetime.now()

              for out_token in outstanding_tokens:
                   if hasattr(out_token, 'blacklistedtoken'):
                       # Token already blacklisted. Skip
                       continue

                       BlacklistedToken.objects.create(token=out_token)

WHat this code basically does is , gets all outstanding tokens for the user, then adds all of them to blacklist. 该代码的主要作用是,为用户获取所有未完成的令牌,然后将所有令牌添加到黑名单中。 You can get more info on outstanding/blacklisted tokens here. 您可以在此处获取有关未处理/列入黑名单的令牌的更多信息。 https://github.com/davesque/django-rest-framework-simplejwt#blacklist-app https://github.com/davesque/django-rest-framework-simplejwt#blacklist-app

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM