nonce_length = 8, 250
# Because piston.models.Token.key is char(18).
+ request_token_length = 18, 32
access_token_length = 18, 32
+ # TODO: oauthlib request-access switch.
def check_client_key(self, client_key):
"""We control the keys anyway."""
return True
+ def get_request_token_secret(self, client_key, token, request):
+ return request.token.secret
+
def get_access_token_secret(self, client_key, token, request):
return request.token.secret
def get_default_realms(self, client_key, request):
return ['API']
+ def validate_request_token(self, client_key, token, request):
+ try:
+ token = Token.objects.get(
+ token_type=Token.REQUEST,
+ consumer__key=client_key,
+ key=token,
+ is_approved=True,
+ )
+ except Token.DoesNotExist:
+ return False
+ else:
+ request.token = token
+ return True
+
def validate_access_token(self, client_key, token, request):
try:
token = Token.objects.get(
def validate_redirect_uri(self, *args, **kwargs):
return True
+ def validate_verifier(self, client_key, token, verifier, request):
+ return True
+
def get_client_secret(self, client_key, request):
return request.oauth_consumer.secret
consumer=request.oauth_consumer,
)
+ def save_access_token(self, token, request):
+ Token.objects.create(
+ token_type=Token.ACCESS,
+ timestamp=request.timestamp,
+ key=token['oauth_token'],
+ secret=token['oauth_token_secret'],
+ consumer=request.oauth_consumer,
+ user=request.token.user,
+ )
+
def verify_request_token(self, token, request):
return Token.objects.filter(
token_type=Token.REQUEST, key=token, is_approved=False
def get_redirect_uri(self, token, request):
return request.redirect_uri
+
+ def invalidate_request_token(self, client_key, request_token, request):
+ Token.objects.filter(
+ token_type=Token.REQUEST,
+ key=request_token,
+ consumer__key=client_key,
+ )
with open(filename) as f:
good_content = f.read().rstrip()
self.assertEqual(content, good_content, content)
-
+
def assert_json_response(self, url, name):
data = self.load_json(url)
filename = path.join(path.dirname(__file__), 'res', 'responses', name)
from django.conf.urls import url, include
from django.views.decorators.csrf import csrf_exempt
from django.views.generic import TemplateView
-from piston.authentication import oauth_access_token
import catalogue.views
from api import handlers
from api.piston_patch import oauth_user_auth
urlpatterns = [
url(r'^oauth/request_token/$', views.OAuth1RequestTokenView.as_view()),
url(r'^oauth/authorize/$', oauth_user_auth, name='oauth_user_auth'),
- url(r'^oauth/access_token/$', csrf_exempt(oauth_access_token)),
+ url(r'^oauth/access_token/$', csrf_exempt(views.OAuth1AccessTokenView.as_view())),
url(r'^$', TemplateView.as_view(template_name='api/main.html'), name='api'),
# Copyright © Fundacja Nowoczesna Polska. See NOTICE for more information.
#
from django.http import Http404
+from django.views.generic.base import View
from oauthlib.common import urlencode
-from oauthlib.oauth1 import RequestTokenEndpoint
+from oauthlib.oauth1 import RequestTokenEndpoint, AccessTokenEndpoint
from piston.models import KEY_SIZE, SECRET_SIZE
from rest_framework.permissions import IsAuthenticated
from rest_framework.response import Response
return urlencode(token.items())
-class OAuth1RequestTokenView(APIView):
+class OAuth1RequestTokenView(View):
def __init__(self):
self.endpoint = OAuth1RequestTokenEndpoint(PistonRequestValidator())
)
+class OAuth1AccessTokenEndpoint(AccessTokenEndpoint):
+ def _create_request(self, *args, **kwargs):
+ r = super(OAuth1AccessTokenEndpoint, self)._create_request(*args, **kwargs)
+ r.verifier = 'x' * 20
+ return r
+
+ def create_access_token(self, request, credentials):
+ request.realms = self.request_validator.get_realms(
+ request.resource_owner_key, request)
+ token = {
+ 'oauth_token': self.token_generator()[:KEY_SIZE],
+ 'oauth_token_secret': self.token_generator()[:SECRET_SIZE],
+ 'oauth_authorized_realms': ' '.join(request.realms)
+ }
+ token.update(credentials)
+ self.request_validator.save_access_token(token, request)
+ return urlencode(token.items())
+
+
+class OAuth1AccessTokenView(View):
+ def __init__(self):
+ self.endpoint = OAuth1AccessTokenEndpoint(PistonRequestValidator())
+
+ def dispatch(self, request):
+ return oauthlib_response(
+ self.endpoint.create_access_token_response(
+ **oauthlib_request(request)
+ )
+ )
+
+
class UserView(RetrieveAPIView):
permission_classes = [IsAuthenticated]
serializer_class = serializers.UserSerializer