Skip to content

Instantly share code, notes, and snippets.

@tetafro
Last active April 5, 2023 17:25
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 2 You must be signed in to fork a gist
  • Save tetafro/477e613e9f79eed01cdce8ac09132ec5 to your computer and use it in GitHub Desktop.
Save tetafro/477e613e9f79eed01cdce8ac09132ec5 to your computer and use it in GitHub Desktop.
Django token auth backend
from apps.users.models import User, Token
class TokenBackend(object):
"""Token authentication for API"""
def authenticate(self, token=None):
try:
token = Token.objects.get(key=token)
return token.user
except Token.DoesNotExist:
return None
def get_user(self, user_id):
try:
return User.objects.get(pk=user_id)
except User.DoesNotExist:
return None
from django.http import JsonResponse
def token_required(func):
"""login_requred analog for API"""
def wrap(request, *args, **kwargs):
error401 = JsonResponse({'error': 'Authentication error'}, status=401)
if 'HTTP_AUTHORIZATION' in request.META:
if request.user is None or not request.user.is_active:
return error401
else:
return func(request, *args, **kwargs)
else:
return error401
return wrap
from django.contrib.auth import authenticate
def get_token(request):
"""Get token from HTTP header"""
if 'HTTP_AUTHORIZATION' in request.META:
full_auth = request.META['HTTP_AUTHORIZATION'].split(' ')
if len(full_auth) < 2 or full_auth[0] != 'Token':
return None
auth = full_auth[1].split('=')
if len(auth) < 2 or auth[0] != 'token':
return None
token = auth[1].strip('"')
return token
return None
class AuthAPI(object):
"""
Add user to request var for API calls
Header format (RFC2617):
Authorization: Token token="abcd1234"
"""
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
if request.get_full_path()[:4] != '/api':
return self.get_response(request)
token = get_token(request)
if token:
user = authenticate(token=token)
if user and user.is_active:
user.backend = 'core.backends.TokenBackend'
request.user = user
return self.get_response(request)
MIDDLEWARE += ['core.middleware.AuthAPI']
AUTHENTICATION_BACKENDS = [
'django.contrib.auth.backends.ModelBackend',
'core.backends.TokenBackend',
]
@devops724-2
Copy link

there are some missing files
from apps.users.models import User, Token
where is Token model?

@tetafro
Copy link
Author

tetafro commented Nov 18, 2020

@devops724-2 most probably I forgot to add it. You can find full example in this small project.
It was quite a long time ago, so I won't add it to this example, since I don't remember which fields are important, and which are not.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment