se genera jwt de usuario

develop/Rodrigo/Backend
Francisco Sandoval 2023-06-25 22:41:07 -04:00
parent 72071fd7b7
commit de4e1c88e6
8 changed files with 142 additions and 4 deletions

View File

@ -14,6 +14,7 @@ services:
- DBSCHEMA=desarrollo2
- DBUSER=postgres
- DBPASS=password
- SECRET_JWT="kf6Jc!f30Z!1k1N0#!%#"
ports:
- 4000:4000
volumes:

View File

@ -0,0 +1,9 @@
from rest_framework.exceptions import APIException
class NotAuthorized(APIException):
status_code = 401
default_detail = 'Acceso negado'
class JWTExpired(APIException):
status_code = 400
default_detail = 'Token ya no es valido'

View File

@ -0,0 +1,42 @@
from django.http import HttpResponse
from .models import Usuario, Persona
import jwt
from decouple import config
private_key = config('SECRET_JWT')
class ApiMiddleware:
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
if not request.headers.get('Authorization') and request.path == '/api/auth/' and request.method == 'POST':
# cuando se quiere obtener el token, se omite esta regla
response = self.get_response(request)
return response
authorization = request.headers.get('Authorization').split(' ')
token = authorization[1]
try:
decoded = jwt.decode(token, private_key, algorithms=["HS256"])
except jwt.ExpiredSignatureError:
return HttpResponse('token ya no es valido', status = 400)
except jwt.InvalidTokenError:
return HttpResponse('token es invalido', status = 400)
usuario = Usuario.objects.filter(login = decoded['login'], vigente = True).values().first()
if not usuario:
return HttpResponse('Usuario ya no vigente', status = 400)
persona = Persona.objects.filter(rut = usuario['rut_id']).values().first()
if not persona:
return HttpResponse('No existe información de la persona', status = 500)
request.jwt_info = {
'login': usuario['login'],
'persona': persona
}
response = self.get_response(request)
return response

View File

@ -1,7 +1,23 @@
from rest_framework import serializers
from .models import Aplicacion
from .models import Usuario, Persona
class AplicacionSerializer(serializers.ModelSerializer):
class Meta:
model = Aplicacion
fields = '__all__'
class PersonaSerializer(serializers.ModelSerializer):
class Meta:
model = Persona
fields = '__all__'
class UsuarioSerializer(serializers.ModelSerializer):
# persona = serializers.PrimaryKeyRelatedField(queryset=Persona.objects.all(), source='rut')
class Meta:
model = Usuario
fields = ('login','vigente','rut')
# def get_persona(self, usuario):
# return usuario.persona

View File

@ -4,7 +4,10 @@ from api import views
router = routers.DefaultRouter()
router.register(r'aplicaciones', views.AplicacionViewSet)
router.register(r'usuarios', views.UsuarioViewSet)
router.register(r'personas', views.PersonaViewSet)
urlpatterns = [
path('', include(router.urls)),
path(r'auth/', views.jwt_login, name='auth'),
]

View File

@ -1,8 +1,56 @@
from rest_framework import viewsets
from rest_framework.decorators import action
from django.views.decorators.csrf import csrf_exempt
from django.http import HttpResponse
from django.http import JsonResponse
from .models import Usuario, Persona
from .models import Aplicacion
from .serializers import UsuarioSerializer, PersonaSerializer
from .serializers import AplicacionSerializer
import json
import jwt
import datetime
from decouple import config
private_key = config('SECRET_JWT')
# Create your views here.
class AplicacionViewSet(viewsets.ModelViewSet):
queryset = Aplicacion.objects.all()
serializer_class = AplicacionSerializer
class PersonaViewSet(viewsets.ModelViewSet):
queryset = Persona.objects.all()
serializer_class = PersonaSerializer
class UsuarioViewSet(viewsets.ModelViewSet):
queryset = Usuario.objects.all()
serializer_class = UsuarioSerializer
# Views jwt
@csrf_exempt
@action(detail=False, methods=['post','get'])
def jwt_login(request):
if request.method == 'POST':
# validar username y password
json_data = json.loads(request.body)
username = json_data['username']
password = json_data['password']
usuario = Usuario.objects.filter(login = username, vigente = True).values().first()
if not usuario:
return HttpResponse('Acceso no valido', status = 400)
if usuario['clave'] != password:
return HttpResponse('Acceso no valido', status = 400)
now = datetime.datetime.utcnow()
payload = {
'exp': now + datetime.timedelta(minutes=60),
'login': usuario['login']
}
token = jwt.encode(payload, private_key, algorithm="HS256")
return JsonResponse({ 'token': token })
elif request.method == 'GET':
return JsonResponse(request.jwt_info)

View File

@ -52,6 +52,8 @@ MIDDLEWARE = [
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
'corsheaders.middleware.CorsMiddleware',
'api.middlewares.ApiMiddleware',
]
ROOT_URLCONF = 'project.urls'
@ -135,7 +137,7 @@ STATIC_URL = 'static/'
DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
REST_FRAMEWORK = { 'DEFAULT_SCHEMA_CLASS': 'rest_framework.schemas.coreapi.AutoSchema' }
CORS_ALLOW_CREDENTIALS = True
CORS_ALLOWED_ORIGINS = [
CORS_ORIGIN_ALLOW_ALL = False
CORS_ORIGIN_WHITELIST = [
"http://localhost:3000",
]

17
rest/login.rest 100644
View File

@ -0,0 +1,17 @@
@server = http://localhost:4000/api
@token = {{login.response.body.$.token}}
###
# @name login
POST {{server}}/auth/
Content-Type: application/json
{
"username": "usuario1",
"password": "usuario1"
}
###
GET {{server}}/auth/
Authorization: Bearer {{token}}