Browse Source

fixed token refresh logic and sending username on login

Dimitri Korsch 3 years ago
parent
commit
0ea726c65f

+ 3 - 9
backend/pycs_api/urls.py

@@ -17,21 +17,15 @@ from django.urls import include
 from django.urls import path
 from pycs_api import views
 
-from rest_framework import routers
-from rest_framework_simplejwt.views import TokenObtainPairView
-from rest_framework_simplejwt.views import TokenRefreshView
-
-router = routers.DefaultRouter()
-router.register(r'models', views.ModelViewSet)
 
 urlpatterns = [
-    path('', include(router.urls)),
+    path('', include(views.router.urls)),
 
     path('api-token/',
-        TokenObtainPairView.as_view(), name="obtain-token"),
+        views.TokenObtainPairView.as_view(), name="obtain-token"),
 
     path('api-token-refresh/',
-        TokenRefreshView.as_view(), name="refresh-token"),
+        views.TokenRefreshView.as_view(), name="refresh-token"),
 
     path('projects/',
         views.ProjectView.as_view(), name="projects"),

+ 27 - 1
backend/pycs_api/views/__init__.py

@@ -3,8 +3,31 @@ from pycs_api.views.project import ProjectView
 from pycs_api import models
 from pycs_api import serializers
 
-from rest_framework import viewsets
 from rest_framework import permissions
+from rest_framework import routers
+from rest_framework import viewsets
+from rest_framework_simplejwt.serializers import TokenObtainPairSerializer
+from rest_framework_simplejwt.views import TokenObtainPairView as BaseTokenObtainView
+from rest_framework_simplejwt.views import TokenRefreshView as BaseTokenRefreshView
+
+class CustomTokenSerializer(TokenObtainPairSerializer):
+
+    def validate(self, attrs):
+        data = super().validate(attrs)
+
+        # Add custom data
+        data['username'] = self.user.username
+
+        return data
+
+class TokenObtainPairView(BaseTokenObtainView):
+    serializer_class = CustomTokenSerializer
+
+
+class TokenRefreshView(BaseTokenRefreshView):
+    # serializer_class = CustomTokenSerializer
+    pass
+
 
 class ModelViewSet(viewsets.ModelViewSet):
 
@@ -12,3 +35,6 @@ class ModelViewSet(viewsets.ModelViewSet):
     serializer_class = serializers.ModelSerializer
     permission_classes = [permissions.IsAuthenticated]
 
+
+router = routers.DefaultRouter()
+router.register(r'models', ModelViewSet)

+ 18 - 5
frontend/src/services/auth.service.js

@@ -2,22 +2,35 @@ import api from "./api";
 import TokenService from "./token.service";
 
 class AuthService {
-  login({ username, password }) {
+  login ({ username, password }) {
     return api
       .post("/api-token/", {username, password})
       .then((response) => {
-        if (response.data.access) {
-          TokenService.setTokens(username, response.data);
-        }
+        if (response.data.access)
+          TokenService.setTokens(response.data);
 
         return response.data;
       });
   }
 
-  logout() {
+  logout () {
     TokenService.removeTokens();
   }
 
+  refreshAccessToken () {
+
+    return api.
+      post("/api-token-refresh/", {
+        refresh: TokenService.getLocalRefreshToken(),
+      })
+      .then((response) => {
+        if (response.data.access)
+          TokenService.updateLocalAccessToken(response.data.access);
+
+        return response.data;
+      });
+  }
+
 }
 
 export default new AuthService();

+ 11 - 12
frontend/src/services/setupInterceptors.js

@@ -1,13 +1,14 @@
-import axiosInstance from "./api";
+import api from "./api";
 import TokenService from "./token.service";
+import AuthService from "./auth.service";
 
 const setup = (store) => {
-  axiosInstance.interceptors.request.use(
+  api.interceptors.request.use(
     (config) => {
       const token = TokenService.getLocalAccessToken();
-      if (token) {
+      if (token)
         config.headers["Authorization"] = `Bearer ${token}`
-      }
+
       return config;
     },
     (error) => {
@@ -16,7 +17,7 @@ const setup = (store) => {
     }
   );
 
-  axiosInstance.interceptors.response.use(
+  api.interceptors.response.use(
     (res) => {
       return res;
     },
@@ -31,16 +32,14 @@ const setup = (store) => {
           console.log("Access token expired!")
           originalConfig._retry = true;
           try {
-            const response = await axiosInstance.post("/api-token-refresh/", {
-              refresh: TokenService.getLocalRefreshToken(),
-            });
-
-            const { access } = response.data;
+            const { access } = await AuthService.refreshAccessToken();
+            console.log("New acces token: ", access)
 
             store.dispatch('auth/refreshToken', access);
-            TokenService.updateLocalAccessToken(access);
 
-            return axiosInstance(originalConfig);
+            console.log("Retrying original request")
+            return api(originalConfig);
+
           } catch (_error) {
             return Promise.reject(_error);
           }

+ 3 - 7
frontend/src/services/token.service.js

@@ -4,13 +4,9 @@ class TokenService {
     return JSON.parse(localStorage.getItem("tokens"));
   }
 
-  setTokens(username, tokens) {
-    let tokens_str = JSON.stringify(
-      Object.assign(
-        tokens, {username}
-      )
-    )
-    // console.log("Setting token info: ", tokens_str);
+  setTokens(tokens) {
+    let tokens_str = JSON.stringify(tokens)
+    console.log("Setting token info: ", tokens_str);
     localStorage.setItem("tokens", tokens_str);
   }