From fe91bb710387b55aa369f0cb7a667de7d1dc0a7a Mon Sep 17 00:00:00 2001 From: Vladislav Date: Wed, 21 May 2025 12:44:28 +0500 Subject: [PATCH 1/3] feat: add base class for all schemas and to camel case mapper --- api/api/db/logic/account.py | 2 ++ api/api/endpoints/auth.py | 18 +++--------------- api/api/schemas/account/account.py | 7 +++++-- api/api/schemas/account/account_keyring.py | 7 +++++-- api/api/schemas/base.py | 11 +++++++++++ api/api/schemas/endpoints/account.py | 7 +++++-- api/api/schemas/endpoints/account_keyring.py | 7 +++++-- api/api/schemas/endpoints/auth.py | 11 ++++++++--- api/api/schemas/events/list_events.py | 6 ++++-- api/api/schemas/process/node_link.py | 6 ++++-- api/api/schemas/process/process_schema.py | 6 ++++-- .../schemas/process/process_version_archive.py | 5 +++-- api/api/schemas/process/ps_node.py | 5 +++-- api/api/utils/mapper.py | 3 +++ 14 files changed, 65 insertions(+), 36 deletions(-) create mode 100644 api/api/schemas/base.py create mode 100644 api/api/utils/mapper.py diff --git a/api/api/db/logic/account.py b/api/api/db/logic/account.py index 489ff32..09b30d9 100644 --- a/api/api/db/logic/account.py +++ b/api/api/db/logic/account.py @@ -47,6 +47,7 @@ async def get_user_login(connection: AsyncConnection, login: str) -> Optional[Us if not user_db: return None + print("user_db", user_db) user_data = { column.name: ( @@ -56,6 +57,7 @@ async def get_user_login(connection: AsyncConnection, login: str) -> Optional[Us ) for column in account_table.columns } + print("user_data", user_data) return User.model_validate(user_data) diff --git a/api/api/endpoints/auth.py b/api/api/endpoints/auth.py index 0d635e9..11c606e 100644 --- a/api/api/endpoints/auth.py +++ b/api/api/endpoints/auth.py @@ -11,9 +11,7 @@ from fastapi import ( status, ) - from loguru import logger -from pydantic.main import BaseModel from fastapi_jwt_auth import AuthJWT from pydantic import BaseModel @@ -26,7 +24,7 @@ from api.services.auth import authenticate_user from api.db.logic.auth import add_new_refresh_token, upgrade_old_refresh_token -from api.schemas.endpoints.auth import Auth +from api.schemas.endpoints.auth import Auth, AccessToken api_router = APIRouter( prefix="/auth", @@ -87,12 +85,7 @@ async def login_for_access_token( Authorize.set_refresh_cookies(refresh_token) - return { - "access_token": access_token, - # "access_token_expires": access_token_expires_time, - # "refresh_token": refresh_token, - # "refresh_token_expires": refresh_token_expires_time - } + return AccessToken(access_token=access_token) @api_router.post("/refresh") @@ -121,9 +114,4 @@ async def refresh( new_access_token = Authorize.create_access_token(subject=current_user, expires_time=access_token_expires) - return { - "access_token": new_access_token, - # "access_token_expires": access_token_expires_time, - # "refresh_token": refresh_token, - # "refresh_token_expires": refresh_token_expires_time - } + return AccessToken(access_token=new_access_token) diff --git a/api/api/schemas/account/account.py b/api/api/schemas/account/account.py index 6cebdf4..91364fe 100644 --- a/api/api/schemas/account/account.py +++ b/api/api/schemas/account/account.py @@ -2,7 +2,10 @@ import datetime from enum import Enum from datetime import datetime from typing import Optional -from pydantic import BaseModel, EmailStr, Field +from pydantic import EmailStr, Field + +from api.schemas.base import Base + # Модель для хранения информации из запроса @@ -21,7 +24,7 @@ class Status(Enum): DELETED = "DELETED" -class User(BaseModel): +class User(Base): id: Optional[int] = None name: str = Field(..., max_length=100) login: str = Field(..., max_length=100) diff --git a/api/api/schemas/account/account_keyring.py b/api/api/schemas/account/account_keyring.py index 0ae3379..1d2dc58 100644 --- a/api/api/schemas/account/account_keyring.py +++ b/api/api/schemas/account/account_keyring.py @@ -1,9 +1,12 @@ import datetime from enum import Enum from typing import Optional, Dict -from pydantic import BaseModel, Field +from pydantic import Field from datetime import datetime +from api.schemas.base import Base + + # Модель для хранения информации из запроса @@ -20,7 +23,7 @@ class StatusKey(Enum): DELETED = "DELETED" -class AccountKeyring(BaseModel): +class AccountKeyring(Base): owner_id: int key_type: TypeKey # Используем тот же KeyType key_id: Optional[str] = Field(None, max_length=40) # Изменено на None как default diff --git a/api/api/schemas/base.py b/api/api/schemas/base.py new file mode 100644 index 0000000..ed76e62 --- /dev/null +++ b/api/api/schemas/base.py @@ -0,0 +1,11 @@ +from pydantic import BaseModel, ConfigDict + +from api.utils.mapper import to_camel + + +class Base(BaseModel): + model_config = ConfigDict( + from_attributes=True, + alias_generator=to_camel, + populate_by_name=True + ) diff --git a/api/api/schemas/endpoints/account.py b/api/api/schemas/endpoints/account.py index 8d06f94..da33b9f 100644 --- a/api/api/schemas/endpoints/account.py +++ b/api/api/schemas/endpoints/account.py @@ -1,7 +1,10 @@ from enum import Enum from typing import Optional from datetime import datetime -from pydantic import BaseModel, EmailStr, Field +from pydantic import EmailStr, Field + +from api.schemas.base import Base + # Таблица для получения информации из запроса @@ -20,7 +23,7 @@ class Status(Enum): DELETED = "DELETED" -class UserUpdate(BaseModel): +class UserUpdate(Base): id: Optional[int] = None name: Optional[str] = Field(None, max_length=100) login: Optional[str] = Field(None, max_length=100) diff --git a/api/api/schemas/endpoints/account_keyring.py b/api/api/schemas/endpoints/account_keyring.py index aab69e4..cce387c 100644 --- a/api/api/schemas/endpoints/account_keyring.py +++ b/api/api/schemas/endpoints/account_keyring.py @@ -1,9 +1,12 @@ import datetime from enum import Enum from typing import Optional -from pydantic import BaseModel, Field +from pydantic import Field from datetime import datetime +from api.schemas.base import Base + + # Таблица для получения информации из запроса @@ -20,7 +23,7 @@ class StatusKey(Enum): DELETED = "DELETED" -class AccountKeyringUpdate(BaseModel): +class AccountKeyringUpdate(Base): owner_id: Optional[int] = None key_type: Optional[TypeKey] = None key_id: Optional[str] = Field(None, max_length=40) diff --git a/api/api/schemas/endpoints/auth.py b/api/api/schemas/endpoints/auth.py index fe97477..fd7648c 100644 --- a/api/api/schemas/endpoints/auth.py +++ b/api/api/schemas/endpoints/auth.py @@ -1,12 +1,17 @@ -from pydantic import BaseModel +from api.schemas.base import Base + # Таблица для получения информации из запроса -class Auth(BaseModel): +class Auth(Base): login: str password: str -class Refresh(BaseModel): +class AccessToken(Base): + access_token: str + + +class Refresh(Base): refresh_token: str diff --git a/api/api/schemas/events/list_events.py b/api/api/schemas/events/list_events.py index 1412d4a..2df94c7 100644 --- a/api/api/schemas/events/list_events.py +++ b/api/api/schemas/events/list_events.py @@ -1,8 +1,10 @@ -from pydantic import BaseModel, Field +from pydantic import Field from typing import Dict, Any from datetime import datetime from enum import Enum +from api.schemas.base import Base + class State(Enum): AUTO = "Auto" @@ -15,7 +17,7 @@ class Status(Enum): DELETED = "Deleted" -class ListEvent(BaseModel): +class ListEvent(Base): id: int name: str = Field(..., max_length=40) title: str = Field(..., max_length=64) diff --git a/api/api/schemas/process/node_link.py b/api/api/schemas/process/node_link.py index 1e79b72..92d5513 100644 --- a/api/api/schemas/process/node_link.py +++ b/api/api/schemas/process/node_link.py @@ -1,8 +1,10 @@ -from pydantic import BaseModel, Field, conint +from pydantic import Field, conint from typing import Dict, Any from datetime import datetime from enum import Enum +from api.schemas.base import Base + class Status(Enum): ACTIVE = "Active" @@ -11,7 +13,7 @@ class Status(Enum): DELETED = "Deleted" -class MyModel(BaseModel): +class MyModel(Base): id: int link_name: str = Field(..., max_length=20) node_id: int diff --git a/api/api/schemas/process/process_schema.py b/api/api/schemas/process/process_schema.py index 03d0941..70f670b 100644 --- a/api/api/schemas/process/process_schema.py +++ b/api/api/schemas/process/process_schema.py @@ -1,8 +1,10 @@ -from pydantic import BaseModel, Field +from pydantic import Field from typing import Dict, Any from datetime import datetime from enum import Enum +from api.schemas.base import Base + class Status(Enum): ACTIVE = "Active" @@ -11,7 +13,7 @@ class Status(Enum): DELETED = "Deleted" -class ProcessSchema(BaseModel): +class ProcessSchema(Base): id: int title: str = Field(..., max_length=100) description: str diff --git a/api/api/schemas/process/process_version_archive.py b/api/api/schemas/process/process_version_archive.py index 1d7b639..83afe3b 100644 --- a/api/api/schemas/process/process_version_archive.py +++ b/api/api/schemas/process/process_version_archive.py @@ -1,9 +1,10 @@ -from pydantic import BaseModel, Field from typing import Dict, Any from datetime import datetime +from api.schemas.base import Base -class ProcessStatusSchema(BaseModel): + +class ProcessStatusSchema(Base): id: int version: int snapshot: Dict[str, Any] diff --git a/api/api/schemas/process/ps_node.py b/api/api/schemas/process/ps_node.py index 32f1368..0a47f38 100644 --- a/api/api/schemas/process/ps_node.py +++ b/api/api/schemas/process/ps_node.py @@ -1,8 +1,9 @@ -from pydantic import BaseModel from datetime import datetime from typing import Dict, Any from enum import Enum +from api.schemas.base import Base + class NodeType(Enum): pass @@ -14,7 +15,7 @@ class Status(Enum): DELETED = "Deleted" -class Ps_Node(BaseModel): +class Ps_Node(Base): id: int ps_id: int node_type: NodeType diff --git a/api/api/utils/mapper.py b/api/api/utils/mapper.py new file mode 100644 index 0000000..b056aaa --- /dev/null +++ b/api/api/utils/mapper.py @@ -0,0 +1,3 @@ +def to_camel(string: str) -> str: + splitted = string.split("_") + return splitted[0] + "".join(word.capitalize() for word in splitted[1:]) From 86d48d0d1ca338c315c0e850b0091796ae40f1cd Mon Sep 17 00:00:00 2001 From: Vladislav Date: Wed, 21 May 2025 14:51:09 +0500 Subject: [PATCH 2/3] refactor(base): replace to_camel to to_camel from pydantic --- api/api/schemas/base.py | 5 ++--- api/api/utils/mapper.py | 3 --- 2 files changed, 2 insertions(+), 6 deletions(-) delete mode 100644 api/api/utils/mapper.py diff --git a/api/api/schemas/base.py b/api/api/schemas/base.py index ed76e62..5fcc034 100644 --- a/api/api/schemas/base.py +++ b/api/api/schemas/base.py @@ -1,11 +1,10 @@ from pydantic import BaseModel, ConfigDict - -from api.utils.mapper import to_camel +from pydantic.alias_generators import to_camel class Base(BaseModel): model_config = ConfigDict( from_attributes=True, alias_generator=to_camel, - populate_by_name=True + populate_by_name=True, ) diff --git a/api/api/utils/mapper.py b/api/api/utils/mapper.py deleted file mode 100644 index b056aaa..0000000 --- a/api/api/utils/mapper.py +++ /dev/null @@ -1,3 +0,0 @@ -def to_camel(string: str) -> str: - splitted = string.split("_") - return splitted[0] + "".join(word.capitalize() for word in splitted[1:]) From 98e425862ccf05ab6e5962a3db66e11a72e813e9 Mon Sep 17 00:00:00 2001 From: Vladislav Date: Fri, 23 May 2025 18:03:28 +0500 Subject: [PATCH 3/3] refactor(account): remove unused print --- api/api/db/logic/account.py | 2 -- 1 file changed, 2 deletions(-) diff --git a/api/api/db/logic/account.py b/api/api/db/logic/account.py index 09b30d9..489ff32 100644 --- a/api/api/db/logic/account.py +++ b/api/api/db/logic/account.py @@ -47,7 +47,6 @@ async def get_user_login(connection: AsyncConnection, login: str) -> Optional[Us if not user_db: return None - print("user_db", user_db) user_data = { column.name: ( @@ -57,7 +56,6 @@ async def get_user_login(connection: AsyncConnection, login: str) -> Optional[Us ) for column in account_table.columns } - print("user_data", user_data) return User.model_validate(user_data)