|
5 | 5 | import uuid |
6 | 6 | import logging |
7 | 7 | import json |
| 8 | +import requests |
8 | 9 | from django.db.models import Q |
9 | 10 | from django.core.cache import cache |
10 | 11 | from django.http import Http404, HttpResponse |
|
20 | 21 | from rest_framework.response import Response |
21 | 22 | from rest_framework.viewsets import GenericViewSet |
22 | 23 |
|
23 | | -from api import monitor, models, permissions, serializers, viewsets, authentication |
| 24 | +from api import monitor, models, permissions, serializers, viewsets, authentication, oauth |
24 | 25 | from api.tasks import scale_app, restart_app, mount_app, downstream_model_owner |
25 | 26 | from api.exceptions import AlreadyExists, ServiceUnavailable, DryccException |
26 | 27 |
|
@@ -85,22 +86,51 @@ def complete(request, backend, *args, **kwargs): |
85 | 86 | class AuthLoginView(GenericViewSet): |
86 | 87 |
|
87 | 88 | permission_classes = (AllowAny, ) |
| 89 | + serializer_class = serializers.AuthSerializer |
88 | 90 |
|
89 | 91 | def login(self, request, *args, **kwargs): |
90 | | - def get_local_host(request): |
91 | | - uri = request.build_absolute_uri() |
92 | | - return uri[0:uri.find(request.path)] |
93 | | - res = redirect(get_local_host(request) + "/v2/login/drycc/?key=" + uuid.uuid4().hex) |
94 | | - return res |
| 92 | + key = uuid.uuid4().hex |
| 93 | + serializer = self.get_serializer(data=request.data) |
| 94 | + serializer.is_valid(raise_exception=True) |
| 95 | + username = serializer.validated_data.get('username') |
| 96 | + password = serializer.validated_data.get('password') |
| 97 | + if username and password: |
| 98 | + return self._create_interactive_response(username, password, key) |
| 99 | + return self._create_browser_response(key) |
| 100 | + |
| 101 | + def _create_browser_response(self, key): |
| 102 | + uri = self.request.build_absolute_uri() |
| 103 | + return redirect(f"{uri[0:uri.find(self.request.path)]}/v2/login/drycc/?key={key}") |
| 104 | + |
| 105 | + def _create_interactive_response(self, username, password, key): |
| 106 | + response = requests.post( |
| 107 | + settings.SOCIAL_AUTH_DRYCC_ACCESS_TOKEN_URL, |
| 108 | + data={ |
| 109 | + 'grant_type': 'password', |
| 110 | + 'client_id': settings.SOCIAL_AUTH_DRYCC_KEY, |
| 111 | + 'client_secret': settings.SOCIAL_AUTH_DRYCC_SECRET, |
| 112 | + 'username': username, |
| 113 | + 'password': password, |
| 114 | + }, |
| 115 | + ) |
| 116 | + if response.status_code != 200: |
| 117 | + raise DryccException(response.content) |
| 118 | + state = uuid.uuid4().hex |
| 119 | + token = response.json()["access_token"] |
| 120 | + authentication.DryccAuthentication.sync_user(token) |
| 121 | + manager = oauth.TokenManager() |
| 122 | + manager.set_state(key, state) |
| 123 | + manager.set_token(state, token, username) |
| 124 | + return HttpResponse(json.dumps({"key": key})) |
95 | 125 |
|
96 | 126 |
|
97 | 127 | class AuthTokenView(GenericViewSet): |
98 | 128 |
|
99 | 129 | permission_classes = (AllowAny, ) |
100 | 130 |
|
101 | 131 | def token(self, request, *args, **kwargs): |
102 | | - state = cache.get("oidc_key_" + self.kwargs['key'], "") |
103 | | - token = cache.get("oidc_state_" + state, {}) |
| 132 | + manager = oauth.TokenManager() |
| 133 | + token = manager.get_token(self.kwargs['key']) |
104 | 134 | if not token.get('token'): |
105 | 135 | return HttpResponse(status=404) |
106 | 136 | return HttpResponse(json.dumps(token)) |
|
0 commit comments