Compare commits

..

3 Commits

Author SHA1 Message Date
berkay b4b9f97690 updated 2025-03-26 11:10:08 +03:00
berkay 637edfadd4 auth api tested 2025-03-25 19:01:46 +03:00
berkay db2cde2f5d api design 2025-03-25 16:38:58 +03:00
65 changed files with 810 additions and 712 deletions

View File

@ -0,0 +1,118 @@
import datetime
class DefaultApiConfig:
app: str
host: str
port: int
log_level: str
reload: bool
@classmethod
def as_dict(cls):
return {
"app": cls.app,
"host": cls.host,
"port": int(cls.port),
"log_level": cls.log_level,
"reload": bool(cls.reload),
}
class ApiConfigs:
"""Base class for all configurations."""
SECRET: str = (
"59f871a2d2194e96adb36b279d2cc21059f871a2d2194e96adb36b279d2cc21059f871a2d2194e96adb36b279d2cc210s"
)
ACCESS_TIME: int = 432000
REFRESH_TIME: int = 864000
DEFAULT_SIZE: int = 10
MIN_SIZE: int = 5
MAX_SIZE: int = 50
ACCESS_TOKEN_TAG: str = "Authorization"
REFRESH_TOKEN_TAG: str = "Refresher"
ACCESS_TOKEN_LENGTH: int = 72
REFRESH_TOKEN_LENGTH: int = 128
class ApiStatic:
PLACEHOLDER = "https://s.tmimgcdn.com/scr/800x500/276800/building-home-nature-logo-vector-template-3_276851-original.jpg"
FORGOT_LINK = "https://www.evyos.com.tr/password/create?tokenUrl="
BLACKLIST_LINK = "https://www.evyos.com.tr/support/unknown-login-notice/"
APP_DIR = "/home/berkay/git-evyos/api-managment-backend/"
@classmethod
def forgot_link(cls, forgot_key):
return cls.FORGOT_LINK + forgot_key
@classmethod
def blacklist_login(cls, record_id):
return cls.BLACKLIST_LINK + record_id
class MainConfig:
# Date and Time Configuration
DATETIME_FORMAT = "YYYY-MM-DD HH:mm:ss Z"
DATETIME_FORMAT_JS = "YYYY-MM-DD HH:mm:ss +0"
# Timezone Configuration
DEFAULT_TIMEZONE = "GMT+3" # Default timezone for the application
SYSTEM_TIMEZONE = "GMT+0" # System timezone (used for internal operations)
SUPPORTED_TIMEZONES = ["GMT+0", "GMT+3"] # List of supported timezones
class LanguageConfig:
SUPPORTED_LANGUAGES = ["en", "tr"]
DEFAULT_LANGUAGE = "tr"
class ValidationsConfig:
SUPPORTED_VALIDATIONS = ["header", "validation", "all"]
DEFAULT_VALIDATION = "all"
class ApiConfig(DefaultApiConfig):
# Application Information
APP_NAME = "evyos-auth-api-gateway"
TITLE = "WAG API Auth Api Gateway"
DESCRIPTION = (
"This api is serves as web auth api gateway only to evyos web services."
)
APP_URL = "https://www.auth.eys.gen.tr"
# Server Configuration
app = "app:app"
host = "0.0.0.0"
port = 41575
log_level = "info"
reload = True
class Auth:
ACCESS_EMAIL_EXT = "evyos.com.tr"
ACCESS_TOKEN_TAG = "evyos-session-key"
REFRESHER_TOKEN_TAG = "eys-session-refresher"
SECRET_KEY_72 = (
"t3sUAmjTGeTgDc6dAUrB41u2SNg0ZHzj4HTjem95y3fRH1nZXOHIBj163kib6iLybT0gLaxq"
)
SECRET_KEY_96 = "7ct8VpiwaP1hR2bVSet4dEEAgepuTZUOnO1QxOgKyDqBR2PkqNhcubSrbUUigQKoQA1PBoeeQn5ZCo24pESmVtKs76nA4EKq"
SECRET_KEY_144 = (
"R2p5Rq6KCr6PCfjFYUeH1keF2VWHFEuqINVjBGGnvRA2m10pYUKqfOtIGBcaj2v5wZmElDndzSHGOS7roQsoTelPSok0"
+ "qqMucurMWE0FGexGpFuJkfPEm9tH2OjMOqegvEetpSVywH0W4Kh4"
)
ALGORITHM = "HS256"
ACCESS_TOKEN_LENGTH: int = 90
REFRESHER_TOKEN_LENGTH: int = 144
PASSWORD_EXPIRE_DAY = datetime.timedelta(days=30)
TOKEN_EXPIRE_MINUTES_1 = datetime.timedelta(minutes=1)
TOKEN_EXPIRE_MINUTES_15 = datetime.timedelta(minutes=15)
TOKEN_EXPIRE_MINUTES_30 = datetime.timedelta(minutes=30)
TOKEN_EXPIRE_DAY_1 = datetime.timedelta(days=1)
TOKEN_EXPIRE_DAY_5 = datetime.timedelta(days=5)
TOKEN_EXPIRE_DAY_15 = datetime.timedelta(days=15)
TOKEN_EXPIRE_DAY_30 = datetime.timedelta(days=30)

View File

@ -5,19 +5,21 @@ from ApiLayers.AllConfigs import HostConfig
class Config: class Config:
MAILBOX: str = os.getenv('MAILBOX', "bilgilendirme@ileti.isbank.com.tr") MAILBOX: str = os.getenv("MAILBOX", "bilgilendirme@ileti.isbank.com.tr")
MAIN_MAIL: str = os.getenv('MAIN_MAIL', "karatay.berkay@gmail.com") MAIN_MAIL: str = os.getenv("MAIN_MAIL", "karatay.berkay@gmail.com")
INFO_MAIL: str = os.getenv('INFO_MAIL', "mehmet.karatay@hotmail.com") INFO_MAIL: str = os.getenv("INFO_MAIL", "mehmet.karatay@hotmail.com")
EMAIL_HOST: str = os.getenv('EMAIL_HOST', "10.10.2.34") EMAIL_HOST: str = os.getenv("EMAIL_HOST", "10.10.2.34")
EMAIL_SENDER_USERNAME: str = os.getenv('EMAIL_SENDER_USERNAME', "karatay@mehmetkaratay.com.tr") EMAIL_SENDER_USERNAME: str = os.getenv(
EMAIL_USERNAME: str = os.getenv('EMAIL_USERNAME', "isbank@mehmetkaratay.com.tr") "EMAIL_SENDER_USERNAME", "karatay@mehmetkaratay.com.tr"
EMAIL_PASSWORD: str = os.getenv('EMAIL_PASSWORD', "system") )
AUTHORIZE_IBAN: str = os.getenv('AUTHORIZE_IBAN', "4245-0093333") EMAIL_USERNAME: str = os.getenv("EMAIL_USERNAME", "isbank@mehmetkaratay.com.tr")
SERVICE_TIMING: int = int(os.getenv('SERVICE_TIMING', 900)) EMAIL_PASSWORD: str = os.getenv("EMAIL_PASSWORD", "system")
EMAIL_PORT: int = int(os.getenv('EMAIL_PORT', 993)) AUTHORIZE_IBAN: str = os.getenv("AUTHORIZE_IBAN", "4245-0093333")
EMAIL_SEND_PORT: int = int(os.getenv('EMAIL_SEND_PORT', 587)) SERVICE_TIMING: int = int(os.getenv("SERVICE_TIMING", 900))
EMAIL_SLEEP: int = int(os.getenv('EMAIL_SLEEP', 60)) EMAIL_PORT: int = int(os.getenv("EMAIL_PORT", 993))
EMAIL_SEND: bool = bool(os.getenv('EMAIL_SEND', False)) EMAIL_SEND_PORT: int = int(os.getenv("EMAIL_SEND_PORT", 587))
EMAIL_SLEEP: int = int(os.getenv("EMAIL_SLEEP", 60))
EMAIL_SEND: bool = bool(os.getenv("EMAIL_SEND", False))
class EmailConfig: class EmailConfig:

View File

@ -3,7 +3,7 @@ from ApiLayers.AllConfigs import HostConfig
class WagDatabase: class WagDatabase:
HOST: str = HostConfig.MAIN_HOST HOST: str = HostConfig.MAIN_HOST
PORT: int = 5434 PORT: int = 5444
SQL: str = "postgresql+psycopg2" SQL: str = "postgresql+psycopg2"
USERNAME: str = "berkay_wag_user" USERNAME: str = "berkay_wag_user"
PASSWORD: str = "berkay_wag_user_password" PASSWORD: str = "berkay_wag_user_password"

View File

@ -1,5 +1,3 @@
class HostConfig: class HostConfig:
MAIN_HOST = "10.10.2.36" # http://10.10.2.36 Database and other services MAIN_HOST = "10.10.2.36" # http://10.10.2.36 Database and other services

View File

@ -1,5 +1,4 @@
from fastapi import APIRouter from fastapi import APIRouter
import uuid
from Events.Engine.abstract_class import CategoryCluster, MethodToEvent from Events.Engine.abstract_class import CategoryCluster, MethodToEvent

View File

@ -1,4 +1,6 @@
from Services.Redis import RedisActions, AccessToken from Services.RedisService.Actions.actions import RedisActions
from Services.Redis.Models.cluster import RedisList from Services.RedisService.Models.access import AccessToken
from Services.RedisService.Models.cluster import RedisList
redis_list = RedisList(redis_key="test") redis_list = RedisList(redis_key="test")

View File

