Core: add jwt auth
This commit is contained in:
parent
1e0ffd9b2d
commit
495312b060
12 changed files with 234 additions and 17 deletions
|
@ -39,8 +39,10 @@ INSTALLED_APPS = [
|
||||||
'django.contrib.staticfiles',
|
'django.contrib.staticfiles',
|
||||||
|
|
||||||
'rest_framework',
|
'rest_framework',
|
||||||
|
'rest_framework_simplejwt',
|
||||||
|
|
||||||
'proxy',
|
'proxy',
|
||||||
|
'jwtauth',
|
||||||
]
|
]
|
||||||
|
|
||||||
MIDDLEWARE = [
|
MIDDLEWARE = [
|
||||||
|
@ -125,3 +127,60 @@ STATIC_URL = 'static/'
|
||||||
# https://docs.djangoproject.com/en/5.0/ref/settings/#default-auto-field
|
# https://docs.djangoproject.com/en/5.0/ref/settings/#default-auto-field
|
||||||
|
|
||||||
DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
|
DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
|
||||||
|
|
||||||
|
|
||||||
|
#JWT
|
||||||
|
|
||||||
|
REST_FRAMEWORK = {
|
||||||
|
'DEFAULT_AUTHENTICATION_CLASSES': (
|
||||||
|
'rest_framework_simplejwt.authentication.JWTAuthentication',
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
from datetime import timedelta
|
||||||
|
...
|
||||||
|
# Configure Simple JWT
|
||||||
|
SIMPLE_JWT = {
|
||||||
|
"AUTH_HEADER_TYPES": ("Bearer",),
|
||||||
|
}
|
||||||
|
'''
|
||||||
|
SIMPLE_JWT = {
|
||||||
|
"ACCESS_TOKEN_LIFETIME": timedelta(minutes=5),
|
||||||
|
"REFRESH_TOKEN_LIFETIME": timedelta(days=1),
|
||||||
|
"ROTATE_REFRESH_TOKENS": False,
|
||||||
|
"BLACKLIST_AFTER_ROTATION": False,
|
||||||
|
"UPDATE_LAST_LOGIN": False,
|
||||||
|
|
||||||
|
"ALGORITHM": "HS256",
|
||||||
|
#"SIGNING_KEY": settings.SECRET_KEY,
|
||||||
|
"VERIFYING_KEY": "",
|
||||||
|
"AUDIENCE": None,
|
||||||
|
"ISSUER": None,
|
||||||
|
"JSON_ENCODER": None,
|
||||||
|
"JWK_URL": None,
|
||||||
|
"LEEWAY": 0,
|
||||||
|
# This is nessecary!
|
||||||
|
"AUTH_HEADER_TYPES": ("Bearer",),
|
||||||
|
"AUTH_HEADER_NAME": "HTTP_AUTHORIZATION",
|
||||||
|
"USER_ID_FIELD": "id",
|
||||||
|
"USER_ID_CLAIM": "user_id",
|
||||||
|
"USER_AUTHENTICATION_RULE": "rest_framework_simplejwt.authentication.default_user_authentication_rule",
|
||||||
|
|
||||||
|
"AUTH_TOKEN_CLASSES": ("rest_framework_simplejwt.tokens.AccessToken",),
|
||||||
|
"TOKEN_TYPE_CLAIM": "token_type",
|
||||||
|
"TOKEN_USER_CLASS": "rest_framework_simplejwt.models.TokenUser",
|
||||||
|
|
||||||
|
"JTI_CLAIM": "jti",
|
||||||
|
|
||||||
|
"SLIDING_TOKEN_REFRESH_EXP_CLAIM": "refresh_exp",
|
||||||
|
"SLIDING_TOKEN_LIFETIME": timedelta(minutes=5),
|
||||||
|
"SLIDING_TOKEN_REFRESH_LIFETIME": timedelta(days=1),
|
||||||
|
|
||||||
|
"TOKEN_OBTAIN_SERIALIZER": "rest_framework_simplejwt.serializers.TokenObtainPairSerializer",
|
||||||
|
"TOKEN_REFRESH_SERIALIZER": "rest_framework_simplejwt.serializers.TokenRefreshSerializer",
|
||||||
|
"TOKEN_VERIFY_SERIALIZER": "rest_framework_simplejwt.serializers.TokenVerifySerializer",
|
||||||
|
"TOKEN_BLACKLIST_SERIALIZER": "rest_framework_simplejwt.serializers.TokenBlacklistSerializer",
|
||||||
|
"SLIDING_TOKEN_OBTAIN_SERIALIZER": "rest_framework_simplejwt.serializers.TokenObtainSlidingSerializer",
|
||||||
|
"SLIDING_TOKEN_REFRESH_SERIALIZER": "rest_framework_simplejwt.serializers.TokenRefreshSlidingSerializer",
|
||||||
|
}
|
||||||
|
'''
|
|
@ -17,7 +17,14 @@ Including another URLconf
|
||||||
from django.contrib import admin
|
from django.contrib import admin
|
||||||
from django.urls import path, include
|
from django.urls import path, include
|
||||||
|
|
||||||
|
from rest_framework_simplejwt.views import (
|
||||||
|
TokenObtainPairView,
|
||||||
|
TokenRefreshView,
|
||||||
|
TokenVerifyView,
|
||||||
|
)
|
||||||
|
|
||||||
urlpatterns = [
|
urlpatterns = [
|
||||||
path('admin/', admin.site.urls),
|
path('admin/', admin.site.urls),
|
||||||
path('proxy/wells/', include('proxy.urls')),
|
path('wells/', include('proxy.urls')),
|
||||||
|
path('token/', include('jwtauth.urls')),
|
||||||
]
|
]
|
||||||
|
|
0
jwtauth/__init__.py
Normal file
0
jwtauth/__init__.py
Normal file
3
jwtauth/admin.py
Normal file
3
jwtauth/admin.py
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
from django.contrib import admin
|
||||||
|
|
||||||
|
# Register your models here.
|
6
jwtauth/apps.py
Normal file
6
jwtauth/apps.py
Normal file
|
@ -0,0 +1,6 @@
|
||||||
|
from django.apps import AppConfig
|
||||||
|
|
||||||
|
|
||||||
|
class JwtauthConfig(AppConfig):
|
||||||
|
default_auto_field = 'django.db.models.BigAutoField'
|
||||||
|
name = 'jwtauth'
|
22
jwtauth/migrations/0001_initial.py
Normal file
22
jwtauth/migrations/0001_initial.py
Normal file
|
@ -0,0 +1,22 @@
|
||||||
|
# Generated by Django 5.0.7 on 2024-08-19 12:06
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
|
||||||
|
initial = True
|
||||||
|
|
||||||
|
dependencies = [
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.CreateModel(
|
||||||
|
name='OkService',
|
||||||
|
fields=[
|
||||||
|
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
|
||||||
|
('name', models.CharField(max_length=30)),
|
||||||
|
('province', models.CharField(max_length=30)),
|
||||||
|
],
|
||||||
|
),
|
||||||
|
]
|
0
jwtauth/migrations/__init__.py
Normal file
0
jwtauth/migrations/__init__.py
Normal file
7
jwtauth/models.py
Normal file
7
jwtauth/models.py
Normal file
|
@ -0,0 +1,7 @@
|
||||||
|
from django.db import models
|
||||||
|
|
||||||
|
# Create your models here.
|
||||||
|
|
||||||
|
class OkService(models.Model):
|
||||||
|
name = models.CharField(max_length=30)
|
||||||
|
province = models.CharField(max_length=30)
|
3
jwtauth/tests.py
Normal file
3
jwtauth/tests.py
Normal file
|
@ -0,0 +1,3 @@
|
||||||
|
from django.test import TestCase
|
||||||
|
|
||||||
|
# Create your tests here.
|
20
jwtauth/urls.py
Normal file
20
jwtauth/urls.py
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
from django.urls import path
|
||||||
|
|
||||||
|
from rest_framework_simplejwt.views import (
|
||||||
|
TokenObtainPairView,
|
||||||
|
TokenRefreshView,
|
||||||
|
TokenVerifyView,
|
||||||
|
)
|
||||||
|
|
||||||
|
from .views import *
|
||||||
|
|
||||||
|
urlpatterns = [
|
||||||
|
#to do: costumize this!
|
||||||
|
path('register/', register_service, name='register_service'),
|
||||||
|
#post username and password, get access and refresh token
|
||||||
|
path('', TokenObtainPairView.as_view(), name='token_obtain_pair'),
|
||||||
|
#post refresh token to this url to get a new access token
|
||||||
|
path('refresh/', TokenRefreshView.as_view(), name='token_refresh'),
|
||||||
|
#validates the access token
|
||||||
|
path('verify/', TokenVerifyView.as_view(), name='token_verify'),
|
||||||
|
]
|
43
jwtauth/views.py
Normal file
43
jwtauth/views.py
Normal file
|
@ -0,0 +1,43 @@
|
||||||
|
from django.shortcuts import render
|
||||||
|
|
||||||
|
from rest_framework.decorators import api_view
|
||||||
|
from rest_framework_simplejwt.tokens import RefreshToken
|
||||||
|
from rest_framework_simplejwt.exceptions import InvalidToken
|
||||||
|
from rest_framework_simplejwt.tokens import UntypedToken
|
||||||
|
import json
|
||||||
|
|
||||||
|
from .models import OkService
|
||||||
|
|
||||||
|
|
||||||
|
@api_view(['POST'])
|
||||||
|
def register_service(request):
|
||||||
|
try:
|
||||||
|
data = dict(json.loads(request.body.decode('utf-8')))
|
||||||
|
print(data, type(data))
|
||||||
|
if "shared_key" in dict(data).keys:
|
||||||
|
if first_step_check():
|
||||||
|
...
|
||||||
|
|
||||||
|
services = OkService.objects.all()
|
||||||
|
except Exception as ex:
|
||||||
|
print(ex)
|
||||||
|
|
||||||
|
def first_step_check(shared_key):
|
||||||
|
service_id = 1
|
||||||
|
return service_id
|
||||||
|
|
||||||
|
|
||||||
|
def generate_tokens(service_id):
|
||||||
|
refresh = RefreshToken.for_user(service_id)
|
||||||
|
return {
|
||||||
|
'refresh': str(refresh),
|
||||||
|
'access': str(refresh.access_token),
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
def validate_token(token):
|
||||||
|
try:
|
||||||
|
UntypedToken(token)
|
||||||
|
return True
|
||||||
|
except InvalidToken:
|
||||||
|
return False
|
|
@ -7,7 +7,9 @@ from django.core import serializers
|
||||||
|
|
||||||
from rest_framework.response import Response
|
from rest_framework.response import Response
|
||||||
from rest_framework import status
|
from rest_framework import status
|
||||||
from rest_framework.decorators import api_view
|
from rest_framework.decorators import api_view, permission_classes
|
||||||
|
from rest_framework.permissions import IsAuthenticated
|
||||||
|
|
||||||
import json
|
import json
|
||||||
import requests
|
import requests
|
||||||
|
|
||||||
|
@ -15,12 +17,46 @@ from .models import Well
|
||||||
from .serializers import WellSerializer
|
from .serializers import WellSerializer
|
||||||
|
|
||||||
|
|
||||||
|
#To optain the jwt Token for the first time from other services
|
||||||
|
'''
|
||||||
|
import requests
|
||||||
|
url = 'http://<well_service_url>/token/'
|
||||||
|
|
||||||
|
credentials = {
|
||||||
|
"username": "your_username",
|
||||||
|
"password": "your_password"
|
||||||
|
}
|
||||||
|
|
||||||
|
response = requests.post(url, data=credentials)
|
||||||
|
token = response.json().get('access')
|
||||||
|
'''
|
||||||
|
# Store this token to use in future requests
|
||||||
|
'''
|
||||||
|
headers = {
|
||||||
|
'Authorization': f'Bearer {token}',
|
||||||
|
}
|
||||||
|
response = requests.post('http://<well_service_url>/<...>/', headers=headers, json=data_to_send)
|
||||||
|
'''
|
||||||
|
|
||||||
|
#error_list
|
||||||
|
'''
|
||||||
|
{
|
||||||
|
"200_created": ({"data": "<serializer.data>", "message": "<costume message>"}, status=status.HTTP_200_OK),
|
||||||
|
"200_updated": ({"data": "<serializer.data>", "message": f"<Successfully updated {instance.license_code}>"}, status=status.HTTP_200_OK),
|
||||||
|
"400":({"message": serializer.errors}, status=status.HTTP_400_BAD_REQUEST),
|
||||||
|
"404": ({"message": "<Not Found>"}, status=status.HTTP_404_NOT_FOUND),
|
||||||
|
"409": ({"message":f'<{data["license_code"]} already exists>'}, status=status.HTTP_409_CONFLICT),
|
||||||
|
"500": ({"message": "<Internal Server Error>"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR),
|
||||||
|
}
|
||||||
|
'''
|
||||||
|
|
||||||
@api_view(['POST'])
|
@api_view(['POST'])
|
||||||
|
@permission_classes([IsAuthenticated])
|
||||||
def create_well(request):
|
def create_well(request):
|
||||||
try:
|
try:
|
||||||
data = json.loads(request.body.decode('utf-8'))
|
data = json.loads(request.body.decode('utf-8'))
|
||||||
instance = Well.objects.get(
|
instance = Well.objects.filter(
|
||||||
license_code=data["license_code"])
|
license_code=data["license_code"], log_type = 0)
|
||||||
if instance:
|
if instance:
|
||||||
return Response(
|
return Response(
|
||||||
{"message":f'{data["license_code"]} already exists'},
|
{"message":f'{data["license_code"]} already exists'},
|
||||||
|
@ -29,33 +65,38 @@ def create_well(request):
|
||||||
serializer = WellSerializer(data=data)
|
serializer = WellSerializer(data=data)
|
||||||
if serializer.is_valid():
|
if serializer.is_valid():
|
||||||
serializer.save()
|
serializer.save()
|
||||||
|
dd
|
||||||
return Response(
|
return Response(
|
||||||
serializer.data,
|
{"data":serializer.data},
|
||||||
status=status.HTTP_201_CREATED
|
status=status.HTTP_201_CREATED
|
||||||
)
|
)
|
||||||
else:
|
else:
|
||||||
return Response(
|
return Response(
|
||||||
serializer.errors,
|
{"message":serializer.errors},
|
||||||
status=status.HTTP_400_BAD_REQUEST
|
status=status.HTTP_400_BAD_REQUEST
|
||||||
)
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(e)
|
print(e)
|
||||||
return Response({"error": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
return Response({"message": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
||||||
|
|
||||||
@api_view(['GET'])
|
@api_view(['GET'])
|
||||||
|
@permission_classes([IsAuthenticated])
|
||||||
def send_well_by_well_id(request, obj_id):
|
def send_well_by_well_id(request, obj_id):
|
||||||
try:
|
try:
|
||||||
well = Well.objects.filter(id=obj_id).first()
|
well = Well.objects.filter(id=obj_id).first()
|
||||||
if well is None:
|
if well is None:
|
||||||
return Response({"error": "Not Found"}, status=status.HTTP_404_NOT_FOUND)
|
return Response({"message": "Not Found"}, status=status.HTTP_404_NOT_FOUND)
|
||||||
serializer = WellSerializer(well)
|
serializer = WellSerializer(well)
|
||||||
return Response(serializer.data, status=status.HTTP_200_OK)
|
return Response({"data":serializer.data}, status=status.HTTP_200_OK)
|
||||||
except Exception as ex:
|
except Exception as ex:
|
||||||
print(ex)
|
print(ex)
|
||||||
return Response({"error": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
return Response({"message": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
||||||
|
|
||||||
|
|
||||||
@api_view(['GET'])
|
@api_view(['GET'])
|
||||||
|
@permission_classes([IsAuthenticated])
|
||||||
def send_wells(request):
|
def send_wells(request):
|
||||||
|
#permission_classes = [IsAuthenticated]
|
||||||
try:
|
try:
|
||||||
# to do: add owner
|
# to do: add owner
|
||||||
# to do: add filter
|
# to do: add filter
|
||||||
|
@ -63,24 +104,28 @@ def send_wells(request):
|
||||||
# to do: add no return data
|
# to do: add no return data
|
||||||
wells = Well.objects.all()
|
wells = Well.objects.all()
|
||||||
serializer = WellSerializer(wells, many=True)
|
serializer = WellSerializer(wells, many=True)
|
||||||
return Response(serializer.data, status=status.HTTP_200_OK)
|
return Response({"data":serializer.data}, status=status.HTTP_200_OK)
|
||||||
except Exception as ex:
|
except Exception as ex:
|
||||||
print(ex)
|
print(ex)
|
||||||
return Response({"error": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
return Response({"message": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
||||||
|
|
||||||
|
|
||||||
|
@permission_classes([IsAuthenticated])
|
||||||
@api_view(['DELETE'])
|
@api_view(['DELETE'])
|
||||||
def delete_well_by_well_id(request, obj_id):
|
def delete_well_by_well_id(request, obj_id):
|
||||||
try:
|
try:
|
||||||
instance = Well.objects.get(id=obj_id, log_type=0)
|
instance = Well.objects.get(id=obj_id, log_type=0)
|
||||||
instance.log_type = 1
|
instance.log_type = 1
|
||||||
instance.save()
|
instance.save()
|
||||||
return Response({"detail": f"Successfully updated log type for well {instance.license_code}"}, status=status.HTTP_200_OK)
|
return Response({"message": f"Successfully removed log type for well {instance.license_code}"}, status=status.HTTP_200_OK)
|
||||||
except Well.DoesNotExist:
|
except Well.DoesNotExist:
|
||||||
return Response({"error": "Not Found"}, status=status.HTTP_404_NOT_FOUND)
|
return Response({"message": "Not Found"}, status=status.HTTP_404_NOT_FOUND)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(e)
|
print(e)
|
||||||
return Response({"error": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
return Response({"message": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
||||||
|
|
||||||
|
|
||||||
|
@permission_classes([IsAuthenticated])
|
||||||
@api_view(['PUT'])
|
@api_view(['PUT'])
|
||||||
def update_well_by_well_id(request, obj_id):
|
def update_well_by_well_id(request, obj_id):
|
||||||
try:
|
try:
|
||||||
|
@ -94,13 +139,15 @@ def update_well_by_well_id(request, obj_id):
|
||||||
serializer.save()
|
serializer.save()
|
||||||
return Response(serializer.data, status=status.HTTP_200_OK)
|
return Response(serializer.data, status=status.HTTP_200_OK)
|
||||||
else:
|
else:
|
||||||
return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
|
return Response({"message":serializer.errors}, status=status.HTTP_400_BAD_REQUEST)
|
||||||
except Well.DoesNotExist:
|
except Well.DoesNotExist:
|
||||||
return Response({"error": "Not Found"}, status=status.HTTP_404_NOT_FOUND)
|
return Response({"error": "Not Found"}, status=status.HTTP_404_NOT_FOUND)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(e)
|
print(e)
|
||||||
return Response({"error": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
return Response({"error": "Internal Server Error"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
|
||||||
|
|
||||||
|
|
||||||
|
@permission_classes([IsAuthenticated])
|
||||||
@api_view(['PUT'])
|
@api_view(['PUT'])
|
||||||
def edit_well_by_well_id(request, obj_id):
|
def edit_well_by_well_id(request, obj_id):
|
||||||
try:
|
try:
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue