feat: adding user login schema response

This commit is contained in:
akhdanre 2025-05-15 23:45:41 +07:00
parent 596f498674
commit aae53cccce
5 changed files with 42 additions and 39 deletions

View File

@ -1,13 +1,12 @@
from flask import jsonify, request, current_app from flask import jsonify, request, current_app
from pydantic import ValidationError from pydantic import ValidationError
from app.models.login.login_response import UserResponseModel
from app.schemas.basic_response_schema import ResponseSchema from app.schemas.basic_response_schema import ResponseSchema
from app.schemas.google_login_schema import GoogleLoginSchema from app.schemas.google_login_schema import GoogleLoginSchema
from app.schemas import LoginSchema from app.schemas import LoginSchema
from app.services import UserService, AuthService from app.services import UserService, AuthService
from app.exception import AuthException from app.exception import AuthException
from app.mapper import UserMapper from app.mapper import UserMapper
from app.helpers import make_response from app.helpers import make_response, make_error_response
import logging import logging
logging = logging.getLogger(__name__) logging = logging.getLogger(__name__)
@ -26,15 +25,7 @@ class AuthController:
if response is None: if response is None:
return make_response(message="User is not registered", status_code=401) return make_response(message="User is not registered", status_code=401)
return ( return make_response(message="Login success", data=response)
jsonify(
ResponseSchema(
message="Register success",
data=UserMapper.user_entity_to_response(response),
).model_dump()
),
200,
)
except ValidationError as e: except ValidationError as e:
current_app.logger.error(f"Validation error: {e}") current_app.logger.error(f"Validation error: {e}")
response = ResponseSchema(message="Invalid input", data=None, meta=None) response = ResponseSchema(message="Invalid input", data=None, meta=None)
@ -54,25 +45,14 @@ class AuthController:
try: try:
data = request.get_json() data = request.get_json()
# Validasi data dengan Pydantic
validated_data = GoogleLoginSchema(**data) validated_data = GoogleLoginSchema(**data)
id_token = validated_data.token_id id_token = validated_data.token_id
# Verifikasi ID Token ke layanan AuthService
user_info = self.auth_service.verify_google_id_token(id_token) user_info = self.auth_service.verify_google_id_token(id_token)
if not user_info: if not user_info:
current_app.logger.error("Invalid Google ID Token") return make_response(message="Invalid Google ID Token", data=user_info)
response = ResponseSchema(
message="Invalid Google ID Token", data=None, meta=None
)
return jsonify(response.model_dump()), 401
response = ResponseSchema( return make_response(message="Login Success", data=user_info)
message="Login successful",
data=UserMapper.user_entity_to_response(user_info),
meta=None,
)
return jsonify(response.model_dump()), 200
except ValidationError as e: except ValidationError as e:
current_app.logger.error(f"Validation error: {e}") current_app.logger.error(f"Validation error: {e}")

View File

@ -1,7 +1,9 @@
from datetime import datetime from datetime import datetime
from typing import Dict, Optional from typing import Dict, Optional
from app.models import UserEntity, UserResponseModel from app.models import UserEntity
from app.schemas import RegisterSchema from app.schemas import RegisterSchema
from app.schemas.response import LoginResponseSchema
from app.helpers import DatetimeUtil
class UserMapper: class UserMapper:
@ -41,17 +43,15 @@ class UserMapper:
) )
@staticmethod @staticmethod
def user_entity_to_response(user: UserEntity) -> UserResponseModel: def user_entity_to_response(user: UserEntity) -> LoginResponseSchema:
print(str(user.id)) return LoginResponseSchema(
return UserResponseModel( id=str(user.id) if user.id else None,
_id=str(user.id) if user.id else None,
google_id=user.google_id,
email=user.email, email=user.email,
name=user.name, name=user.name,
birth_date=user.birth_date, birth_date=(
DatetimeUtil.to_string(user.birth_date) if user.birth_date else None
),
pic_url=user.pic_url, pic_url=user.pic_url,
phone=user.phone, phone=user.phone,
locale=user.locale, locale=user.locale,
# created_at=user.created_at,
# updated_at=user.updated_at,
) )

View File

@ -6,6 +6,7 @@ from .history.history_response import HistoryResultSchema
from .history.detail_history_response import QuizHistoryResponse, QuestionResult from .history.detail_history_response import QuizHistoryResponse, QuestionResult
from .recomendation.recomendation_response_schema import ListingQuizResponse from .recomendation.recomendation_response_schema import ListingQuizResponse
from .subject.get_subject_schema import GetSubjectResponse from .subject.get_subject_schema import GetSubjectResponse
from .auth.login_response import LoginResponseSchema
__all__ = [ __all__ = [
"QuizCreationResponse", "QuizCreationResponse",
@ -17,4 +18,5 @@ __all__ = [
"QuestionResult", "QuestionResult",
"ListingQuizResponse", "ListingQuizResponse",
"GetSubjectResponse", "GetSubjectResponse",
"LoginResponseSchema",
] ]

View File

@ -0,0 +1,14 @@
from pydantic import BaseModel, EmailStr, field_serializer
from app.models import UserEntity
from typing import Optional
from datetime import datetime
class LoginResponseSchema(BaseModel):
id: str
email: EmailStr
name: str
birth_date: Optional[str] = None
pic_url: Optional[str] = None
phone: Optional[str] = None
locale: Optional[str] = None

View File

@ -1,4 +1,5 @@
from app.schemas import LoginSchema from app.schemas import LoginSchema
from app.schemas.response import LoginResponseSchema
from app.repositories import UserRepository from app.repositories import UserRepository
from app.mapper import UserMapper from app.mapper import UserMapper
from google.oauth2 import id_token from google.oauth2 import id_token
@ -6,6 +7,8 @@ from google.auth.transport import requests
from app.configs import Config from app.configs import Config
from app.exception import AuthException from app.exception import AuthException
from werkzeug.security import check_password_hash from werkzeug.security import check_password_hash
from app.helpers import DatetimeUtil
from app.mapper import UserMapper
class AuthService: class AuthService:
@ -23,14 +26,17 @@ class AuthService:
existing_user = self.user_repository.get_by_google_id(google_id) existing_user = self.user_repository.get_by_google_id(google_id)
if existing_user: if existing_user:
if existing_user.email == email: if existing_user.email == email:
return existing_user
return UserMapper.user_entity_to_response(existing_user)
raise AuthException("Email not match") raise AuthException("Email not match")
new_user = UserMapper.from_google_payload(google_id, email, payload) new_user = UserMapper.from_google_payload(google_id, email, payload)
user_id = self.user_repository.insert_user(user_data=new_user) user_id = self.user_repository.insert_user(user_data=new_user)
return self.user_repository.get_user_by_id(user_id=user_id) user_data = self.user_repository.get_user_by_id(user_id=user_id)
return UserMapper.user_entity_to_response(user_data)
def login(self, data: LoginSchema): def login(self, data: LoginSchema):
user_data = self.user_repository.get_user_by_email(data.email) user_data = self.user_repository.get_user_by_email(data.email)
@ -38,7 +44,8 @@ class AuthService:
if user_data is None: if user_data is None:
return None return None
if check_password_hash(user_data.password, data.password): if not check_password_hash(user_data.password, data.password):
user_data.password = None
return user_data
return None return None
user_data.password = None
return UserMapper.user_entity_to_response(user_data)