@ -23,13 +23,12 @@ class UserLoginModule:
} }
@staticmethod @staticmethod
def check_user_exists(access_key: str): def check_user_exists(access_key: str, db_session):
from ApiLayers.Schemas import Users from ApiLayers.Schemas import Users
""" """
Check if the user exists in the database. Check if the user exists in the database.
""" """
db_session = Users.new_session() # Check if user exists.
if "@" in access_key: if "@" in access_key:
found_user: Users = Users.filter_one( found_user: Users = Users.filter_one(
Users.email == access_key.lower(), db=db_session Users.email == access_key.lower(), db=db_session
@ -54,42 +53,46 @@ class UserLoginModule:
""" """
Login the user via the credentials. Login the user via the credentials.
""" """
with Users.new_session() as db_session: # Check if user exists.
# Get the actual data from the BaseRequestModel if needed # Get the actual data from the BaseRequestModel if needed
found_user: Users = self.check_user_exists(access_key=access_data.access_key) found_user: Users = self.check_user_exists(
if len(found_user.hash_password) < 5: access_key=access_data.access_key, db_session=db_session
)
if len(found_user.hash_password) < 5:
raise HTTPExceptionApi(
error_code="HTTP_400_BAD_REQUEST",
lang=found_user.lang,
loc=get_line_number_for_error(),
sys_msg="login_user_via_credentials: Invalid password create a password to user first",
)
# Check if the password is correct
if PasswordModule.check_password(
domain=access_data.domain,
id_=found_user.uu_id,
password=access_data.password,
password_hashed=found_user.hash_password,
):
found_user_dict = found_user.get_dict()
# Set the access token to the redis
token_response = TokenService.set_access_token_to_redis(
request=self.request,
user=found_user,
domain=access_data.domain,
remember=access_data.remember_me,
db_session=db_session
)
# Set the user and token information to the instance
self.user = found_user_dict
self.access_token = token_response.get("access_token")
self.refresh_token = token_response.get("refresh_token")
self.access_object = {
"user_type": token_response.get("user_type", None),
"selection_list": token_response.get("selection_list", {}),
}
return None
raise HTTPExceptionApi( raise HTTPExceptionApi(
error_code="HTTP_400_BAD_REQUEST", error_code="HTTP_400_BAD_REQUEST",
lang=found_user.lang, lang="tr",
loc=get_line_number_for_error(), loc=get_line_number_for_error(),
sys_msg="login_user_via_credentials: Invalid password create a password to user first", sys_msg="login_user_via_credentials: raised an unknown error",
) )
# Check if the password is correct
if PasswordModule.check_password(
domain=access_data.domain,
id_=found_user.uu_id,
password=access_data.password,
password_hashed=found_user.hash_password,
):
# Set the access token to the redis
token_response = TokenService.set_access_token_to_redis(
request=self.request,
user=found_user,
domain=access_data.domain,
remember=access_data.remember_me,
)
# Set the user and token information to the instance
self.user = found_user.get_dict()
self.access_token = token_response.get("access_token")
self.refresh_token = token_response.get("refresh_token")
self.access_object = {
"user_type": token_response.get("user_type", None),
"selection_list": token_response.get("selection_list", {}),
}
return None
raise HTTPExceptionApi(
error_code="HTTP_400_BAD_REQUEST",
lang="tr",
loc=get_line_number_for_error(),
sys_msg="login_user_via_credentials: raised an unknown error",
)

View File

@ -30,8 +30,9 @@ from ApiLayers.Schemas import (
Departments, Departments,
OccupantTypes, OccupantTypes,
) )
from Services.Redis.Models.response import RedisResponse from Services.RedisService.Models.response import RedisResponse
from Services.Redis import RedisActions, AccessToken from Services.RedisService.Actions.actions import RedisActions
from Services.RedisService.Models.access import AccessToken
if TYPE_CHECKING: if TYPE_CHECKING:
@ -63,78 +64,78 @@ class TokenService:
"""Handle employee login process and return login information.""" """Handle employee login process and return login information."""
from ApiLayers.Schemas.identity.identity import UsersTokens, People from ApiLayers.Schemas.identity.identity import UsersTokens, People
db_session = Employees.new_session() with Employees.new_session() as db_session:
list_employee = Employees.filter_all( list_employee = Employees.filter_all(
Employees.people_id == user.person_id, db=db_session Employees.people_id == user.person_id, db=db_session
).data
companies_uu_id_list: List[str] = []
companies_id_list: List[int] = []
companies_list: List[Dict[str, Any]] = []
duty_uu_id_list: List[str] = []
duty_id_list: List[int] = []
for employee in list_employee:
staff = Staff.filter_one(Staff.id == employee.staff_id, db=db_session).data
if duties := Duties.filter_one(
Duties.id == staff.duties_id, db=db_session
).data:
if duty_found := Duty.filter_by_one(
id=duties.duties_id, db=db_session
).data:
duty_uu_id_list.append(str(duty_found.uu_id))
duty_id_list.append(duty_found.id)
department = Departments.filter_one(
Departments.id == duties.department_id, db=db_session
).data ).data
if company := Companies.filter_one( companies_uu_id_list: List[str] = []
Companies.id == department.company_id, db=db_session companies_id_list: List[int] = []
).data: companies_list: List[Dict[str, Any]] = []
companies_uu_id_list.append(str(company.uu_id)) duty_uu_id_list: List[str] = []
companies_id_list.append(company.id) duty_id_list: List[int] = []
company_address = Addresses.filter_by_one(
id=company.official_address_id, db=db_session for employee in list_employee:
staff = Staff.filter_one(Staff.id == employee.staff_id, db=db_session).data
if duties := Duties.filter_one(
Duties.id == staff.duties_id, db=db_session
).data:
if duty_found := Duty.filter_by_one(
id=duties.duties_id, db=db_session
).data:
duty_uu_id_list.append(str(duty_found.uu_id))
duty_id_list.append(duty_found.id)
department = Departments.filter_one(
Departments.id == duties.department_id, db=db_session
).data ).data
companies_list.append(
{ if company := Companies.filter_one(
"uu_id": str(company.uu_id), Companies.id == department.company_id, db=db_session
"public_name": company.public_name, ).data:
"company_type": company.company_type, companies_uu_id_list.append(str(company.uu_id))
"company_address": company_address, companies_id_list.append(company.id)
} company_address = Addresses.filter_by_one(
) id=company.official_address_id, db=db_session
person = People.filter_one(People.id == user.person_id, db=db_session).data ).data
model_value = EmployeeTokenObject( companies_list.append(
domain=domain, {
user_type=UserType.employee.value, "uu_id": str(company.uu_id),
user_uu_id=str(user.uu_id), "public_name": company.public_name,
credentials=user.credentials(), "company_type": company.company_type,
user_id=user.id, "company_address": company_address,
person_id=person.id, }
person_uu_id=str(person.uu_id), )
full_name=person.full_name, person = People.filter_one(People.id == user.person_id, db=db_session).data
request=dict(request.headers), model_value = EmployeeTokenObject(
companies_uu_id_list=companies_uu_id_list, domain=domain,
companies_id_list=companies_id_list, user_type=UserType.employee.value,
duty_uu_id_list=duty_uu_id_list, user_uu_id=str(user.uu_id),
duty_id_list=duty_id_list, credentials=user.credentials(db_session=db_session),
timezone=user.local_timezone or "GMT+0", user_id=user.id,
lang="tr", person_id=person.id,
).model_dump() person_uu_id=str(person.uu_id),
if access_token := cls.set_object_to_redis(user, model_value): full_name=person.full_name,
return { request=dict(request.headers),
"access_token": access_token, companies_uu_id_list=companies_uu_id_list,
"user_type": UserType.employee.name, companies_id_list=companies_id_list,
"selection_list": companies_list, duty_uu_id_list=duty_uu_id_list,
} duty_id_list=duty_id_list,
raise HTTPExceptionApi( timezone=user.local_timezone or "GMT+0",
error_code="", lang="tr",
lang="en", ).model_dump()
loc=get_line_number_for_error(), if access_token := cls.set_object_to_redis(user, model_value):
sys_msg="Creating Token failed...", return {
) "access_token": access_token,
"user_type": UserType.employee.name,
"selection_list": companies_list,
}
raise HTTPExceptionApi(
error_code="",
lang="en",
loc=get_line_number_for_error(),
sys_msg="Creating Token failed...",
)
@classmethod @classmethod
def do_occupant_login( def do_occupant_login(
@ -285,14 +286,15 @@ class TokenService:
user: Users, user: Users,
domain: str, domain: str,
remember: bool, remember: bool,
db_session
) -> Dict[str, Any]: ) -> Dict[str, Any]:
"""Set access token to redis and handle user session.""" """Set access token to redis and handle user session."""
from ApiLayers.AllConfigs.Token.config import Auth from ApiLayers.AllConfigs.Token.config import Auth
from ApiLayers.Schemas.identity.identity import UsersTokens, People from ApiLayers.Schemas.identity.identity import UsersTokens, People
user_id, user_dict = user.id, user.get_dict()
cls.remove_token_with_domain(user=user, domain=domain) cls.remove_token_with_domain(user=user, domain=domain)
# Users.client_arrow = DateTimeLocal(is_client=True, timezone=user.local_timezone) login_dict = {}
login_dict, db_session = {}, UsersTokens.new_session()
if user.is_occupant: # Handle login based on user type if user.is_occupant: # Handle login based on user type
login_dict = cls.do_occupant_login( login_dict = cls.do_occupant_login(
request=request, user=user, domain=domain request=request, user=user, domain=domain
@ -309,7 +311,7 @@ class TokenService:
login_dict["refresh_token"] = users_token_created login_dict["refresh_token"] = users_token_created
users_token = UsersTokens.find_or_create( users_token = UsersTokens.find_or_create(
db=db_session, db=db_session,
user_id=user.id, user_id=user_id,
token_type="RememberMe", token_type="RememberMe",
domain=domain, domain=domain,
) )
@ -329,15 +331,15 @@ class TokenService:
login_dict["refresh_token"] = users_token.token login_dict["refresh_token"] = users_token.token
else: else:
already_refresher = UsersTokens.filter_all( already_refresher = UsersTokens.filter_all(
UsersTokens.user_id == user.id, UsersTokens.user_id == user_id,
UsersTokens.token_type == "RememberMe", UsersTokens.token_type == "RememberMe",
UsersTokens.domain == domain, UsersTokens.domain == domain,
db=db_session, db=db_session,
) )
if already_refresher.count: if already_refresher.count:
already_refresher.query.delete(synchronize_session=False) already_refresher.core_query.delete(synchronize_session=False)
user.save(db=db_session) user.save(db=db_session)
return {**login_dict, "user": user.get_dict()} return {**login_dict, "user": user_dict}
@classmethod @classmethod
def update_token_at_redis( def update_token_at_redis(

View File

@ -1,4 +1,3 @@
import json
from typing import Any, Union, Awaitable from typing import Any, Union, Awaitable
from pydantic import ValidationError from pydantic import ValidationError

View File

@ -1,4 +1,4 @@
from Services.Redis.Actions.actions import RedisActions from Services.RedisService.Actions.actions import RedisActions
from ApiLayers.AllConfigs.Redis.configs import RedisValidationKeys from ApiLayers.AllConfigs.Redis.configs import RedisValidationKeys

View File

@ -4,7 +4,7 @@ from ApiLayers.AllConfigs.Redis.configs import (
) )
from ApiLayers.AllConfigs.main import LanguageConfig from ApiLayers.AllConfigs.main import LanguageConfig
from Events.Engine.set_defaults.category_cluster_models import CategoryClusterController from Events.Engine.set_defaults.category_cluster_models import CategoryClusterController
from Services.Redis.Actions.actions import RedisActions from Services.RedisService.Actions.actions import RedisActions
class SetDefaultLanguageModelsRedis: class SetDefaultLanguageModelsRedis:

View File

@ -1,5 +1,5 @@
from typing import Optional from typing import Optional
from Services.Redis import RedisActions from Services.RedisService.Actions.actions import RedisActions
from ApiLayers.AllConfigs.Redis.configs import RedisValidationKeysAction from ApiLayers.AllConfigs.Redis.configs import RedisValidationKeysAction

View File

@ -16,7 +16,7 @@ from ApiLayers.ErrorHandlers.Exceptions.api_exc import HTTPExceptionApi
from ApiLayers.Schemas import Events, EndpointRestriction from ApiLayers.Schemas import Events, EndpointRestriction
from ApiLayers.AllConfigs.Redis.configs import RedisCategoryKeys from ApiLayers.AllConfigs.Redis.configs import RedisCategoryKeys
from Services.Redis.Actions.actions import RedisActions from Services.RedisService.Actions.actions import RedisActions
from .auth_middleware import MiddlewareModule from .auth_middleware import MiddlewareModule

View File

@ -10,7 +10,7 @@ from sqlalchemy import (
SmallInteger, SmallInteger,
) )
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
from ApiLayers.LanguageModels.Database.account.account import ( from ApiLayers.LanguageModels.Database.account.account import (
AccountBooksLanguageModel, AccountBooksLanguageModel,
AccountCodesLanguageModel, AccountCodesLanguageModel,

View File

@ -1,7 +1,7 @@
from sqlalchemy import String, ForeignKey, Index, TIMESTAMP, SmallInteger, Identity from sqlalchemy import String, ForeignKey, Index, TIMESTAMP, SmallInteger, Identity
from sqlalchemy.orm import mapped_column, Mapped from sqlalchemy.orm import mapped_column, Mapped
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
class BuildIbans(CrudCollection): class BuildIbans(CrudCollection):

View File

@ -6,7 +6,7 @@ from sqlalchemy import String
from sqlalchemy.orm import mapped_column, Mapped from sqlalchemy.orm import mapped_column, Mapped
from cryptography.fernet import Fernet, MultiFernet from cryptography.fernet import Fernet, MultiFernet
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
class CrypterEngine(CrudCollection): class CrypterEngine(CrudCollection):

View File

@ -9,7 +9,7 @@ from sqlalchemy import (
Integer, Integer,
) )
from sqlalchemy.orm import mapped_column, Mapped from sqlalchemy.orm import mapped_column, Mapped
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
class DecisionBookBudgetBooks(CrudCollection): class DecisionBookBudgetBooks(CrudCollection):

View File

@ -16,7 +16,7 @@ from sqlalchemy import (
) )
from ApiLayers.ApiLibrary import system_arrow, SelectActionWithEmployee from ApiLayers.ApiLibrary import system_arrow, SelectActionWithEmployee
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
from ApiLayers.ApiValidations.Request import ( from ApiLayers.ApiValidations.Request import (
InsertBuild, InsertBuild,
InsertBuildParts, InsertBuildParts,

View File

@ -25,7 +25,7 @@ from ApiLayers.ApiValidations.Request import (
InsertBuildDecisionBookItemDebits, InsertBuildDecisionBookItemDebits,
InsertBuildDecisionBookProjects, InsertBuildDecisionBookProjects,
) )
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
from ApiLayers.LanguageModels.Database.building.decision_book import ( from ApiLayers.LanguageModels.Database.building.decision_book import (
BuildDecisionBookLanguageModel, BuildDecisionBookLanguageModel,
BuildDecisionBookInvitationsLanguageModel, BuildDecisionBookInvitationsLanguageModel,

View File

@ -23,7 +23,7 @@ from ApiLayers.LanguageModels.Database.company.company import (
CompaniesLanguageModel, CompaniesLanguageModel,
# CompanyDutiesLanguageModel, # CompanyDutiesLanguageModel,
) )
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
class RelationshipDutyCompany(CrudCollection): class RelationshipDutyCompany(CrudCollection):

View File

@ -1,7 +1,7 @@
from sqlalchemy import String, Integer, ForeignKey, Index, Boolean, Identity from sqlalchemy import String, Integer, ForeignKey, Index, Boolean, Identity
from sqlalchemy.orm import mapped_column, Mapped from sqlalchemy.orm import mapped_column, Mapped
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
class Departments(CrudCollection): class Departments(CrudCollection):

View File

@ -12,7 +12,7 @@ from ApiLayers.LanguageModels.Database.company.employee import (
EmployeeHistoryLanguageModel, EmployeeHistoryLanguageModel,
EmployeesSalariesLanguageModel, EmployeesSalariesLanguageModel,
) )
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
from ApiLayers.ApiValidations.Request import InsertCompanyEmployees from ApiLayers.ApiValidations.Request import InsertCompanyEmployees

View File

@ -1,4 +1,4 @@
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
from ApiLayers.LanguageModels.Database.event.event import ( from ApiLayers.LanguageModels.Database.event.event import (
EventsLanguageModel, EventsLanguageModel,
ModulesLanguageModel, ModulesLanguageModel,
@ -250,29 +250,28 @@ class Event2Employee(CrudCollection):
) )
@classmethod @classmethod
def get_event_codes(cls, employee_id: int) -> list: def get_event_codes(cls, employee_id: int, db_session) -> list:
db = cls.new_session()
employee_events = cls.filter_all( employee_events = cls.filter_all(
cls.employee_id == employee_id, cls.employee_id == employee_id,
db=db, db=db_session,
).data ).data
active_event_ids = Service2Events.filter_all_system( active_event_ids = Service2Events.filter_all_system(
Service2Events.service_id.in_( Service2Events.service_id.in_(
[event.event_service_id for event in employee_events] [event.event_service_id for event in employee_events]
), ),
db=db, db=db_session,
).data ).data
active_events = Events.filter_all( active_events = Events.filter_all(
Events.id.in_([event.event_id for event in active_event_ids]), Events.id.in_([event.event_id for event in active_event_ids]),
db=db, db=db_session,
).data ).data
if extra_events := Event2EmployeeExtra.filter_all( if extra_events := Event2EmployeeExtra.filter_all(
Event2EmployeeExtra.employee_id == employee_id, Event2EmployeeExtra.employee_id == employee_id,
db=db, db=db_session,
).data: ).data:
events_extra = Events.filter_all( events_extra = Events.filter_all(
Events.id.in_([event.event_id for event in extra_events]), Events.id.in_([event.event_id for event in extra_events]),
db=db, db=db_session,
).data ).data
active_events.extend(events_extra) active_events.extend(events_extra)
return [event.function_code for event in active_events] return [event.function_code for event in active_events]
@ -349,29 +348,28 @@ class Event2Occupant(CrudCollection):
) )
@classmethod @classmethod
def get_event_codes(cls, build_living_space_id) -> list: def get_event_codes(cls, build_living_space_id, db_session) -> list:
db = cls.new_session()
occupant_events = cls.filter_all( occupant_events = cls.filter_all(
cls.build_living_space_id == build_living_space_id, cls.build_living_space_id == build_living_space_id,
db=db, db=db_session,
).data ).data
active_event_ids = Service2Events.filter_all_system( active_event_ids = Service2Events.filter_all_system(
Service2Events.service_id.in_( Service2Events.service_id.in_(
[event.event_service_id for event in occupant_events] [event.event_service_id for event in occupant_events]
), ),
db=db, db=db_session,
).data ).data
active_events = Events.filter_all( active_events = Events.filter_all(
Events.id.in_([event.event_id for event in active_event_ids]), Events.id.in_([event.event_id for event in active_event_ids]),
db=db, db=db_session,
).data ).data
if extra_events := Event2OccupantExtra.filter_all( if extra_events := Event2OccupantExtra.filter_all(
Event2OccupantExtra.build_living_space_id == build_living_space_id, Event2OccupantExtra.build_living_space_id == build_living_space_id,
db=db, db=db_session,
).data: ).data:
events_extra = Events.filter_all( events_extra = Events.filter_all(
Events.id.in_([event.event_id for event in extra_events]), Events.id.in_([event.event_id for event in extra_events]),
db=db, db=db_session,
).data ).data
active_events.extend(events_extra) active_events.extend(events_extra)
return [event.function_code for event in active_events] return [event.function_code for event in active_events]

View File

@ -15,7 +15,7 @@ from sqlalchemy import (
) )
from sqlalchemy.orm import mapped_column, relationship, Mapped from sqlalchemy.orm import mapped_column, relationship, Mapped
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
from config import ApiStatic from config import ApiStatic
from ApiLayers.ApiLibrary.date_time_actions.date_functions import system_arrow from ApiLayers.ApiLibrary.date_time_actions.date_functions import system_arrow
@ -144,8 +144,7 @@ class Users(CrudCollection, SelectAction):
return "Occupant" if self.is_occupant else "Employee" return "Occupant" if self.is_occupant else "Employee"
@classmethod @classmethod
def credentials(cls): def credentials(cls, db_session):
db_session = cls.new_session()
person_object: People = People.filter_by_one( person_object: People = People.filter_by_one(
db=db_session, system=True, id=cls.person_id db=db_session, system=True, id=cls.person_id
).data ).data

View File

@ -9,7 +9,7 @@ from sqlalchemy.orm import (
Mapped, Mapped,
mapped_column, mapped_column,
) )
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
class ApiEnumDropdown(CrudCollection): class ApiEnumDropdown(CrudCollection):

View File

@ -4,7 +4,7 @@ from sqlalchemy.orm import mapped_column, Mapped
from ApiLayers.LanguageModels.Database.rules.rules import ( from ApiLayers.LanguageModels.Database.rules.rules import (
EndpointRestrictionLanguageModel, EndpointRestrictionLanguageModel,
) )
from Services.PostgresDb import CrudCollection from Services.PostgresService.controllers.mixin_controllers import CrudCollection
class EndpointRestriction(CrudCollection): class EndpointRestriction(CrudCollection):

View File

@ -5,6 +5,7 @@ description = "Add your description here"
readme = "README.md" readme = "README.md"
requires-python = ">=3.12" requires-python = ">=3.12"
dependencies = [ dependencies = [
"arrow>=1.3.0",
"cryptography>=44.0.2", "cryptography>=44.0.2",
"fastapi>=0.115.11", "fastapi>=0.115.11",
"prometheus-fastapi-instrumentator>=7.1.0", "prometheus-fastapi-instrumentator>=7.1.0",

View File

@ -41,24 +41,26 @@ def parse_excel_file(excel_frame: DataFrame) -> list[dict]:
iban = str(row[5]).replace(" ", "") iban = str(row[5]).replace(" ", "")
if not str(row[1]) == "nan" and not str(row[2]) == "nan": if not str(row[1]) == "nan" and not str(row[2]) == "nan":
if len(str(row[1]).split("/")) > 2: if len(str(row[1]).split("/")) > 2:
data_list.append(dict( data_list.append(
iban=str(iban), dict(
bank_date=arrow.get( iban=str(iban),
datetime.datetime.strptime(str(row[1]), "%d/%m/%Y-%H:%M:%S") bank_date=arrow.get(
).__str__(), datetime.datetime.strptime(str(row[1]), "%d/%m/%Y-%H:%M:%S")
channel_branch=unidecode(str(row[3])), ).__str__(),
currency_value=( channel_branch=unidecode(str(row[3])),
float(str(row[4]).replace(",", "")) if row[4] else 0 currency_value=(
), float(str(row[4]).replace(",", "")) if row[4] else 0
balance=float(str(row[5]).replace(",", "")) if row[5] else 0, ),
additional_balance=( balance=float(str(row[5]).replace(",", "")) if row[5] else 0,
float(str(row[6]).replace(",", "")) if row[6] else 0 additional_balance=(
), float(str(row[6]).replace(",", "")) if row[6] else 0
process_name=str(row[7]), ),
process_type=unidecode(str(row[8])), process_name=str(row[7]),
process_comment=unidecode(str(row[9])), process_type=unidecode(str(row[8])),
bank_reference_code=str(row[15]), process_comment=unidecode(str(row[9])),
)) bank_reference_code=str(row[15]),
)
)
return data_list return data_list

View File

@ -43,36 +43,39 @@ def set_account_records_to_send_email():
""" """
from app import set_account_records_to_send_email from app import set_account_records_to_send_email
""" """
db_session = AccountRecords.new_session()
account_records = AccountRecords.filter_all(db=db_session).core_query
account_records = (
account_records.order_by(
AccountRecords.bank_date.desc(), AccountRecords.bank_reference_code.desc()
)
.limit(3)
.all()
)
with AccountRecords.new_session() as db_session: first_record, second_record, balance_error = (
account_records = AccountRecords.filter_all(db=db_session).core_query account_records[0],
account_records = ( account_records[1],
account_records.order_by( False,
AccountRecords.bank_date.desc(), AccountRecords.bank_reference_code.desc() )
).limit(3).all() second_balance = first_record.bank_balance - first_record.currency_value
if second_balance != second_record.bank_balance:
balance_error = True
list_of_rows = list()
for record in account_records:
list_of_rows.append(
[record.bank_date, record.process_comment, f"{record.currency_value:.4f}"]
) )
first_record, second_record, balance_error = ( send_to = "karatay@mehmetkaratay.com.tr"
account_records[0], account_records[1], False html_template = render_email_template(
) headers=["Ulaştığı Tarih", "Banka Transaksiyonu Ek Bilgi", "Aktarım Değeri"],
second_balance = first_record.bank_balance - first_record.currency_value rows=list_of_rows,
if second_balance != second_record.bank_balance: balance_error=balance_error,
balance_error = True bank_balance=account_records[0].bank_balance,
)
list_of_rows = list() send_email_to_given_address(send_to=send_to, html_template=html_template)
for record in account_records:
list_of_rows.append(
[record.bank_date, record.process_comment, f"{record.currency_value:.4f}"]
)
send_to = "karatay@mehmetkaratay.com.tr"
html_template = render_email_template(
headers=["Ulaştığı Tarih", "Banka Transaksiyonu Ek Bilgi", "Aktarım Değeri"],
rows=list_of_rows,
balance_error=balance_error,
bank_balance=account_records[0].bank_balance,
)
send_email_to_given_address(send_to=send_to, html_template=html_template)
if __name__ == "__main__": if __name__ == "__main__":

View File

@ -86,6 +86,7 @@ if __name__ == "__main__":
results = check_any_written_stage_in_mongo_database(mongo_provider=provider) results = check_any_written_stage_in_mongo_database(mongo_provider=provider)
for result in results: for result in results:
send_email_and_update_mongo_database( send_email_and_update_mongo_database(
mongo_provider=provider, email_data=result, mongo_provider=provider,
email_data=result,
) )
time.sleep(60) time.sleep(60)

View File

@ -1,5 +1,3 @@
def main(): def main():
print("Hello from seperatorservice!") print("Hello from seperatorservice!")

View File

@ -1,9 +1,9 @@
import time import time
import arrow import arrow
from model import BankReceive
from Schemas import AccountRecords, BuildIbans from Schemas import AccountRecords, BuildIbans
from Services.MongoService.provider import MongoProvider from Services.MongoService.provider import MongoProvider
from model import BankReceive
from Configs.mongo import MongoConfig from Configs.mongo import MongoConfig
@ -46,7 +46,9 @@ def write_parsed_data_to_account_records(
).data: ).data:
print("already @database record", found_record.id) print("already @database record", found_record.id)
else: else:
new_account_record = AccountRecords.find_or_create(db=db_session, **data_dict) new_account_record = AccountRecords.find_or_create(
db=db_session, **data_dict
)
new_account_record.is_confirmed = True new_account_record.is_confirmed = True
new_account_record.save(db=db_session) new_account_record.save(db=db_session)
mongo_provider.update_one( mongo_provider.update_one(

View File

@ -1,4 +1,6 @@
from typing import Any, Union import arrow
from typing import Any
from fastapi import Request from fastapi import Request
from ApiLayers.ApiLibrary.common.line_number import get_line_number_for_error from ApiLayers.ApiLibrary.common.line_number import get_line_number_for_error
@ -10,6 +12,7 @@ from ApiLayers.ApiValidations.Response.default_response import (
EndpointNotAcceptableResponse, EndpointNotAcceptableResponse,
EndpointBadRequestResponse, EndpointBadRequestResponse,
) )
from ApiLayers.AllConfigs.Redis.configs import RedisAuthKeys
from ApiLayers.ErrorHandlers import HTTPExceptionApi from ApiLayers.ErrorHandlers import HTTPExceptionApi
from ApiLayers.Schemas import ( from ApiLayers.Schemas import (
BuildLivingSpace, BuildLivingSpace,
@ -27,9 +30,9 @@ from ApiLayers.Schemas import (
Users, Users,
UsersTokens, UsersTokens,
) )
from Events.base_request_model import TokenDictType, BaseRouteModel from Events.base_request_model import TokenDictType, BaseRouteModel
from Services.Redis.Actions.actions import RedisActions from Services.RedisService.Actions.actions import RedisActions
from ApiLayers.AllConfigs.Redis.configs import RedisAuthKeys
class Handlers: class Handlers:
@ -39,178 +42,180 @@ class Handlers:
def handle_employee_selection( def handle_employee_selection(
cls, request: Request, data: Any, token_dict: TokenDictType cls, request: Request, data: Any, token_dict: TokenDictType
): ):
db = Users.new_session() with Users.new_session() as db:
if data.company_uu_id not in token_dict.companies_uu_id_list: if data.company_uu_id not in token_dict.companies_uu_id_list:
raise HTTPExceptionApi( raise HTTPExceptionApi(
error_code="HTTP_400_BAD_REQUEST", error_code="HTTP_400_BAD_REQUEST",
lang=token_dict.lang, lang=token_dict.lang,
loc=get_line_number_for_error(), loc=get_line_number_for_error(),
sys_msg="Company not found in token", sys_msg="Company not found in token",
) )
selected_company: Companies = Companies.filter_one( selected_company: Companies = Companies.filter_one(
Companies.uu_id == data.company_uu_id, db=db Companies.uu_id == data.company_uu_id, db=db
).data
if not selected_company:
raise HTTPExceptionApi(
error_code="HTTP_400_BAD_REQUEST",
lang=token_dict.lang,
loc=get_line_number_for_error(),
sys_msg="Company not found in token",
)
# Get duties IDs for the company
duties_ids = [
duty.id
for duty in Duties.filter_all(
Duties.company_id == selected_company.id, db=db
).data ).data
] if not selected_company:
raise HTTPExceptionApi(
error_code="HTTP_400_BAD_REQUEST",
lang=token_dict.lang,
loc=get_line_number_for_error(),
sys_msg="Company not found in token",
)
# Get staff IDs # Get duties IDs for the company
staff_ids = [ duties_ids = [
staff.id duty.id
for staff in Staff.filter_all(Staff.duties_id.in_(duties_ids), db=db).data for duty in Duties.filter_all(
] Duties.company_id == selected_company.id, db=db
).data
]
# Get employee # Get staff IDs
employee: Employees = Employees.filter_one( staff_ids = [
Employees.people_id == token_dict.person_id, staff.id
Employees.staff_id.in_(staff_ids), for staff in Staff.filter_all(Staff.duties_id.in_(duties_ids), db=db).data
db=db, ]
).data
if not employee: # Get employee
raise HTTPExceptionApi( employee: Employees = Employees.filter_one(
error_code="HTTP_400_BAD_REQUEST", Employees.people_id == token_dict.person_id,
lang=token_dict.lang, Employees.staff_id.in_(staff_ids),
loc=get_line_number_for_error(), db=db,
sys_msg="Employee not found in token", ).data
if not employee:
raise HTTPExceptionApi(
error_code="HTTP_400_BAD_REQUEST",
lang=token_dict.lang,
loc=get_line_number_for_error(),
sys_msg="Employee not found in token",
)
# Get reachable events
reachable_event_codes = Event2Employee.get_event_codes(
employee_id=employee.id, db_session=db
) )
# Get reachable events # Get staff and duties
reachable_event_codes = Event2Employee.get_event_codes(employee_id=employee.id) staff = Staff.filter_one(Staff.id == employee.staff_id, db=db).data
duties = Duties.filter_one(Duties.id == staff.duties_id, db=db).data
department = Departments.filter_one(
Departments.id == duties.department_id, db=db
).data
# Get staff and duties # Get bulk duty
staff = Staff.filter_one(Staff.id == employee.staff_id, db=db).data bulk_id = Duty.filter_by_one(system=True, duty_code="BULK", db=db).data
duties = Duties.filter_one(Duties.id == staff.duties_id, db=db).data bulk_duty_id = Duties.filter_by_one(
department = Departments.filter_one( company_id=selected_company.id,
Departments.id == duties.department_id, db=db duties_id=bulk_id.id,
).data db=db,
).data
# Get bulk duty # Create company token
bulk_id = Duty.filter_by_one(system=True, duty_code="BULK", db=db).data company_token = CompanyToken(
bulk_duty_id = Duties.filter_by_one( company_uu_id=selected_company.uu_id.__str__(),
company_id=selected_company.id, company_id=selected_company.id,
duties_id=bulk_id.id, department_id=department.id,
db=db, department_uu_id=department.uu_id.__str__(),
).data duty_id=duties.id,
duty_uu_id=duties.uu_id.__str__(),
# Create company token bulk_duties_id=bulk_duty_id.id,
company_token = CompanyToken( staff_id=staff.id,
company_uu_id=selected_company.uu_id.__str__(), staff_uu_id=staff.uu_id.__str__(),
company_id=selected_company.id, employee_id=employee.id,
department_id=department.id, employee_uu_id=employee.uu_id.__str__(),
department_uu_id=department.uu_id.__str__(), reachable_event_codes=reachable_event_codes,
duty_id=duties.id,
duty_uu_id=duties.uu_id.__str__(),
bulk_duties_id=bulk_duty_id.id,
staff_id=staff.id,
staff_uu_id=staff.uu_id.__str__(),
employee_id=employee.id,
employee_uu_id=employee.uu_id.__str__(),
reachable_event_codes=reachable_event_codes,
)
try: # Update Redis
return TokenService.update_token_at_redis(
request=request, add_payload=company_token
)
except Exception as e:
raise HTTPExceptionApi(
error_code="",
lang="en",
loc=get_line_number_for_error(),
sys_msg=f"{e}",
) )
try: # Update Redis
return TokenService.update_token_at_redis(
request=request, add_payload=company_token
)
except Exception as e:
raise HTTPExceptionApi(
error_code="",
lang="en",
loc=get_line_number_for_error(),
sys_msg=f"{e}",
)
@classmethod # Requires no auth context @classmethod # Requires no auth context
def handle_occupant_selection( def handle_occupant_selection(
cls, request: Request, data: Any, token_dict: TokenDictType cls, request: Request, data: Any, token_dict: TokenDictType
): ):
"""Handle occupant type selection""" """Handle occupant type selection"""
db = BuildLivingSpace.new_session() with BuildLivingSpace.new_session() as db:
# Get selected occupant type # Get selected occupant type
selected_build_living_space: BuildLivingSpace = BuildLivingSpace.filter_one( selected_build_living_space: BuildLivingSpace = BuildLivingSpace.filter_one(
BuildLivingSpace.uu_id == data.build_living_space_uu_id, BuildLivingSpace.uu_id == data.build_living_space_uu_id,
db=db, db=db,
).data ).data
if not selected_build_living_space: if not selected_build_living_space:
raise HTTPExceptionApi( raise HTTPExceptionApi(
error_code="HTTP_400_BAD_REQUEST", error_code="HTTP_400_BAD_REQUEST",
lang=token_dict.lang, lang=token_dict.lang,
loc=get_line_number_for_error(), loc=get_line_number_for_error(),
sys_msg="Selected occupant type not found", sys_msg="Selected occupant type not found",
)
# Get reachable events
reachable_event_codes = Event2Occupant.get_event_codes(
build_living_space_id=selected_build_living_space.id, db_session=db
)
occupant_type = OccupantTypes.filter_one_system(
OccupantTypes.id == selected_build_living_space.occupant_type_id,
db=db,
).data
build_part = BuildParts.filter_one(
BuildParts.id == selected_build_living_space.build_parts_id,
db=db,
).data
build = BuildParts.filter_one(
BuildParts.id == build_part.build_id,
db=db,
).data
responsible_employee = Employees.filter_one(
Employees.id == build_part.responsible_employee_id,
db=db,
).data
related_company = RelationshipEmployee2Build.filter_one(
RelationshipEmployee2Build.member_id == build.id,
db=db,
).data
# Get company
company_related = Companies.filter_one(
Companies.id == related_company.company_id,
db=db,
).data
# Create occupant token
occupant_token = OccupantToken(
living_space_id=selected_build_living_space.id,
living_space_uu_id=selected_build_living_space.uu_id.__str__(),
occupant_type_id=occupant_type.id,
occupant_type_uu_id=occupant_type.uu_id.__str__(),
occupant_type=occupant_type.occupant_type,
build_id=build.id,
build_uuid=build.uu_id.__str__(),
build_part_id=build_part.id,
build_part_uuid=build_part.uu_id.__str__(),
responsible_employee_id=responsible_employee.id,
responsible_employee_uuid=responsible_employee.uu_id.__str__(),
responsible_company_id=company_related.id,
responsible_company_uuid=company_related.uu_id.__str__(),
reachable_event_codes=reachable_event_codes,
) )
# Get reachable events try: # Update Redis
reachable_event_codes = Event2Occupant.get_event_codes( return TokenService.update_token_at_redis(
build_living_space_id=selected_build_living_space.id request=request, add_payload=occupant_token
) )
occupant_type = OccupantTypes.filter_one_system( except Exception as e:
OccupantTypes.id == selected_build_living_space.occupant_type_id, raise HTTPExceptionApi(
db=db, error_code="",
).data lang="en",
build_part = BuildParts.filter_one( loc=get_line_number_for_error(),
BuildParts.id == selected_build_living_space.build_parts_id, sys_msg=f"{e}",
db=db, )
).data
build = BuildParts.filter_one(
BuildParts.id == build_part.build_id,
db=db,
).data
responsible_employee = Employees.filter_one(
Employees.id == build_part.responsible_employee_id,
db=db,
).data
related_company = RelationshipEmployee2Build.filter_one(
RelationshipEmployee2Build.member_id == build.id,
db=db,
).data
# Get company
company_related = Companies.filter_one(
Companies.id == related_company.company_id,
db=db,
).data
# Create occupant token
occupant_token = OccupantToken(
living_space_id=selected_build_living_space.id,
living_space_uu_id=selected_build_living_space.uu_id.__str__(),
occupant_type_id=occupant_type.id,
occupant_type_uu_id=occupant_type.uu_id.__str__(),
occupant_type=occupant_type.occupant_type,
build_id=build.id,
build_uuid=build.uu_id.__str__(),
build_part_id=build_part.id,
build_part_uuid=build_part.uu_id.__str__(),
responsible_employee_id=responsible_employee.id,
responsible_employee_uuid=responsible_employee.uu_id.__str__(),
responsible_company_id=company_related.id,
responsible_company_uuid=company_related.uu_id.__str__(),
reachable_event_codes=reachable_event_codes,
)
try: # Update Redis
return TokenService.update_token_at_redis(
request=request, add_payload=occupant_token
)
except Exception as e:
raise HTTPExceptionApi(
error_code="",
lang="en",
loc=get_line_number_for_error(),
sys_msg=f"{e}",
)
class AuthenticationFunctions(BaseRouteModel): class AuthenticationFunctions(BaseRouteModel):
@ -298,106 +303,109 @@ class AuthenticationFunctions(BaseRouteModel):
def authentication_access_token_user_info(cls): def authentication_access_token_user_info(cls):
"""Refresh user info using access token""" """Refresh user info using access token"""
if cls.context_retriever.token: if cls.context_retriever.token:
db = Users.new_session() with Users.new_session() as db:
if found_user := Users.filter_one( if found_user := Users.filter_one(
Users.id == cls.context_retriever.token.user_id, db=db Users.id == cls.context_retriever.token.user_id, db=db
).data: ).data:
return EndpointSuccessResponse( return EndpointSuccessResponse(
code="USER_INFO_REFRESHED", lang=cls.context_retriever.token.lang code="USER_INFO_REFRESHED", lang=cls.context_retriever.token.lang
).as_dict( ).as_dict(
{ {
"access_token": cls.context_retriever.get_token, "access_token": cls.context_retriever.get_token,
"user": found_user.get_dict(), "user": found_user.get_dict(),
} }
) )
if not found_user: if not found_user:
return EndpointNotAcceptableResponse( return EndpointNotAcceptableResponse(
code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang
).as_dict(data={}) ).as_dict(data={})
@classmethod # Requires no auth context @classmethod # Requires no auth context
def authentication_change_password(cls, data: Any): def authentication_change_password(cls, data: Any):
"""Change password with access token""" """Change password with access token"""
if cls.context_retriever.token: if cls.context_retriever.token:
db = Users.new_session() with Users.new_session() as db:
if found_user := Users.filter_one( if found_user := Users.filter_one(
Users.id == cls.context_retriever.token.user_id, db=db Users.id == cls.context_retriever.token.user_id, db=db
).data: ).data:
found_user.set_password(data.new_password) found_user.set_password(data.new_password)
return EndpointSuccessResponse( return EndpointSuccessResponse(
code="PASSWORD_CHANGED", lang=cls.context_retriever.token.lang code="PASSWORD_CHANGED", lang=cls.context_retriever.token.lang
).as_dict(data={"user": found_user.get_dict()}) ).as_dict(data={"user": found_user.get_dict()})
if not found_user: if not found_user:
return EndpointNotAcceptableResponse( return EndpointNotAcceptableResponse(
code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang
).as_dict(data={}) ).as_dict(data={})
@classmethod # Requires not auth context @classmethod # Requires not auth context
def authentication_create_password(cls, data: Any): def authentication_create_password(cls, data: Any):
"""Create password with password reset token requested via email""" """Create password with password reset token requested via email"""
db = Users.new_session()
if not data.re_password == data.password: with Users.new_session() as db:
return EndpointNotAcceptableResponse( if not data.re_password == data.password:
code="PASSWORD_NOT_MATCH", lang=cls.context_retriever.token.lang return EndpointNotAcceptableResponse(
).as_dict(data={"password": data.password, "re_password": data.re_password}) code="PASSWORD_NOT_MATCH", lang=cls.context_retriever.token.lang
if found_user := Users.filter_one( ).as_dict(data={"password": data.password, "re_password": data.re_password})
Users.password_token == data.password_token, db=db if found_user := Users.filter_one(
).data: Users.password_token == data.password_token, db=db
found_user.create_password(found_user=found_user, password=data.password) ).data:
found_user.password_token = "" found_user.create_password(found_user=found_user, password=data.password)
found_user.save() found_user.password_token = ""
return EndpointSuccessResponse( found_user.save()
code="CREATED_PASSWORD", lang=cls.context_retriever.token.lang return EndpointSuccessResponse(
).as_dict(data={"user": found_user.get_dict()}) code="CREATED_PASSWORD", lang=cls.context_retriever.token.lang
).as_dict(data={"user": found_user.get_dict()})
@classmethod # Requires auth context @classmethod # Requires auth context
def authentication_disconnect_user(cls): def authentication_disconnect_user(cls):
"""Disconnect all sessions of user in access token""" """Disconnect all sessions of user in access token"""
db = Users.new_session() with Users.new_session() as db:
found_user = Users.filter_one_system( found_user = Users.filter_one_system(
Users.id == cls.context_retriever.token.user_id, db=db Users.id == cls.context_retriever.token.user_id, db=db
).data ).data
if not found_user: if not found_user:
return EndpointNotAcceptableResponse( return EndpointNotAcceptableResponse(
code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang
).as_dict(data={}) ).as_dict(data={})
registered_tokens = UsersTokens.filter_all( registered_tokens = UsersTokens.filter_all(
UsersTokens.user_id == cls.context_retriever.token.user_id, db=db UsersTokens.user_id == cls.context_retriever.token.user_id, db=db
) )
if registered_tokens.count: if registered_tokens.count:
registered_tokens.query.delete() registered_tokens.query.delete()
UsersTokens.save(db=db) UsersTokens.save(db=db)
RedisActions.delete( RedisActions.delete(
list_keys=[f"{RedisAuthKeys.AUTH}:*:{str(found_user.uu_id)}"] list_keys=[f"{RedisAuthKeys.AUTH}:*:{str(found_user.uu_id)}"]
) )
return EndpointSuccessResponse( return EndpointSuccessResponse(
code="DISCONNECTED_USER", lang=cls.context_retriever.token.lang code="DISCONNECTED_USER", lang=cls.context_retriever.token.lang
).as_dict(data={"user": found_user.get_dict()}) ).as_dict(data={"user": found_user.get_dict()})
@classmethod # Requires auth context @classmethod # Requires auth context
def authentication_logout_user(cls, data: Any): def authentication_logout_user(cls, data: Any):
"""Logout only single session of user which domain is provided""" """Logout only single session of user which domain is provided"""
db = Users.new_session() with Users.new_session() as db:
found_user = Users.filter_one_system( found_user = Users.filter_one_system(
Users.id == cls.context_retriever.token.user_id, db=db Users.id == cls.context_retriever.token.user_id, db=db
).data ).data
if not found_user: if not found_user:
return EndpointNotAcceptableResponse( return EndpointNotAcceptableResponse(
code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang
).as_dict(data={}) ).as_dict(data={})
registered_tokens = UsersTokens.filter_all_system( registered_tokens = UsersTokens.filter_all(
UsersTokens.user_id == cls.context_retriever.token.user_id, UsersTokens.user_id == cls.context_retriever.token.user_id,
UsersTokens.domain == cls.context_retriever.token.domain, UsersTokens.domain == cls.context_retriever.token.domain,
db=db, db=db,
) )
if registered_tokens.count: if registered_tokens.count:
registered_tokens.query.delete() registered_tokens.core_query.delete()
UsersTokens.save(db=db) UsersTokens.save(db=db)
TokenService.remove_token_with_domain(user=found_user, domain=data.domain) TokenService.remove_token_with_domain(
return EndpointSuccessResponse( user=found_user, domain=data.domain
code="LOGOUT_USER", lang=cls.context_retriever.token.lang )
).as_dict(data={"user": found_user.get_dict()}) return EndpointSuccessResponse(
code="LOGOUT_USER", lang=cls.context_retriever.token.lang
).as_dict(data={"user": found_user.get_dict()})
@classmethod # Requires not auth context @classmethod # Requires not auth context
def authentication_refresher_token(cls, request: Request, data: Any): def authentication_refresher_token(cls, request: Request, data: Any):
@ -410,89 +418,80 @@ class AuthenticationFunctions(BaseRouteModel):
} }
} }
""" """
import arrow
from ApiLayers.ApiServices.Token.token_handler import TokenService from ApiLayers.ApiServices.Token.token_handler import TokenService
db = UsersTokens.new_session() with UsersTokens.new_session() as db:
token_refresher: UsersTokens = UsersTokens.filter_by_one( token_refresher: UsersTokens = UsersTokens.filter_one(
token=data.refresh_token, UsersTokens.token==data.refresh_token,
domain=data.domain, UsersTokens.domain==data.domain,
db=db, db=db,
).data ).data
language = request.headers.get("evyos-language", "tr") language = request.headers.get("evyos-language", "tr")
if not token_refresher: if not token_refresher:
return EndpointNotAcceptableResponse( return EndpointNotAcceptableResponse(
code="REFRESHER_NOT_FOUND", lang=language code="REFRESHER_NOT_FOUND", lang=language
).as_dict(data={"refresh_token": data.refresh_token}) ).as_dict(data={"refresh_token": data.refresh_token})
if found_user := Users.filter_one( if found_user := Users.filter_one(
Users.id == token_refresher.user_id, db=db Users.id == token_refresher.user_id, db=db
).data: ).data:
token_created = TokenService.set_access_token_to_redis( token_created = TokenService.set_access_token_to_redis(
request=request, request=request, user=found_user, domain=data.domain, remember=True, db_session=db
user=found_user, )
domain=data.domain, found_user.last_agent = request.headers.get("User-Agent", None)
remember=True, found_user.last_platform = request.headers.get("Origin", None)
) found_user.last_remote_addr = getattr(request, "remote_addr", None
found_user.last_agent = request.headers.get("User-Agent", None) ) or request.headers.get("X-Forwarded-For", None)
found_user.last_platform = request.headers.get("Origin", None) found_user.last_seen = str(arrow.now())
found_user.last_remote_addr = getattr( response_data = {
request, "remote_addr", None "access_token": token_created.get("access_token"),
) or request.headers.get("X-Forwarded-For", None) "refresh_token": data.refresh_token,
found_user.last_seen = str(arrow.now()) }
response_data = { return EndpointSuccessResponse(code="TOKEN_REFRESH", lang=language).as_dict(
"access_token": token_created.get("access_token"), data=response_data
"refresh_token": data.refresh_token, )
} raise EndpointNotAcceptableResponse(
return EndpointSuccessResponse(code="TOKEN_REFRESH", lang=language).as_dict( code="USER_NOT_FOUND", lang=language
data=response_data ).as_dict(data={})
)
raise EndpointNotAcceptableResponse(
code="USER_NOT_FOUND", lang=language
).as_dict(data={})
@classmethod # Requires not auth context @classmethod # Requires not auth context
def authentication_forgot_password(cls, data: Any): def authentication_forgot_password(cls, data: Any):
"""Send an email to user for a valid password reset token""" """Send an email to user for a valid password reset token"""
import arrow
from ApiLayers.ApiServices.Token.token_handler import TokenService from ApiLayers.ApiServices.Token.token_handler import TokenService
from ApiLayers.AllConfigs.Templates.password_templates import ( from ApiLayers.AllConfigs.Templates.password_templates import change_your_password_template
change_your_password_template, from Services.EmailService.provider import email_sender
) from ApiLayers.AllConfigs.Api.config import ApiStatic
from Services.Email.send_email import email_sender
from config import ApiStatic with Users.new_session() as db:
# request = cls.context_retriever.request
db = Users.new_session() found_user: Users = Users.check_user_exits(
request = cls.context_retriever.request access_key=data.access_key, domain=data.domain
found_user: Users = Users.check_user_exits( )
access_key=data.access_key, domain=data.domain forgot_key = TokenService._create_access_token(access=False)
) forgot_link = ApiStatic.forgot_link(forgot_key=forgot_key)
forgot_key = TokenService._create_access_token(access=False) send_email_completed = email_sender.send_email(
forgot_link = ApiStatic.forgot_link(forgot_key=forgot_key) subject=f"Dear {found_user.user_tag}, your forgot password link has been sent.",
send_email_completed = email_sender.send_email( receivers=[str(found_user.email)],
subject=f"Dear {found_user.user_tag}, your forgot password link has been sent.", html=change_your_password_template(
receivers=[str(found_user.email)], user_name=found_user.user_tag, forgot_link=forgot_link
html=change_your_password_template( ),
user_name=found_user.user_tag, forgot_link=forgot_link )
), if not send_email_completed:
) return EndpointBadRequestResponse(
if not send_email_completed: code="EMAIL_NOT_SENT", lang=cls.context_retriever.token.lang
return EndpointBadRequestResponse( ).as_dict(data={"email": found_user.email})
code="EMAIL_NOT_SENT", lang=cls.context_retriever.token.lang found_user.password_token = forgot_key
).as_dict(data={"email": found_user.email}) found_user.password_token_is_valid = str(arrow.now().shift(days=1))
found_user.password_token = forgot_key found_user.save(db=db)
found_user.password_token_is_valid = str(arrow.now().shift(days=1)) return EndpointSuccessResponse(
found_user.save(db=db) code="FORGOT_PASSWORD", lang=cls.context_retriever.token.lang
return EndpointSuccessResponse( ).as_dict(
code="FORGOT_PASSWORD", lang=cls.context_retriever.token.lang data={
).as_dict( "user": found_user.get_dict(),
data={ "forgot_link": forgot_link,
"user": found_user.get_dict(), "token": forgot_key,
"forgot_link": forgot_link, }
"token": forgot_key, )
}
)
@classmethod # Requires not auth context @classmethod # Requires not auth context
def authentication_reset_password(cls, data: Any): def authentication_reset_password(cls, data: Any):
@ -502,28 +501,26 @@ class AuthenticationFunctions(BaseRouteModel):
@classmethod # Requires not auth context @classmethod # Requires not auth context
def authentication_download_avatar(cls): def authentication_download_avatar(cls):
"""Download avatar icon and profile info of user""" """Download avatar icon and profile info of user"""
import arrow with Users.new_session() as db:
if found_user := Users.filter_one(
db = Users.new_session() Users.id == cls.context_retriever.token.user_id, db=db
if found_user := Users.filter_one( ).data:
Users.id == cls.context_retriever.token.user_id, db=db expired_starts = str(arrow.now() - arrow.get(str(found_user.expiry_ends)))
).data: expired_int = (
expired_starts = str(arrow.now() - arrow.get(str(found_user.expiry_ends))) arrow.now().datetime - arrow.get(str(found_user.expiry_ends)).datetime
expired_int = ( )
arrow.now().datetime - arrow.get(str(found_user.expiry_ends)).datetime user_info = {
) "lang": cls.context_retriever.token.lang,
user_info = { "full_name": found_user.person.full_name,
"lang": cls.context_retriever.token.lang, "avatar": found_user.avatar,
"full_name": found_user.person.full_name, "remember_me": found_user.remember_me,
"avatar": found_user.avatar, "expiry_ends": str(found_user.expiry_ends),
"remember_me": found_user.remember_me, "expired_humanized": expired_starts,
"expiry_ends": str(found_user.expiry_ends), "expired_day": int(expired_int.days) * -1,
"expired_humanized": expired_starts, }
"expired_day": int(expired_int.days) * -1, return EndpointSuccessResponse(
} code="USER_AVATAR", lang=cls.context_retriever.token.lang
return EndpointSuccessResponse( ).as_dict(data=user_info)
code="USER_AVATAR", lang=cls.context_retriever.token.lang return EndpointNotAcceptableResponse(
).as_dict(data=user_info) code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang
return EndpointNotAcceptableResponse( ).as_dict(data={})
code="USER_NOT_FOUND", lang=cls.context_retriever.token.lang
).as_dict(data={})

