我已阅读Django Rest Framework指南并完成了所有教程。一切似乎都有意义,并且应该如何运作。我按照描述进行基本和会话认证。 http://django-rest-framework.org/api-guide
但是,我正在努力使用文档的令牌认证部分,它有点缺乏或没有深入到教程的深度。
http://django-rest-framework.org/api-guide/authentication/#tokenauthentication
它说我需要为用户创建令牌,但确实在models.py?
中说明了哪里我的问题是:
有人可以为第一个计时器更好地解释文档的令牌认证部分吗?
答案 0 :(得分:77)
@ ian-clelland已经提供了正确的答案。他的文章中只提到了一些小件,所以我将记录完整的程序(我使用的是Django 1.8.5和DRF 3.2.4):
执行以下操作之前,即可创建超级用户。否则,超级用户不会创建他/她的令牌。
转到 settings.py 并添加以下内容:
INSTALLED_APPS = (
'rest_framework',
'rest_framework.authtoken',
'myapp',
)
REST_FRAMEWORK = {
'DEFAULT_PERMISSION_CLASSES': (
'rest_framework.permissions.IsAuthenticated',
),
'DEFAULT_AUTHENTICATION_CLASSES': (
'rest_framework.authentication.TokenAuthentication',
)
}
在 myapp 的 models.py 中添加以下代码:
from django.db.models.signals import post_save
from django.dispatch import receiver
from rest_framework.authtoken.models import Token
from django.conf import settings
# This code is triggered whenever a new user has been created and saved to the database
@receiver(post_save, sender=settings.AUTH_USER_MODEL)
def create_auth_token(sender, instance=None, created=False, **kwargs):
if created:
Token.objects.create(user=instance)
或者,如果您想更明确,请在 myapp 项目下创建名为 signals.py 的文件。将上面的代码放在其中,然后在 __ init __。py 中,写下import signals
打开控制台窗口,导航到项目目录,然后输入以下命令:
python manage.py migrate
python manage.py makemigrations
查看数据库,应创建一个名为 authtoken_token 的表,其中包含以下字段:key(这是标记值),创建(创建它的日期时间),user_id(a引用auth_user表的id列的外键)
使用python manage.py createsuperuser
创建超级用户。现在,使用select * from authtoken_token;
查看数据库中的 authtoken_token 表,您应该会看到添加了新条目。
使用curl
或更简单的替代httpie来测试对api的访问权限,我使用的是httpie:
http GET 127.0.0.1:8000/whatever 'Authorization: Token your_token_value'
就是这样。从现在开始,对于任何API访问,您需要在HTTP标头中包含以下值(注意空白):
Authorization: Token your_token_value
(可选)如果您提供用户名和密码,DRF还可以返回用户的令牌。您所要做的就是在 urls.py :
中加入以下内容from rest_framework.authtoken import views
urlpatterns = [
...
url(r'^api-token-auth/', views.obtain_auth_token),
]
使用httpie验证:
http POST 127.0.0.1:8000/api-token-auth/ username='admin' password='whatever'
在返回机构中,您应该看到:
{
"token": "blah_blah_blah"
}
就是这样!
答案 1 :(得分:61)
不,不在您的models.py中 - 在模型方面,您需要做的就是在rest_framework.authtoken
中添加相应的应用(INSTALLED_APPS
)。这将提供一个外键键入用户的Token模型。
您需要做的是决定何时以及如何创建这些令牌对象。在您的应用中,每个用户都会自动获得令牌吗?或者只有某些授权用户?或者只有当他们特意请求一个?
如果每个用户都应该有一个令牌,那么您链接到的页面上会有一段代码,告诉您如何设置信号以自动创建它们:
@receiver(post_save, sender=User)
def create_auth_token(sender, instance=None, created=False, **kwargs):
if created:
Token.objects.create(user=instance)
(将 this 放在models.py文件中的任何地方,并在Django线程启动时注册)
如果只应在特定时间创建令牌,那么在您的视图代码中,您需要在适当的时间创建和保存令牌:
# View Pseudocode
from rest_framework.authtoken.models import Token
def token_request(request):
if user_requested_token() and token_request_is_warranted():
new_token = Token.objects.create(user=request.user)
创建(并保存)令牌后,它将可用于身份验证。
答案 2 :(得分:13)
只是为了增加我的两分钱,如果你有一个处理用户创建(和激活)的自定义用户管理器,你也可以像这样执行这个任务:
from rest_framework.authtoken.models import Token
# Other imports
class UserManager(BaseUserManager):
def create_user(self, **whatever_else):
"""
This is your custom method for creating user instances.
IMHO, if you're going to do this, you might as well use a signal.
"""
user = self.model(**whatever_params)
.... #Method ramblings that somehow gave us a user instance
Token.objects.create(user=user)
#You may also choose to handle this upon user activation.
#Again, a signal works as well here.
def activate_user(**activation_ramblings):
.... #Method ramblings that somehow gave us a user instance
Token.objects.create(user=user)
如果您已经创建了用户,那么您可以直接进入终端中的python shell并为数据库中的所有用户创建令牌。
>>>from *whatever import User
>>>from rest_framework.authtoken.models import Token
>>>for user in User.objects.all():
>>>... Token.objects.create(user=user)
这就是她写的所有人!希望能帮助别人。
答案 3 :(得分:13)
在Django 1.8.2和rest framework 3.3.2之后,上述所有内容都不足以启用基于令牌的身份验证。
虽然在django设置文件中指定了REST_FRAMEWORK设置,但基于函数的视图需要@api_view装饰器:
from rest_framework.decorators import api_view
@api_view(['POST','GET'])
def my_view(request):
if request.user.is_authenticated():
...
否则,不会执行任何令牌身份验证
答案 4 :(得分:9)
有一种更简洁的方法来获取用户令牌。
只需运行manage.py shell
然后
from rest_framework.authtoken.models import Token
from django.contrib.auth.models import User
u = User.objects.get(username='admin')
token = Token.objects.create(user=u)
print token.key
然后应在表DB_Schema.authtoken_token
中找到记录答案 5 :(得分:5)
除了这里的优秀答案之外,我还想提一下更好的令牌认证方法:JSON Web令牌认证。 http://getblimp.github.io/django-rest-framework-jwt/提供的实现非常易于使用。
this answer中详细解释了这些好处。
答案 6 :(得分:1)
JSON Web令牌认证比令牌认证更好。该项目已使用Django(http://getblimp.github.io/django-rest-framework-jwt/)实现了JWT Auth,但当前该项目尚未维护。
有关替代方法,您可以遵循:https://github.com/davesque/django-rest-framework-simplejwt