How can I use SessionAuthentication to create a login API with the Django Rest Framework?

I want to make a rest api to be able to log into my Django app (from an Android app) using a request like

curl -X POST -d "username=myusername&password=mypassword" http://localhost:12345/rest/api-auth/login/ 

which should return a session identifier that I can use in future requests. It seems that I should use the SessionAuthentication authentication scheme, but there is no doc about it.

I know this question , but I would not want to use another application.

Any suggestion / pointer?

+8
django django-rest-framework
source share
2 answers

The resource /api-auth/login/ intended only for authentication in the browseble api. To use session authentication, you must first create a session. You must have a login resource that accepts user credentials and authenticates the user using the Django authentication system. When this resource is requested, the client will be the header of the cookie. Amd cookie should be used in subsequent requests.

 curl -v -X POST https://example.com/api/user/login/ -d 'username=user&password=pass' ... > Set-Cookie: csrftoken=TqIuhp8oEP9VY32tUDcfQyUwn3cqpYCa; expires=Fri, 15-May-2015 12:48:57 GMT; Max-Age=31449600; Path=/ > Set-Cookie: sessionid=4yb4s456lbvd974oijbdha7k3l6g52q3; expires=Fri, 30-May-2014 12:48:57 GMT; Max-Age=1209600; Path=/ 

DRF also supports basic authentication. You can use it to authenticate the user and create a session. Here is an example:

 from django.contrib.auth import login from rest_framework.authentication import BasicAuthentication, SessionAuthentication from rest_framework.permissions import IsAuthenticated from rest_framework.response import Response from rest_framework.views import APIView class MyBasicAuthentication(BasicAuthentication): def authenticate(self, request): user, _ = super(MyBasicAuthentication, self).authenticate(request) login(request, user) return user, _ class ExampleView(APIView): authentication_classes = (SessionAuthentication, MyBasicAuthentication) permission_classes = (IsAuthenticated,) def get(self, request, format=None): content = { 'user': unicode(request.user), 'auth': unicode(request.auth), # None } return Response(content) 
+3
source share

If the goal is to access some endpoint by passing the username and password in the POST data, you can do the following:

urls.py

 urlpatterns = [ url(r'^stuff/', views.MyView.as_view()), ... ] 

views.py

  from django.contrib.auth.models import User from rest_framework import viewsets from rest_framework.response import Response from rest_framework.views import APIView from rest_framework.permissions import IsAuthenticated from rest_framework import exceptions from rest_framework import authentication from django.contrib.auth import authenticate, get_user_model from rest_framework.authentication import BasicAuthentication, SessionAuthentication class ExampleAuthentication(authentication.BaseAuthentication): def authenticate(self, request): # Get the username and password username = request.data.get('username', None) password = request.data.get('password', None) if not username or not password: raise exceptions.AuthenticationFailed(_('No credentials provided.')) credentials = { get_user_model().USERNAME_FIELD: username, 'password': password } user = authenticate(**credentials) if user is None: raise exceptions.AuthenticationFailed(_('Invalid username/password.')) if not user.is_active: raise exceptions.AuthenticationFailed(_('User inactive or deleted.')) return (user, None) # authentication successful class MyView(APIView): authentication_classes = (SessionAuthentication, ExampleAuthentication,) permission_classes = (IsAuthenticated,) def post(self, request, format=None): content = { 'user': unicode(request.user), 'auth': unicode(request.auth), # None } return Response(content) 

Curl

 curl -v -X POST http://localhost:8000/stuff/ -d 'username=my_username&password=my_password' 
0
source share

All Articles