View File

@ -24,7 +24,7 @@ from ApiLayers.Schemas import (
from ApiLayers.ApiValidations.Response import AccountRecordResponse from ApiLayers.ApiValidations.Response import AccountRecordResponse
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class AccountListEventMethods(BaseRouteModel): class AccountListEventMethods(BaseRouteModel):

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
from ApiLayers.Schemas import AddressNeighborhood from ApiLayers.Schemas import AddressNeighborhood

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -2,7 +2,7 @@ from typing import Union, Optional
from ApiLayers.ApiValidations.Request import ListOptions from ApiLayers.ApiValidations.Request import ListOptions
from Events.base_request_model import BaseRouteModel, ListOptionsBase from Events.base_request_model import BaseRouteModel, ListOptionsBase
from Services.PostgresDb.Models.pagination import PaginationResult from Services.PostgresService.controllers.pagination_controllers import PaginationResult
class Handlers: class Handlers:

View File

@ -3,19 +3,17 @@ Validation function handlers
""" """
from typing import Dict, Any, Optional from typing import Dict, Any, Optional
from fastapi import Request
from ApiLayers.AllConfigs.Redis.configs import ( from ApiLayers.AllConfigs.Redis.configs import (
RedisCategoryKeys, RedisCategoryKeys,
RedisValidationKeysAction, RedisValidationKeysAction,
RedisCategoryPageInfoKeysAction, RedisCategoryPageInfoKeysAction,
) )
from ApiLayers.ApiLibrary.common.line_number import get_line_number_for_error
from ApiLayers.ErrorHandlers.Exceptions.api_exc import HTTPExceptionApi from Services.RedisService.Actions.actions import RedisActions
from Services.Redis.Actions.actions import RedisActions
from Events.base_request_model import BaseRouteModel from Events.base_request_model import BaseRouteModel
from config import ValidationsConfig from ApiLayers.AllConfigs.Api.config import ValidationsConfig
class ValidateBase: class ValidateBase:

View File

@ -10,7 +10,10 @@ from Events.abstract_class import (
if TYPE_CHECKING: if TYPE_CHECKING:
from fastapi import Request, HTTPException, status, Body from fastapi import Request, HTTPException, status, Body
from ApiLayers.ApiValidations.Custom.token_objects import EmployeeTokenObject, OccupantTokenObject from ApiLayers.ApiValidations.Custom.token_objects import (
EmployeeTokenObject,
OccupantTokenObject,
)
# Type aliases for common types # Type aliases for common types

View File

@ -5,7 +5,7 @@ from pydantic import BaseModel
# from application.validations.request.list_options.list_options import ListOptions # from application.validations.request.list_options.list_options import ListOptions
from Services.PostgresService.controllers.response_controllers import PostgresResponse from Services.PostgresService.controllers.response_controllers import PostgresResponse
from Configs.api import ApiConfigs from ApiLayers.AllConfigs.Api.config import ApiConfigs
class ListOptions: ... class ListOptions: ...

View File

@ -2,7 +2,7 @@ from contextlib import contextmanager
from functools import lru_cache from functools import lru_cache
from typing import Generator from typing import Generator
from Configs.postgres import Database from ApiLayers.AllConfigs.SqlDatabase.configs import WagDatabase as Database
from sqlalchemy import create_engine from sqlalchemy import create_engine
from sqlalchemy.orm import declarative_base, sessionmaker, scoped_session, Session from sqlalchemy.orm import declarative_base, sessionmaker, scoped_session, Session

View File

@ -1,24 +1,24 @@
services: services:
mongo_service: # mongo_service:
container_name: mongo_service # container_name: mongo_service
# image: "bitnami/mongodb:latest" ## image: "bitnami/mongodb:latest"
image: "bitnami/mongodb:4.4.1-debian-10-r3" # image: "bitnami/mongodb:4.4.1-debian-10-r3"
networks: # networks:
- network_store_services # - network_store_services
environment: # environment:
- MONGODB_DISABLE_ENFORCE_AUTH=true # - MONGODB_DISABLE_ENFORCE_AUTH=true
- MONGODB_ROOT_PASSWORD=root # - MONGODB_ROOT_PASSWORD=root
- MONGODB_DATABASE=mongo_database # - MONGODB_DATABASE=mongo_database
- MONGODB_USERNAME=mongo_user # - MONGODB_USERNAME=mongo_user
- MONGODB_PASSWORD=mongo_password # - MONGODB_PASSWORD=mongo_password
- MONGO_INITDB_ROOT_USERNAME=mongo_user # - MONGO_INITDB_ROOT_USERNAME=mongo_user
- MONGO_INITDB_ROOT_PASSWORD=mongo_password # - MONGO_INITDB_ROOT_PASSWORD=mongo_password
- MONGO_INITDB_DATABASE=mongo_database # - MONGO_INITDB_DATABASE=mongo_database
volumes: # volumes:
- wag_commercial_mongodb_data:/bitnami/mongodb # - wag_commercial_mongodb_data:/bitnami/mongodb
ports: # ports:
- "11117:27017" # - "11117:27017"
# #
# commercial_memory_service: # commercial_memory_service:
@ -52,70 +52,70 @@ services:
# volumes: # volumes:
# - wag_postgres_commercial_data:/bitnami/postgresql # - wag_postgres_commercial_data:/bitnami/postgresql
email_service: # email_service:
container_name: email_service # container_name: email_service
restart: on-failure # restart: on-failure
build: # build:
context: . # context: .
dockerfile: BankServices/EmailService/Dockerfile # dockerfile: BankServices/EmailService/Dockerfile
networks: # networks:
- network_store_services # - network_store_services
depends_on: # depends_on:
- mongo_service # - mongo_service
env_file: # env_file:
- email.env # - email.env
#
parser_service: # parser_service:
container_name: parser_service # container_name: parser_service
restart: on-failure # restart: on-failure
build: # build:
context: . # context: .
dockerfile: BankServices/ParserService/Dockerfile # dockerfile: BankServices/ParserService/Dockerfile
networks: # networks:
- network_store_services # - network_store_services
depends_on: # depends_on:
- mongo_service # - mongo_service
env_file: # env_file:
- email.env # - email.env
#
writer_service: # writer_service:
container_name: writer_service # container_name: writer_service
restart: on-failure # restart: on-failure
build: # build:
context: . # context: .
dockerfile: BankServices/WriterService/Dockerfile # dockerfile: BankServices/WriterService/Dockerfile
networks: # networks:
- network_store_services # - network_store_services
depends_on: # depends_on:
- mongo_service # - mongo_service
env_file: # env_file:
- email.env # - email.env
#
routine_email_service: # routine_email_service:
container_name: routine_email_service # container_name: routine_email_service
restart: on-failure # restart: on-failure
build: # build:
context: . # context: .
dockerfile: BankServices/RoutineEmailService/Dockerfile # dockerfile: BankServices/RoutineEmailService/Dockerfile
networks: # networks:
- network_store_services # - network_store_services
depends_on: # depends_on:
- mongo_service # - mongo_service
env_file: # env_file:
- email.env # - email.env
#
sender_service: # sender_service:
container_name: sender_service # container_name: sender_service
restart: on-failure # restart: on-failure
build: # build:
context: . # context: .
dockerfile: BankServices/SenderService/Dockerfile # dockerfile: BankServices/SenderService/Dockerfile
networks: # networks:
- network_store_services # - network_store_services
depends_on: # depends_on:
- mongo_service # - mongo_service
env_file: # env_file:
- email.env # - email.env
# initservice: # initservice:
# container_name: initservice # container_name: initservice
@ -123,17 +123,17 @@ services:
# context: . # context: .
# dockerfile: ApiServices/InitServiceApi/Dockerfile # dockerfile: ApiServices/InitServiceApi/Dockerfile
# authservice: authservice:
# container_name: authservice container_name: authservice
# build: build:
# context: . context: .
# dockerfile: ApiServices/AuthApiService/Dockerfile dockerfile: ApiServices/AuthApiService/Dockerfile
# ports: ports:
# - "8081:8888" - "8081:8888"
# depends_on: # depends_on:
# - initservice # - initservice
# networks: networks:
# - wag-network - wag-network
# validationservice: # validationservice:
# container_name: validationservice # container_name: validationservice

31
uv.lock
View File

@ -67,38 +67,32 @@ name = "authapiservice"
version = "0.1.0" version = "0.1.0"
source = { virtual = "ApiServices/AuthApiService" } source = { virtual = "ApiServices/AuthApiService" }
dependencies = [ dependencies = [
{ name = "arrow" },
{ name = "cryptography" }, { name = "cryptography" },
{ name = "faker" },
{ name = "fastapi" }, { name = "fastapi" },
{ name = "pandas" },
{ name = "prometheus-fastapi-instrumentator" }, { name = "prometheus-fastapi-instrumentator" },
{ name = "psycopg2-binary" }, { name = "psycopg2-binary" },
{ name = "pymongo" }, { name = "pymongo" },
{ name = "redis" }, { name = "redis" },
{ name = "redmail" }, { name = "redmail" },
{ name = "requests" }, { name = "requests" },
{ name = "rsa" },
{ name = "sqlalchemy-mixins" }, { name = "sqlalchemy-mixins" },
{ name = "textdistance" },
{ name = "unidecode" }, { name = "unidecode" },
{ name = "uvicorn" }, { name = "uvicorn" },
] ]
[package.metadata] [package.metadata]
requires-dist = [ requires-dist = [
{ name = "arrow", specifier = ">=1.3.0" },
{ name = "cryptography", specifier = ">=44.0.2" }, { name = "cryptography", specifier = ">=44.0.2" },
{ name = "faker", specifier = ">=37.0.2" },
{ name = "fastapi", specifier = ">=0.115.11" }, { name = "fastapi", specifier = ">=0.115.11" },
{ name = "pandas", specifier = ">=2.2.3" },
{ name = "prometheus-fastapi-instrumentator", specifier = ">=7.1.0" }, { name = "prometheus-fastapi-instrumentator", specifier = ">=7.1.0" },
{ name = "psycopg2-binary", specifier = ">=2.9.10" }, { name = "psycopg2-binary", specifier = ">=2.9.10" },
{ name = "pymongo", specifier = ">=4.11.3" }, { name = "pymongo", specifier = ">=4.11.3" },
{ name = "redis", specifier = ">=5.2.1" }, { name = "redis", specifier = ">=5.2.1" },
{ name = "redmail", specifier = ">=0.6.0" }, { name = "redmail", specifier = ">=0.6.0" },
{ name = "requests", specifier = ">=2.32.3" }, { name = "requests", specifier = ">=2.32.3" },
{ name = "rsa", specifier = ">=4.9" },
{ name = "sqlalchemy-mixins", specifier = ">=2.0.5" }, { name = "sqlalchemy-mixins", specifier = ">=2.0.5" },
{ name = "textdistance", specifier = ">=4.6.3" },
{ name = "unidecode", specifier = ">=1.3.8" }, { name = "unidecode", specifier = ">=1.3.8" },
{ name = "uvicorn", specifier = ">=0.34.0" }, { name = "uvicorn", specifier = ">=0.34.0" },
] ]
@ -547,15 +541,6 @@ wheels = [
{ url = "https://files.pythonhosted.org/packages/08/50/d13ea0a054189ae1bc21af1d85b6f8bb9bbc5572991055d70ad9006fe2d6/psycopg2_binary-2.9.10-cp313-cp313-win_amd64.whl", hash = "sha256:27422aa5f11fbcd9b18da48373eb67081243662f9b46e6fd07c3eb46e4535142", size = 2569224 }, { url = "https://files.pythonhosted.org/packages/08/50/d13ea0a054189ae1bc21af1d85b6f8bb9bbc5572991055d70ad9006fe2d6/psycopg2_binary-2.9.10-cp313-cp313-win_amd64.whl", hash = "sha256:27422aa5f11fbcd9b18da48373eb67081243662f9b46e6fd07c3eb46e4535142", size = 2569224 },
] ]
[[package]]
name = "pyasn1"
version = "0.6.1"
source = { registry = "https://pypi.org/simple" }
sdist = { url = "https://files.pythonhosted.org/packages/ba/e9/01f1a64245b89f039897cb0130016d79f77d52669aae6ee7b159a6c4c018/pyasn1-0.6.1.tar.gz", hash = "sha256:6f580d2bdd84365380830acf45550f2511469f673cb4a5ae3857a3170128b034", size = 145322 }
wheels = [
{ url = "https://files.pythonhosted.org/packages/c8/f1/d6a797abb14f6283c0ddff96bbdd46937f64122b8c925cab503dd37f8214/pyasn1-0.6.1-py3-none-any.whl", hash = "sha256:0d632f46f2ba09143da3a8afe9e33fb6f92fa2320ab7e886e2d0f7672af84629", size = 83135 },
]
[[package]] [[package]]
name = "pycparser" name = "pycparser"
version = "2.22" version = "2.22"
@ -750,18 +735,6 @@ requires-dist = [
{ name = "sqlalchemy-mixins", specifier = ">=2.0.5" }, { name = "sqlalchemy-mixins", specifier = ">=2.0.5" },
] ]
[[package]]
name = "rsa"
version = "4.9"
source = { registry = "https://pypi.org/simple" }
dependencies = [
{ name = "pyasn1" },
]
sdist = { url = "https://files.pythonhosted.org/packages/aa/65/7d973b89c4d2351d7fb232c2e452547ddfa243e93131e7cfa766da627b52/rsa-4.9.tar.gz", hash = "sha256:e38464a49c6c85d7f1351b0126661487a7e0a14a50f1675ec50eb34d4f20ef21", size = 29711 }
wheels = [
{ url = "https://files.pythonhosted.org/packages/49/97/fa78e3d2f65c02c8e1268b9aba606569fe97f6c8f7c2d74394553347c145/rsa-4.9-py3-none-any.whl", hash = "sha256:90260d9058e514786967344d0ef75fa8727eed8a7d2e43ce9f4bcf1b536174f7", size = 34315 },
]
[[package]] [[package]]
name = "senderservice" name = "senderservice"
version = "0.1.0" version = "0.1.0"