Compare commits
35 Commits
35aab0ba11
...
developmen
| Author | SHA1 | Date | |
|---|---|---|---|
| 4d7a6e6ec0 | |||
| aee9d59750 | |||
| bc43471259 | |||
| e0ae1ee80a | |||
| dd707b2463 | |||
| 0cde34a9bc | |||
| 01f3e82a54 | |||
| ac8c3fe1c3 | |||
| c6b1a2b1e8 | |||
| 734dc59e38 | |||
| 71c808a5c3 | |||
| 1ce28ec5f0 | |||
| 1920c2a25d | |||
| e815251123 | |||
| 36e63960f8 | |||
| f2cc7a69b5 | |||
| 0052c92974 | |||
| 113e43c7d7 | |||
| 2d418644bb | |||
| ac344773c5 | |||
| 346b132f4c | |||
| 090567ade8 | |||
| ba784c40e4 | |||
| a886c2f28c | |||
| f4e43306c1 | |||
| c553975e82 | |||
| 0bdc0d287e | |||
| 7efd6f8941 | |||
| 9f0c42e57a | |||
| b9825bb8e8 | |||
| 0bd8ddce4d | |||
| 9511f81bc0 | |||
| e5f88f2eb4 | |||
| d7f1da8de8 | |||
| 9069ba0754 |
56
ApiControllers/abstracts/default_validations.py
Normal file
56
ApiControllers/abstracts/default_validations.py
Normal file
@@ -0,0 +1,56 @@
|
|||||||
|
from fastapi import Header, Request, Response
|
||||||
|
from pydantic import BaseModel
|
||||||
|
|
||||||
|
from ApiDefaults.config import api_config
|
||||||
|
|
||||||
|
|
||||||
|
class CommonHeaders(BaseModel):
|
||||||
|
language: str | None = None
|
||||||
|
domain: str | None = None
|
||||||
|
timezone: str | None = None
|
||||||
|
token: str | None = None
|
||||||
|
request: Request | None = None
|
||||||
|
response: Response | None = None
|
||||||
|
operation_id: str | None = None
|
||||||
|
|
||||||
|
model_config = {
|
||||||
|
"arbitrary_types_allowed": True
|
||||||
|
}
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def as_dependency(
|
||||||
|
cls,
|
||||||
|
request: Request,
|
||||||
|
response: Response,
|
||||||
|
language: str = Header(None, alias="language"),
|
||||||
|
domain: str = Header(None, alias="domain"),
|
||||||
|
tz: str = Header(None, alias="timezone"),
|
||||||
|
):
|
||||||
|
token = request.headers.get(api_config.ACCESS_TOKEN_TAG, None)
|
||||||
|
|
||||||
|
# Extract operation_id from the route
|
||||||
|
operation_id = None
|
||||||
|
if hasattr(request.scope.get("route"), "operation_id"):
|
||||||
|
operation_id = request.scope.get("route").operation_id
|
||||||
|
|
||||||
|
return cls(
|
||||||
|
language=language,
|
||||||
|
domain=domain,
|
||||||
|
timezone=tz,
|
||||||
|
token=token,
|
||||||
|
request=request,
|
||||||
|
response=response,
|
||||||
|
operation_id=operation_id,
|
||||||
|
)
|
||||||
|
|
||||||
|
def get_headers_dict(self):
|
||||||
|
"""Convert the headers to a dictionary format used in the application"""
|
||||||
|
import uuid
|
||||||
|
|
||||||
|
return {
|
||||||
|
"language": self.language or "",
|
||||||
|
"domain": self.domain or "",
|
||||||
|
"eys-ext": f"{str(uuid.uuid4())}",
|
||||||
|
"tz": self.timezone or "GMT+3",
|
||||||
|
"token": self.token,
|
||||||
|
}
|
||||||
133
ApiControllers/abstracts/event_clusters.py
Normal file
133
ApiControllers/abstracts/event_clusters.py
Normal file
@@ -0,0 +1,133 @@
|
|||||||
|
from typing import Optional, Type
|
||||||
|
from pydantic import BaseModel
|
||||||
|
|
||||||
|
|
||||||
|
class EventCluster:
|
||||||
|
"""
|
||||||
|
EventCluster
|
||||||
|
"""
|
||||||
|
def __repr__(self):
|
||||||
|
return f"EventCluster(name={self.name})"
|
||||||
|
|
||||||
|
def __init__(self, endpoint_uu_id: str, name: str):
|
||||||
|
self.endpoint_uu_id = endpoint_uu_id
|
||||||
|
self.name = name
|
||||||
|
self.events: list["Event"] = []
|
||||||
|
|
||||||
|
def add_event(self, event: "Event"):
|
||||||
|
"""
|
||||||
|
Add an event to the cluster
|
||||||
|
"""
|
||||||
|
if event.key not in [e.key for e in self.events]:
|
||||||
|
self.events.append(event)
|
||||||
|
|
||||||
|
def get_event(self, event_key: str):
|
||||||
|
"""
|
||||||
|
Get an event by its key
|
||||||
|
"""
|
||||||
|
|
||||||
|
for event in self.events:
|
||||||
|
if event.key == event_key:
|
||||||
|
return event
|
||||||
|
return None
|
||||||
|
|
||||||
|
def set_events_to_database(self):
|
||||||
|
from Schemas import Events, EndpointRestriction
|
||||||
|
|
||||||
|
with Events.new_session() as db_session:
|
||||||
|
if to_save_endpoint := EndpointRestriction.filter_one(
|
||||||
|
EndpointRestriction.operation_uu_id == self.endpoint_uu_id,
|
||||||
|
db=db_session,
|
||||||
|
).data:
|
||||||
|
for event in self.events:
|
||||||
|
event_dict_to_save = dict(
|
||||||
|
function_code=event.key,
|
||||||
|
function_class=event.name,
|
||||||
|
description=event.description,
|
||||||
|
endpoint_code=self.endpoint_uu_id,
|
||||||
|
endpoint_id=to_save_endpoint.id,
|
||||||
|
endpoint_uu_id=str(to_save_endpoint.uu_id),
|
||||||
|
is_confirmed=True,
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
event_found = Events.filter_one(
|
||||||
|
Events.function_code == event_dict_to_save["function_code"],
|
||||||
|
db=db_session,
|
||||||
|
).data
|
||||||
|
if event_found:
|
||||||
|
event_found.update(**event_dict_to_save)
|
||||||
|
event_found.save(db=db_session)
|
||||||
|
else:
|
||||||
|
event_to_save_database = Events.find_or_create(
|
||||||
|
**event_dict_to_save,
|
||||||
|
include_args=[
|
||||||
|
Events.function_code,
|
||||||
|
Events.function_class,
|
||||||
|
Events.endpoint_code,
|
||||||
|
Events.endpoint_uu_id,
|
||||||
|
]
|
||||||
|
)
|
||||||
|
if event_to_save_database.meta_data.created:
|
||||||
|
print(f"UUID: {event_to_save_database.uu_id} event is saved to {to_save_endpoint.uu_id}")
|
||||||
|
event_to_save_database.save(db=db_session)
|
||||||
|
|
||||||
|
def match_event(self, event_key: str) -> "Event":
|
||||||
|
"""
|
||||||
|
Match an event by its key
|
||||||
|
"""
|
||||||
|
if event := self.get_event(event_key=event_key):
|
||||||
|
return event
|
||||||
|
raise ValueError("Event key not found")
|
||||||
|
|
||||||
|
|
||||||
|
class Event:
|
||||||
|
|
||||||
|
def __init__(
|
||||||
|
self,
|
||||||
|
name: str,
|
||||||
|
key: str,
|
||||||
|
request_validator: Optional[Type[BaseModel]] = None,
|
||||||
|
response_validator: Optional[Type[BaseModel]] = None,
|
||||||
|
description: str = "",
|
||||||
|
):
|
||||||
|
self.name = name
|
||||||
|
self.key = key
|
||||||
|
self.request_validator = request_validator
|
||||||
|
self.response_validator = response_validator
|
||||||
|
self.description = description
|
||||||
|
|
||||||
|
def event_callable(self):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
print(self.name)
|
||||||
|
return {}
|
||||||
|
|
||||||
|
|
||||||
|
class RouterCluster:
|
||||||
|
"""
|
||||||
|
RouterCluster
|
||||||
|
"""
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
return f"RouterCluster(name={self.name})"
|
||||||
|
|
||||||
|
def __init__(self, name: str):
|
||||||
|
self.name = name
|
||||||
|
self.event_clusters: dict[str, EventCluster] = {}
|
||||||
|
|
||||||
|
def set_event_cluster(self, event_cluster: EventCluster):
|
||||||
|
"""
|
||||||
|
Add an event cluster to the set
|
||||||
|
"""
|
||||||
|
print("Setting event cluster:", event_cluster.name)
|
||||||
|
if event_cluster.name not in self.event_clusters:
|
||||||
|
self.event_clusters[event_cluster.name] = event_cluster
|
||||||
|
|
||||||
|
def get_event_cluster(self, event_cluster_name: str) -> EventCluster:
|
||||||
|
"""
|
||||||
|
Get an event cluster by its name
|
||||||
|
"""
|
||||||
|
if event_cluster_name not in self.event_clusters:
|
||||||
|
raise ValueError("Event cluster not found")
|
||||||
|
return self.event_clusters[event_cluster_name]
|
||||||
@@ -23,17 +23,24 @@ class RouteRegisterController:
|
|||||||
for route_method in [
|
for route_method in [
|
||||||
method.lower() for method in getattr(route, "methods")
|
method.lower() for method in getattr(route, "methods")
|
||||||
]:
|
]:
|
||||||
restriction = EndpointRestriction.find_or_create(
|
add_or_update_dict = dict(
|
||||||
endpoint_method=route_method,
|
endpoint_method=route_method,
|
||||||
endpoint_name=route_path,
|
endpoint_name=route_path,
|
||||||
endpoint_desc=route_summary.replace("_", " "),
|
endpoint_desc=route_summary.replace("_", " "),
|
||||||
endpoint_function=route_summary,
|
endpoint_function=route_summary,
|
||||||
operation_uu_id=operation_id, # UUID of the endpoint
|
operation_uu_id=operation_id,
|
||||||
is_confirmed=True,
|
is_confirmed=True,
|
||||||
db=db_session,
|
|
||||||
)
|
)
|
||||||
if restriction.meta_data.created:
|
endpoint_restriction_found = EndpointRestriction.filter_one_system(
|
||||||
restriction.save(db=db_session)
|
EndpointRestriction.operation_uu_id == operation_id, db=db_session,
|
||||||
|
).data
|
||||||
|
if endpoint_restriction_found:
|
||||||
|
endpoint_restriction_found.update(**add_or_update_dict, db=db_session)
|
||||||
|
endpoint_restriction_found.save(db=db_session)
|
||||||
|
else:
|
||||||
|
restriction = EndpointRestriction.find_or_create(**add_or_update_dict, db=db_session)
|
||||||
|
if restriction.meta_data.created:
|
||||||
|
restriction.save(db=db_session)
|
||||||
|
|
||||||
def register_routes(self):
|
def register_routes(self):
|
||||||
for router in self.router_list:
|
for router in self.router_list:
|
||||||
@@ -1,11 +1,11 @@
|
|||||||
from fastapi import Request, status
|
from fastapi import Request, status
|
||||||
from fastapi.responses import JSONResponse
|
from fastapi.responses import JSONResponse
|
||||||
from ApiServices.IdentityService.endpoints.routes import get_safe_endpoint_urls
|
from ApiDefaults.config import api_config
|
||||||
from ApiServices.IdentityService.config import api_config
|
|
||||||
|
from Endpoints.routes import get_safe_endpoint_urls
|
||||||
|
|
||||||
|
|
||||||
async def token_middleware(request: Request, call_next):
|
async def token_middleware(request: Request, call_next):
|
||||||
|
|
||||||
base_url = request.url.path
|
base_url = request.url.path
|
||||||
safe_endpoints = [_[0] for _ in get_safe_endpoint_urls()]
|
safe_endpoints = [_[0] for _ in get_safe_endpoint_urls()]
|
||||||
if base_url in safe_endpoints:
|
if base_url in safe_endpoints:
|
||||||
@@ -1,7 +1,7 @@
|
|||||||
import uvicorn
|
import uvicorn
|
||||||
|
|
||||||
from config import api_config
|
from ApiDefaults.config import api_config
|
||||||
from create_app import create_app
|
from ApiDefaults.create_app import create_app
|
||||||
|
|
||||||
# from prometheus_fastapi_instrumentator import Instrumentator
|
# from prometheus_fastapi_instrumentator import Instrumentator
|
||||||
|
|
||||||
@@ -22,7 +22,7 @@ class Configs(BaseSettings):
|
|||||||
EMAIL_HOST: str = ""
|
EMAIL_HOST: str = ""
|
||||||
DATETIME_FORMAT: str = ""
|
DATETIME_FORMAT: str = ""
|
||||||
FORGOT_LINK: str = ""
|
FORGOT_LINK: str = ""
|
||||||
ALLOW_ORIGINS: list = ["http://localhost:3000"]
|
ALLOW_ORIGINS: list = ["http://localhost:3000", "http://localhost:3001"]
|
||||||
VERSION: str = "0.1.001"
|
VERSION: str = "0.1.001"
|
||||||
DESCRIPTION: str = ""
|
DESCRIPTION: str = ""
|
||||||
|
|
||||||
@@ -1,24 +1,42 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import RouterCluster, EventCluster
|
||||||
from fastapi import FastAPI, Request
|
from fastapi import FastAPI, Request
|
||||||
from fastapi.middleware.cors import CORSMiddleware
|
from fastapi.middleware.cors import CORSMiddleware
|
||||||
from fastapi.responses import RedirectResponse
|
from fastapi.responses import RedirectResponse
|
||||||
|
|
||||||
from endpoints.routes import get_routes
|
cluster_is_set = False
|
||||||
from open_api_creator import create_openapi_schema
|
|
||||||
from middlewares.token_middleware import token_middleware
|
|
||||||
from initializer.create_route import RouteRegisterController
|
|
||||||
|
|
||||||
from config import api_config
|
|
||||||
|
|
||||||
|
|
||||||
def create_events_if_any_cluster_set():
|
def create_events_if_any_cluster_set():
|
||||||
import events
|
import Events
|
||||||
|
|
||||||
for event_str in events.__all__:
|
global cluster_is_set
|
||||||
if to_set_events := getattr(events, event_str, None):
|
if not Events.__all__ or cluster_is_set:
|
||||||
to_set_events.set_events_to_database()
|
return
|
||||||
|
|
||||||
|
router_cluster_stack: list[RouterCluster] = [
|
||||||
|
getattr(Events, e, None) for e in Events.__all__
|
||||||
|
]
|
||||||
|
for router_cluster in router_cluster_stack:
|
||||||
|
event_cluster_stack: list[EventCluster] = list(
|
||||||
|
router_cluster.event_clusters.values()
|
||||||
|
)
|
||||||
|
for event_cluster in event_cluster_stack:
|
||||||
|
try:
|
||||||
|
event_cluster.set_events_to_database()
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error creating event cluster: {e}")
|
||||||
|
|
||||||
|
cluster_is_set = True
|
||||||
|
|
||||||
|
|
||||||
def create_app():
|
def create_app():
|
||||||
|
from ApiDefaults.open_api_creator import create_openapi_schema
|
||||||
|
from ApiDefaults.config import api_config
|
||||||
|
|
||||||
|
from ApiControllers.middlewares.token_middleware import token_middleware
|
||||||
|
from ApiControllers.initializer.create_route import RouteRegisterController
|
||||||
|
|
||||||
|
from Endpoints.routes import get_routes
|
||||||
|
|
||||||
application = FastAPI(**api_config.api_info)
|
application = FastAPI(**api_config.api_info)
|
||||||
# application.mount(
|
# application.mount(
|
||||||
@@ -44,6 +62,7 @@ def create_app():
|
|||||||
|
|
||||||
route_register = RouteRegisterController(app=application, router_list=get_routes())
|
route_register = RouteRegisterController(app=application, router_list=get_routes())
|
||||||
application = route_register.register_routes()
|
application = route_register.register_routes()
|
||||||
|
|
||||||
create_events_if_any_cluster_set()
|
create_events_if_any_cluster_set()
|
||||||
application.openapi = lambda _=application: create_openapi_schema(_)
|
application.openapi = lambda _=application: create_openapi_schema(_)
|
||||||
return application
|
return application
|
||||||
@@ -3,8 +3,8 @@ from fastapi import FastAPI
|
|||||||
from fastapi.routing import APIRoute
|
from fastapi.routing import APIRoute
|
||||||
from fastapi.openapi.utils import get_openapi
|
from fastapi.openapi.utils import get_openapi
|
||||||
|
|
||||||
from config import api_config as template_api_config
|
from ApiDefaults.config import api_config as template_api_config
|
||||||
from endpoints.routes import get_safe_endpoint_urls
|
from Endpoints.routes import get_safe_endpoint_urls
|
||||||
|
|
||||||
|
|
||||||
class OpenAPISchemaCreator:
|
class OpenAPISchemaCreator:
|
||||||
@@ -22,7 +22,7 @@ class Configs(BaseSettings):
|
|||||||
EMAIL_HOST: str = ""
|
EMAIL_HOST: str = ""
|
||||||
DATETIME_FORMAT: str = ""
|
DATETIME_FORMAT: str = ""
|
||||||
FORGOT_LINK: str = ""
|
FORGOT_LINK: str = ""
|
||||||
ALLOW_ORIGINS: list = ["http://localhost:3000"]
|
ALLOW_ORIGINS: list = ["http://localhost:3000", "http://localhost:3001"]
|
||||||
VERSION: str = "0.1.001"
|
VERSION: str = "0.1.001"
|
||||||
DESCRIPTION: str = ""
|
DESCRIPTION: str = ""
|
||||||
|
|
||||||
|
|||||||
@@ -304,7 +304,9 @@ def authentication_token_check_post(
|
|||||||
status_code=status.HTTP_406_NOT_ACCEPTABLE,
|
status_code=status.HTTP_406_NOT_ACCEPTABLE,
|
||||||
headers=headers,
|
headers=headers,
|
||||||
)
|
)
|
||||||
if AuthHandlers.LoginHandler.authentication_check_token_valid(access_token=token):
|
if AuthHandlers.LoginHandler.authentication_check_token_valid(
|
||||||
|
domain=domain, access_token=token
|
||||||
|
):
|
||||||
return JSONResponse(
|
return JSONResponse(
|
||||||
content={"message": "MSG_0001"},
|
content={"message": "MSG_0001"},
|
||||||
status_code=status.HTTP_202_ACCEPTED,
|
status_code=status.HTTP_202_ACCEPTED,
|
||||||
@@ -438,7 +440,7 @@ def authentication_page_valid(
|
|||||||
summary="Lists all sites that are available for user",
|
summary="Lists all sites that are available for user",
|
||||||
description="Lists all sites that are available for user",
|
description="Lists all sites that are available for user",
|
||||||
)
|
)
|
||||||
def authentication_page_valid(
|
def authentication_get_all_sites_list(
|
||||||
request: Request,
|
request: Request,
|
||||||
language: str = Header(None, alias="language"),
|
language: str = Header(None, alias="language"),
|
||||||
domain: str = Header(None, alias="domain"),
|
domain: str = Header(None, alias="domain"),
|
||||||
|
|||||||
@@ -171,8 +171,20 @@ class LoginHandler:
|
|||||||
access_key=data.access_key, db_session=db_session
|
access_key=data.access_key, db_session=db_session
|
||||||
)
|
)
|
||||||
|
|
||||||
|
other_domains_list, main_domain = [], ""
|
||||||
|
with mongo_handler.collection(
|
||||||
|
f"{str(found_user.related_company)}*Domain"
|
||||||
|
) as collection:
|
||||||
|
result = collection.find_one({"user_uu_id": str(found_user.uu_id)})
|
||||||
|
if not result:
|
||||||
|
raise ValueError("EYS_00087")
|
||||||
|
other_domains_list = result.get("other_domains_list", [])
|
||||||
|
main_domain = result.get("main_domain", None)
|
||||||
|
if domain not in other_domains_list or not main_domain:
|
||||||
|
raise ValueError("EYS_00088")
|
||||||
|
|
||||||
if not user_handler.check_password_valid(
|
if not user_handler.check_password_valid(
|
||||||
domain=domain or "",
|
domain=main_domain,
|
||||||
id_=str(found_user.uu_id),
|
id_=str(found_user.uu_id),
|
||||||
password=data.password,
|
password=data.password,
|
||||||
password_hashed=found_user.hash_password,
|
password_hashed=found_user.hash_password,
|
||||||
@@ -233,6 +245,7 @@ class LoginHandler:
|
|||||||
person_id=found_user.person_id,
|
person_id=found_user.person_id,
|
||||||
person_uu_id=str(person.uu_id),
|
person_uu_id=str(person.uu_id),
|
||||||
request=dict(request.headers),
|
request=dict(request.headers),
|
||||||
|
domain_list=other_domains_list,
|
||||||
companies_uu_id_list=companies_uu_id_list,
|
companies_uu_id_list=companies_uu_id_list,
|
||||||
companies_id_list=companies_id_list,
|
companies_id_list=companies_id_list,
|
||||||
duty_uu_id_list=duty_uu_id_list,
|
duty_uu_id_list=duty_uu_id_list,
|
||||||
@@ -286,8 +299,20 @@ class LoginHandler:
|
|||||||
found_user = user_handler.check_user_exists(
|
found_user = user_handler.check_user_exists(
|
||||||
access_key=data.access_key, db_session=db_session
|
access_key=data.access_key, db_session=db_session
|
||||||
)
|
)
|
||||||
|
other_domains_list, main_domain = [], ""
|
||||||
|
with mongo_handler.collection(
|
||||||
|
f"{str(found_user.related_company)}*Domain"
|
||||||
|
) as collection:
|
||||||
|
result = collection.find_one({"user_uu_id": str(found_user.uu_id)})
|
||||||
|
if not result:
|
||||||
|
raise ValueError("EYS_00087")
|
||||||
|
other_domains_list = result.get("other_domains_list", [])
|
||||||
|
main_domain = result.get("main_domain", None)
|
||||||
|
if domain not in other_domains_list or not main_domain:
|
||||||
|
raise ValueError("EYS_00088")
|
||||||
|
|
||||||
if not user_handler.check_password_valid(
|
if not user_handler.check_password_valid(
|
||||||
domain=domain,
|
domain=main_domain,
|
||||||
id_=str(found_user.uu_id),
|
id_=str(found_user.uu_id),
|
||||||
password=data.password,
|
password=data.password,
|
||||||
password_hashed=found_user.hash_password,
|
password_hashed=found_user.hash_password,
|
||||||
@@ -343,6 +368,7 @@ class LoginHandler:
|
|||||||
user_id=found_user.id,
|
user_id=found_user.id,
|
||||||
person_id=person.id,
|
person_id=person.id,
|
||||||
person_uu_id=str(person.uu_id),
|
person_uu_id=str(person.uu_id),
|
||||||
|
domain_list=other_domains_list,
|
||||||
request=dict(request.headers),
|
request=dict(request.headers),
|
||||||
available_occupants=occupants_selection_dict,
|
available_occupants=occupants_selection_dict,
|
||||||
).model_dump()
|
).model_dump()
|
||||||
@@ -606,10 +632,17 @@ class LoginHandler:
|
|||||||
)
|
)
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def authentication_check_token_valid(cls, access_token: str) -> bool:
|
def authentication_check_token_valid(cls, domain, access_token: str) -> bool:
|
||||||
redis_handler = RedisHandlers()
|
redis_handler = RedisHandlers()
|
||||||
if redis_handler.get_object_from_redis(access_token=access_token):
|
if auth_token := redis_handler.get_object_from_redis(access_token=access_token):
|
||||||
return True
|
if auth_token.is_employee:
|
||||||
|
if domain not in auth_token.domain_list:
|
||||||
|
raise ValueError("EYS_00112")
|
||||||
|
return True
|
||||||
|
elif auth_token.is_occupant:
|
||||||
|
if domain not in auth_token.domain_list:
|
||||||
|
raise ValueError("EYS_00113")
|
||||||
|
return True
|
||||||
return False
|
return False
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -5,6 +5,7 @@ from ..config import api_config
|
|||||||
|
|
||||||
|
|
||||||
async def token_middleware(request: Request, call_next):
|
async def token_middleware(request: Request, call_next):
|
||||||
|
print("Token Middleware", dict(request.headers))
|
||||||
base_url = request.url.path
|
base_url = request.url.path
|
||||||
safe_endpoints = [_[0] for _ in get_safe_endpoint_urls()]
|
safe_endpoints = [_[0] for _ in get_safe_endpoint_urls()]
|
||||||
if base_url in safe_endpoints:
|
if base_url in safe_endpoints:
|
||||||
|
|||||||
@@ -35,6 +35,7 @@ class ApplicationToken(BaseModel):
|
|||||||
person_uu_id: str
|
person_uu_id: str
|
||||||
|
|
||||||
request: Optional[dict] = None # Request Info of Client
|
request: Optional[dict] = None # Request Info of Client
|
||||||
|
domain_list: Optional[list[str]] = None
|
||||||
expires_at: Optional[float] = None # Expiry timestamp
|
expires_at: Optional[float] = None # Expiry timestamp
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
29
ApiServices/BuildingService/Dockerfile
Normal file
29
ApiServices/BuildingService/Dockerfile
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
FROM python:3.12-slim
|
||||||
|
|
||||||
|
WORKDIR /
|
||||||
|
|
||||||
|
# Install system dependencies and Poetry
|
||||||
|
RUN apt-get update && apt-get install -y --no-install-recommends gcc && rm -rf /var/lib/apt/lists/* && pip install --no-cache-dir poetry
|
||||||
|
|
||||||
|
# Copy Poetry configuration
|
||||||
|
COPY /pyproject.toml ./pyproject.toml
|
||||||
|
|
||||||
|
# Configure Poetry and install dependencies with optimizations
|
||||||
|
RUN poetry config virtualenvs.create false && poetry install --no-interaction --no-ansi --no-root --only main \
|
||||||
|
&& pip cache purge && rm -rf ~/.cache/pypoetry
|
||||||
|
|
||||||
|
# Copy application code
|
||||||
|
COPY /ApiControllers /ApiControllers
|
||||||
|
COPY /ApiDefaults /ApiDefaults
|
||||||
|
COPY /Controllers /Controllers
|
||||||
|
COPY /Schemas /Schemas
|
||||||
|
|
||||||
|
COPY /ApiServices/BuildingService/Endpoints /ApiDefaults/Endpoints
|
||||||
|
COPY /ApiServices/BuildingService/Events /ApiDefaults/Events
|
||||||
|
COPY /ApiServices/BuildingService/Validations /ApiDefaults/Validations
|
||||||
|
|
||||||
|
# Set Python path to include app directory
|
||||||
|
ENV PYTHONPATH=/ PYTHONUNBUFFERED=1 PYTHONDONTWRITEBYTECODE=1
|
||||||
|
|
||||||
|
# Run the application using the configured uvicorn server
|
||||||
|
CMD ["poetry", "run", "python", "ApiDefaults/app.py"]
|
||||||
70
ApiServices/BuildingService/Endpoints/area/route.py
Normal file
70
ApiServices/BuildingService/Endpoints/area/route.py
Normal file
@@ -0,0 +1,70 @@
|
|||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly
|
||||||
|
from Events.area.cluster import BuildAreaRouterCluster
|
||||||
|
|
||||||
|
|
||||||
|
area_route = APIRouter(prefix="/building/area", tags=["Building Area"])
|
||||||
|
|
||||||
|
|
||||||
|
@area_route.post(
|
||||||
|
path="/list",
|
||||||
|
description="List building area endpoint",
|
||||||
|
operation_id="f2831efc-5493-448c-bcf6-4d52d744ba7e",
|
||||||
|
)
|
||||||
|
def area_list_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List building area endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildAreaRouterCluster.get_event_cluster("BuildAreaList")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@area_route.post(
|
||||||
|
path="/create",
|
||||||
|
description="Create building area endpoint",
|
||||||
|
operation_id="66e8b310-7a5d-41f4-977c-ee5f3b0603da",
|
||||||
|
)
|
||||||
|
def area_create_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Create building area endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildAreaRouterCluster.get_event_cluster("BuildAreaCreate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@area_route.post(
|
||||||
|
path="/update",
|
||||||
|
description="Update building area endpoint",
|
||||||
|
operation_id="d7769899-156d-49ff-85f4-06e3faa23e30",
|
||||||
|
)
|
||||||
|
def area_update_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Update building area endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildAreaRouterCluster.get_event_cluster("BuildAreaUpdate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
70
ApiServices/BuildingService/Endpoints/building/route.py
Normal file
70
ApiServices/BuildingService/Endpoints/building/route.py
Normal file
@@ -0,0 +1,70 @@
|
|||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly
|
||||||
|
from Events.building.cluster import BuildRouterCluster
|
||||||
|
|
||||||
|
|
||||||
|
building_route = APIRouter(prefix="/building", tags=["Building"])
|
||||||
|
|
||||||
|
|
||||||
|
@building_route.post(
|
||||||
|
path="/list",
|
||||||
|
description="List buildings endpoint",
|
||||||
|
operation_id="72003d1f-79cc-43c3-9150-3a94f318186e",
|
||||||
|
)
|
||||||
|
def building_list_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List buildings endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildRouterCluster.get_event_cluster("BuildList")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@building_route.post(
|
||||||
|
path="/create",
|
||||||
|
description="Create buildings endpoint",
|
||||||
|
operation_id="13b86c9c-702b-411f-acb9-9ff50ef86507",
|
||||||
|
)
|
||||||
|
def building_create_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Create buildings endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildRouterCluster.get_event_cluster("BuildCreate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@building_route.post(
|
||||||
|
path="/update",
|
||||||
|
description="Update buildings endpoint",
|
||||||
|
operation_id="b09fb6fd-a6c9-4c03-8637-9af0570a84e8",
|
||||||
|
)
|
||||||
|
def building_update_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Update buildings endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildRouterCluster.get_event_cluster("BuildUpdate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
29
ApiServices/BuildingService/Endpoints/routes.py
Normal file
29
ApiServices/BuildingService/Endpoints/routes.py
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
from fastapi import APIRouter
|
||||||
|
|
||||||
|
|
||||||
|
def get_routes() -> list[APIRouter]:
|
||||||
|
from .building.route import building_route
|
||||||
|
from .area.route import area_route
|
||||||
|
from .sites.route import sites_route
|
||||||
|
from .parts.route import parts_route
|
||||||
|
from .spaces.route import spaces_route
|
||||||
|
from .type.route import build_types_route
|
||||||
|
|
||||||
|
return [
|
||||||
|
building_route,
|
||||||
|
area_route,
|
||||||
|
sites_route,
|
||||||
|
parts_route,
|
||||||
|
spaces_route,
|
||||||
|
build_types_route,
|
||||||
|
]
|
||||||
|
|
||||||
|
|
||||||
|
def get_safe_endpoint_urls() -> list[tuple[str, str]]:
|
||||||
|
return [
|
||||||
|
("/", "GET"),
|
||||||
|
("/docs", "GET"),
|
||||||
|
("/redoc", "GET"),
|
||||||
|
("/openapi.json", "GET"),
|
||||||
|
("/metrics", "GET"),
|
||||||
|
]
|
||||||
70
ApiServices/BuildingService/Endpoints/sites/route.py
Normal file
70
ApiServices/BuildingService/Endpoints/sites/route.py
Normal file
@@ -0,0 +1,70 @@
|
|||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly
|
||||||
|
from Events.sites.cluster import BuildSitesRouterCluster
|
||||||
|
|
||||||
|
|
||||||
|
sites_route = APIRouter(prefix="/building/sites", tags=["Build Sites"])
|
||||||
|
|
||||||
|
|
||||||
|
@sites_route.post(
|
||||||
|
path="/list",
|
||||||
|
description="List build sites endpoint",
|
||||||
|
operation_id="b64a2479-4160-43bf-9676-cd762a48bf62",
|
||||||
|
)
|
||||||
|
def sites_list_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List build sites endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildSitesRouterCluster.get_event_cluster("BuildSitesList")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@sites_route.post(
|
||||||
|
path="/create",
|
||||||
|
description="Create build sites endpoint",
|
||||||
|
operation_id="e63dab4b-d446-430c-ac7d-0cb47a66390c",
|
||||||
|
)
|
||||||
|
def sites_create_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Create build sites endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildSitesRouterCluster.get_event_cluster("BuildSitesCreate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@sites_route.post(
|
||||||
|
path="/update",
|
||||||
|
description="Update build sites endpoint",
|
||||||
|
operation_id="34ec902c-5ebe-41f6-8294-dfe634d47d98",
|
||||||
|
)
|
||||||
|
def sites_update_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Update build sites endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildSitesRouterCluster.get_event_cluster("BuildSitesUpdate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
76
ApiServices/BuildingService/Endpoints/spaces/route.py
Normal file
76
ApiServices/BuildingService/Endpoints/spaces/route.py
Normal file
@@ -0,0 +1,76 @@
|
|||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly
|
||||||
|
from Events.spaces.cluster import BuildLivingSpaceRouterCluster
|
||||||
|
|
||||||
|
|
||||||
|
spaces_route = APIRouter(prefix="/building/spaces", tags=["Build Spaces"])
|
||||||
|
|
||||||
|
|
||||||
|
@spaces_route.post(
|
||||||
|
path="/list",
|
||||||
|
description="List build spaces endpoint",
|
||||||
|
operation_id="9d072fd3-d727-4f71-bf0c-fd74e25ba507",
|
||||||
|
)
|
||||||
|
def spaces_list_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List build spaces endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildLivingSpaceRouterCluster.get_event_cluster(
|
||||||
|
"BuildLivingSpaceList"
|
||||||
|
)
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@spaces_route.post(
|
||||||
|
path="/create",
|
||||||
|
description="Create build spaces endpoint",
|
||||||
|
operation_id="4520cfb7-ed45-44d2-a706-e2a8be777419",
|
||||||
|
)
|
||||||
|
def spaces_create_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Create build spaces endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildLivingSpaceRouterCluster.get_event_cluster(
|
||||||
|
"BuildLivingSpaceCreate"
|
||||||
|
)
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@spaces_route.post(
|
||||||
|
path="/update",
|
||||||
|
description="Update build spaces endpoint",
|
||||||
|
operation_id="d8c90f64-0a4c-4a7c-a685-0e1894cbe1c4",
|
||||||
|
)
|
||||||
|
def spaces_update_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Update build spaces endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildLivingSpaceRouterCluster.get_event_cluster(
|
||||||
|
"BuildLivingSpaceUpdate"
|
||||||
|
)
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
70
ApiServices/BuildingService/Endpoints/type/route.py
Normal file
70
ApiServices/BuildingService/Endpoints/type/route.py
Normal file
@@ -0,0 +1,70 @@
|
|||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly
|
||||||
|
from Events.type.cluster import BuildTypeRouterCluster
|
||||||
|
|
||||||
|
|
||||||
|
build_types_route = APIRouter(prefix="/building/types", tags=["Build Types"])
|
||||||
|
|
||||||
|
|
||||||
|
@build_types_route.post(
|
||||||
|
path="/list",
|
||||||
|
description="List build types endpoint",
|
||||||
|
operation_id="916d2e02-ee83-4099-ba02-63e2a3f83ec4",
|
||||||
|
)
|
||||||
|
def build_types_list_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List build types endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildTypeRouterCluster.get_event_cluster("BuildTypeList")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@build_types_route.post(
|
||||||
|
path="/create",
|
||||||
|
description="Create build types endpoint",
|
||||||
|
operation_id="ae7d9e5d-3933-4613-a686-c887d74b85b3",
|
||||||
|
)
|
||||||
|
def build_types_create_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Create build types endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildTypeRouterCluster.get_event_cluster("BuildTypeCreate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@build_types_route.post(
|
||||||
|
path="/update",
|
||||||
|
description="Update build types endpoint",
|
||||||
|
operation_id="0f304075-efb0-4f9d-a3b2-e60eeb4d9a87",
|
||||||
|
)
|
||||||
|
def build_types_update_route(
|
||||||
|
data: dict,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Update build types endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = BuildTypeRouterCluster.get_event_cluster("BuildTypeUpdate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
15
ApiServices/BuildingService/Events/__init__.py
Normal file
15
ApiServices/BuildingService/Events/__init__.py
Normal file
@@ -0,0 +1,15 @@
|
|||||||
|
from .building.cluster import BuildRouterCluster
|
||||||
|
from .area.cluster import BuildAreaRouterCluster
|
||||||
|
from .parts.cluster import BuildPartsRouterCluster
|
||||||
|
from .spaces.cluster import BuildLivingSpaceRouterCluster
|
||||||
|
from .type.cluster import BuildTypeRouterCluster
|
||||||
|
from .sites.cluster import BuildSitesRouterCluster
|
||||||
|
|
||||||
|
__all__ = [
|
||||||
|
"BuildRouterCluster",
|
||||||
|
"BuildAreaRouterCluster",
|
||||||
|
"BuildPartsRouterCluster",
|
||||||
|
"BuildLivingSpaceRouterCluster",
|
||||||
|
"BuildTypeRouterCluster",
|
||||||
|
"BuildSitesRouterCluster",
|
||||||
|
]
|
||||||
26
ApiServices/BuildingService/Events/area/cluster.py
Normal file
26
ApiServices/BuildingService/Events/area/cluster.py
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
BuildAreaListEvent,
|
||||||
|
BuildAreaCreateEvent,
|
||||||
|
BuildAreaUpdateEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
BuildAreaRouterCluster = RouterCluster(name="BuildAreaRouterCluster")
|
||||||
|
|
||||||
|
BuildAreaEventClusterList = EventCluster(
|
||||||
|
name="BuildAreaList", endpoint_uu_id="cc487a4f-9a45-4072-89c1-a1ad504c79ad"
|
||||||
|
)
|
||||||
|
BuildAreaEventClusterCreate = EventCluster(
|
||||||
|
name="BuildAreaCreate", endpoint_uu_id="bdd58d68-3a7c-4150-9f5b-e322db35b804"
|
||||||
|
)
|
||||||
|
BuildAreaEventClusterUpdate = EventCluster(
|
||||||
|
name="BuildAreaUpdate", endpoint_uu_id="cad0c4e2-36e3-4f80-9ad2-b06bf8cd8d1c"
|
||||||
|
)
|
||||||
|
|
||||||
|
BuildAreaEventClusterList.add_event(BuildAreaListEvent)
|
||||||
|
BuildAreaEventClusterCreate.add_event(BuildAreaCreateEvent)
|
||||||
|
BuildAreaEventClusterUpdate.add_event(BuildAreaUpdateEvent)
|
||||||
|
|
||||||
|
BuildAreaRouterCluster.set_event_cluster(BuildAreaEventClusterList)
|
||||||
|
BuildAreaRouterCluster.set_event_cluster(BuildAreaEventClusterCreate)
|
||||||
|
BuildAreaRouterCluster.set_event_cluster(BuildAreaEventClusterUpdate)
|
||||||
96
ApiServices/BuildingService/Events/area/supers_events.py
Normal file
96
ApiServices/BuildingService/Events/area/supers_events.py
Normal file
@@ -0,0 +1,96 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
|
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Schemas import BuildArea
|
||||||
|
|
||||||
|
|
||||||
|
# List endpoint
|
||||||
|
BuildAreaListEvent = Event(
|
||||||
|
name="build_area_list",
|
||||||
|
key="306e6e11-21da-4fbb-b3d6-3a5179ecfe71",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="List events of build area endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Create endpoint
|
||||||
|
BuildAreaCreateEvent = Event(
|
||||||
|
name="build_area_create",
|
||||||
|
key="aa173f0f-7a97-4e91-97da-173626dd3257",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Create events of build area endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Update endpoint
|
||||||
|
BuildAreaUpdateEvent = Event(
|
||||||
|
name="build_area_update",
|
||||||
|
key="358404d0-fb80-4d58-8907-0c04948b364e",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Update events of build area endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def build_area_list_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
with BuildArea.new_session() as db_session:
|
||||||
|
if list_options.query:
|
||||||
|
buildings_list = BuildArea.filter_all(
|
||||||
|
*BuildArea.convert(list_options.query), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
buildings_list = BuildArea.filter_all(db=db_session)
|
||||||
|
pagination = Pagination(data=buildings_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(
|
||||||
|
data=buildings_list,
|
||||||
|
pagination=pagination,
|
||||||
|
# response_model="",
|
||||||
|
).pagination.as_dict
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST",
|
||||||
|
pagination_result=pagination_result,
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
BuildAreaListEvent.event_callable = build_area_list_callable
|
||||||
|
|
||||||
|
|
||||||
|
def build_area_create_callable(data: dict):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
with BuildArea.new_session() as db_session:
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Example callable method 2",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildAreaCreateEvent.event_callable = build_area_create_callable
|
||||||
|
|
||||||
|
|
||||||
|
def build_area_update_callable(data: dict):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
with BuildArea.new_session() as db_session:
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Example callable method 2",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildAreaUpdateEvent.event_callable = build_area_update_callable
|
||||||
27
ApiServices/BuildingService/Events/building/cluster.py
Normal file
27
ApiServices/BuildingService/Events/building/cluster.py
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
BuildingListEvent,
|
||||||
|
BuildingCreateEvent,
|
||||||
|
BuildingUpdateEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
BuildRouterCluster = RouterCluster(name="BuildRouterCluster")
|
||||||
|
|
||||||
|
BuildEventClusterList = EventCluster(
|
||||||
|
name="BuildList", endpoint_uu_id="1a186985-ed2a-434b-af28-22d6773382e9"
|
||||||
|
)
|
||||||
|
BuildEventClusterList.add_event(BuildingListEvent)
|
||||||
|
|
||||||
|
BuildEventClusterCreate = EventCluster(
|
||||||
|
name="BuildCreate", endpoint_uu_id="d545c5a9-bbbf-4795-a4de-467db0809a04"
|
||||||
|
)
|
||||||
|
BuildEventClusterCreate.add_event(BuildingCreateEvent)
|
||||||
|
|
||||||
|
BuildEventClusterUpdate = EventCluster(
|
||||||
|
name="BuildUpdate", endpoint_uu_id="6166a28e-8da8-4a2c-96c8-0a1651739cf3"
|
||||||
|
)
|
||||||
|
BuildEventClusterUpdate.add_event(BuildingUpdateEvent)
|
||||||
|
|
||||||
|
BuildRouterCluster.set_event_cluster(BuildEventClusterList)
|
||||||
|
BuildRouterCluster.set_event_cluster(BuildEventClusterCreate)
|
||||||
|
BuildRouterCluster.set_event_cluster(BuildEventClusterUpdate)
|
||||||
98
ApiServices/BuildingService/Events/building/supers_events.py
Normal file
98
ApiServices/BuildingService/Events/building/supers_events.py
Normal file
@@ -0,0 +1,98 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
|
from Validations.building.building.validations import (
|
||||||
|
REQUESTEWFAZCDMPVZHIWOKZEJBIEUDAFBNXFEEAEGSELVGGCDMWLQPYMRAEEABSRQJUFBIMFEEADXK,
|
||||||
|
)
|
||||||
|
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Schemas import Build
|
||||||
|
|
||||||
|
|
||||||
|
# List endpoint
|
||||||
|
BuildingListEvent = Event(
|
||||||
|
name="building_list",
|
||||||
|
key="e675d36a-6772-44a8-b153-9a8d55e0f560",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="List events of buildings endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Create endpoint
|
||||||
|
BuildingCreateEvent = Event(
|
||||||
|
name="building_create",
|
||||||
|
key="d79e3bdc-8f75-41d0-8eeb-dd9893d7ea0d",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Create events of buildings endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Update endpoint
|
||||||
|
BuildingUpdateEvent = Event(
|
||||||
|
name="building_update",
|
||||||
|
key="45e1bb8c-c521-4013-9e99-d3a58204bc5f",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Update events of buildings endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def building_list_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
with Build.new_session() as db_session:
|
||||||
|
if list_options.query:
|
||||||
|
buildings_list = Build.filter_all(
|
||||||
|
*Build.convert(list_options.query), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
buildings_list = Build.filter_all(db=db_session)
|
||||||
|
pagination = Pagination(data=buildings_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(
|
||||||
|
data=buildings_list,
|
||||||
|
pagination=pagination,
|
||||||
|
# response_model="",
|
||||||
|
).pagination.as_dict
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST",
|
||||||
|
pagination_result=pagination_result,
|
||||||
|
request=REQUESTEWFAZCDMPVZHIWOKZEJBIEUDAFBNXFEEAEGSELVGGCDMWLQPYMRAEEABSRQJUFBIMFEEADXK,
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
BuildingListEvent.event_callable = building_list_callable
|
||||||
|
|
||||||
|
|
||||||
|
def building_create_callable():
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Example callable method 2",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildingCreateEvent.event_callable = building_create_callable
|
||||||
|
|
||||||
|
|
||||||
|
def building_update_callable():
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Example callable method 2",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildingUpdateEvent.event_callable = building_update_callable
|
||||||
27
ApiServices/BuildingService/Events/sites/cluster.py
Normal file
27
ApiServices/BuildingService/Events/sites/cluster.py
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
BuildSitesListEvent,
|
||||||
|
BuildSitesCreateEvent,
|
||||||
|
BuildSitesUpdateEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
BuildSitesRouterCluster = RouterCluster(name="BuildSitesRouterCluster")
|
||||||
|
|
||||||
|
BuildSitesEventClusterList = EventCluster(
|
||||||
|
name="BuildSitesList", endpoint_uu_id="1159fb39-ad5d-46fb-8b6b-461021a39da3"
|
||||||
|
)
|
||||||
|
BuildSitesEventClusterList.add_event(BuildSitesListEvent)
|
||||||
|
|
||||||
|
BuildSitesEventClusterCreate = EventCluster(
|
||||||
|
name="BuildCreate", endpoint_uu_id="bc71d276-fd51-43bb-90f2-6f4245b59d72"
|
||||||
|
)
|
||||||
|
BuildSitesEventClusterCreate.add_event(BuildSitesCreateEvent)
|
||||||
|
|
||||||
|
BuildSitesEventClusterUpdate = EventCluster(
|
||||||
|
name="BuildUpdate", endpoint_uu_id="eca87985-3074-44cb-a947-f01e30769019"
|
||||||
|
)
|
||||||
|
BuildSitesEventClusterUpdate.add_event(BuildSitesUpdateEvent)
|
||||||
|
|
||||||
|
BuildSitesRouterCluster.set_event_cluster(BuildSitesEventClusterList)
|
||||||
|
BuildSitesRouterCluster.set_event_cluster(BuildSitesEventClusterCreate)
|
||||||
|
BuildSitesRouterCluster.set_event_cluster(BuildSitesEventClusterUpdate)
|
||||||
96
ApiServices/BuildingService/Events/sites/supers_events.py
Normal file
96
ApiServices/BuildingService/Events/sites/supers_events.py
Normal file
@@ -0,0 +1,96 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
|
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Schemas import BuildSites
|
||||||
|
|
||||||
|
|
||||||
|
# List endpoint
|
||||||
|
BuildSitesListEvent = Event(
|
||||||
|
name="build_sites_list",
|
||||||
|
key="d16c692f-5597-493a-90fe-b2bfe0d1c163",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="List events of build sites endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Create endpoint
|
||||||
|
BuildSitesCreateEvent = Event(
|
||||||
|
name="build_sites_create",
|
||||||
|
key="8ed0929e-9c96-4e81-b073-e3578ca13f37",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Create events of build sites endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Update endpoint
|
||||||
|
BuildSitesUpdateEvent = Event(
|
||||||
|
name="build_sites_update",
|
||||||
|
key="ece55fa6-afba-4c34-bd2e-f39a4cdd6b5c",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Update events of build sites endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def build_sites_list_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
with BuildSites.new_session() as db_session:
|
||||||
|
if list_options.query:
|
||||||
|
buildings_list = BuildSites.filter_all(
|
||||||
|
*BuildSites.convert(list_options.query), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
buildings_list = BuildSites.filter_all(db=db_session)
|
||||||
|
pagination = Pagination(data=buildings_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(
|
||||||
|
data=buildings_list,
|
||||||
|
pagination=pagination,
|
||||||
|
# response_model="",
|
||||||
|
).pagination.as_dict
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST",
|
||||||
|
pagination_result=pagination_result,
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
BuildSitesListEvent.event_callable = build_sites_list_callable
|
||||||
|
|
||||||
|
|
||||||
|
def build_sites_create_callable(data: dict):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
with BuildSites.new_session() as db_session:
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Example callable method 2",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildSitesCreateEvent.event_callable = build_sites_create_callable
|
||||||
|
|
||||||
|
|
||||||
|
def build_sites_update_callable(data: dict):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
with BuildSites.new_session() as db_session:
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Example callable method 2",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildSitesUpdateEvent.event_callable = build_sites_update_callable
|
||||||
27
ApiServices/BuildingService/Events/spaces/cluster.py
Normal file
27
ApiServices/BuildingService/Events/spaces/cluster.py
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
BuildLivingSpaceListEvent,
|
||||||
|
BuildLivingSpaceCreateEvent,
|
||||||
|
BuildLivingSpaceUpdateEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
BuildLivingSpaceRouterCluster = RouterCluster(name="BuildLivingSpaceRouterCluster")
|
||||||
|
|
||||||
|
BuildLivingSpaceEventClusterList = EventCluster(
|
||||||
|
name="BuildLivingSpaceList", endpoint_uu_id="ad17c019-3050-4c41-ab6f-9ce43290e81a"
|
||||||
|
)
|
||||||
|
BuildLivingSpaceEventClusterList.add_event(BuildLivingSpaceListEvent)
|
||||||
|
|
||||||
|
BuildLivingSpaceEventClusterCreate = EventCluster(
|
||||||
|
name="BuildCreate", endpoint_uu_id="ed9a0303-14e2-46fe-bec0-d395c29801ff"
|
||||||
|
)
|
||||||
|
BuildLivingSpaceEventClusterCreate.add_event(BuildLivingSpaceCreateEvent)
|
||||||
|
|
||||||
|
BuildLivingSpaceEventClusterUpdate = EventCluster(
|
||||||
|
name="BuildUpdate", endpoint_uu_id="c62bb3dc-03c0-406c-8bbc-0e1f75a6420c"
|
||||||
|
)
|
||||||
|
BuildLivingSpaceEventClusterUpdate.add_event(BuildLivingSpaceUpdateEvent)
|
||||||
|
|
||||||
|
BuildLivingSpaceRouterCluster.set_event_cluster(BuildLivingSpaceEventClusterList)
|
||||||
|
BuildLivingSpaceRouterCluster.set_event_cluster(BuildLivingSpaceEventClusterCreate)
|
||||||
|
BuildLivingSpaceRouterCluster.set_event_cluster(BuildLivingSpaceEventClusterUpdate)
|
||||||
96
ApiServices/BuildingService/Events/spaces/supers_events.py
Normal file
96
ApiServices/BuildingService/Events/spaces/supers_events.py
Normal file
@@ -0,0 +1,96 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
|
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Schemas import BuildLivingSpace
|
||||||
|
|
||||||
|
|
||||||
|
# List endpoint
|
||||||
|
BuildLivingSpaceListEvent = Event(
|
||||||
|
name="build_living_space_list",
|
||||||
|
key="d16c692f-5597-493a-90fe-b2bfe0d1c163",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="List events of build living spaces endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Create endpoint
|
||||||
|
BuildLivingSpaceCreateEvent = Event(
|
||||||
|
name="build_living_space_create",
|
||||||
|
key="8ed0929e-9c96-4e81-b073-e3578ca13f37",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Create events of build living spaces endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Update endpoint
|
||||||
|
BuildLivingSpaceUpdateEvent = Event(
|
||||||
|
name="build_living_space_update",
|
||||||
|
key="ece55fa6-afba-4c34-bd2e-f39a4cdd6b5c",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Update events of build living spaces endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def build_living_space_list_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
List callable method
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
with BuildLivingSpace.new_session() as db_session:
|
||||||
|
if list_options.query:
|
||||||
|
buildings_list = BuildLivingSpace.filter_all(
|
||||||
|
*BuildLivingSpace.convert(list_options.query), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
buildings_list = BuildLivingSpace.filter_all(db=db_session)
|
||||||
|
pagination = Pagination(data=buildings_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(
|
||||||
|
data=buildings_list,
|
||||||
|
pagination=pagination,
|
||||||
|
# response_model="",
|
||||||
|
).pagination.as_dict
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST",
|
||||||
|
pagination_result=pagination_result,
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
BuildLivingSpaceListEvent.event_callable = build_living_space_list_callable
|
||||||
|
|
||||||
|
|
||||||
|
def build_living_space_create_callable(data: dict):
|
||||||
|
"""
|
||||||
|
Create callable method
|
||||||
|
"""
|
||||||
|
with BuildLivingSpace.new_session() as db_session:
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Build living space created",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildLivingSpaceCreateEvent.event_callable = build_living_space_create_callable
|
||||||
|
|
||||||
|
|
||||||
|
def build_living_space_update_callable(data: dict):
|
||||||
|
"""
|
||||||
|
Update callable method
|
||||||
|
"""
|
||||||
|
with BuildLivingSpace.new_session() as db_session:
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Build living space updated",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildLivingSpaceUpdateEvent.event_callable = build_living_space_update_callable
|
||||||
27
ApiServices/BuildingService/Events/type/cluster.py
Normal file
27
ApiServices/BuildingService/Events/type/cluster.py
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
BuildTypeListEvent,
|
||||||
|
BuildTypeCreateEvent,
|
||||||
|
BuildTypeUpdateEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
BuildTypeRouterCluster = RouterCluster(name="BuildTypeRouterCluster")
|
||||||
|
|
||||||
|
BuildTypeEventClusterList = EventCluster(
|
||||||
|
name="BuildTypeList", endpoint_uu_id="14f076c2-b118-4cfb-b679-9f2168a2658c"
|
||||||
|
)
|
||||||
|
BuildTypeEventClusterList.add_event(BuildTypeListEvent)
|
||||||
|
|
||||||
|
BuildTypeEventClusterCreate = EventCluster(
|
||||||
|
name="BuildCreate", endpoint_uu_id="4c90c4cf-8873-479a-a56b-d12f276efa9d"
|
||||||
|
)
|
||||||
|
BuildTypeEventClusterCreate.add_event(BuildTypeCreateEvent)
|
||||||
|
|
||||||
|
BuildTypeEventClusterUpdate = EventCluster(
|
||||||
|
name="BuildUpdate", endpoint_uu_id="cde9db69-6795-4562-802d-540d0b03ceaa"
|
||||||
|
)
|
||||||
|
BuildTypeEventClusterUpdate.add_event(BuildTypeUpdateEvent)
|
||||||
|
|
||||||
|
BuildTypeRouterCluster.set_event_cluster(BuildTypeEventClusterList)
|
||||||
|
BuildTypeRouterCluster.set_event_cluster(BuildTypeEventClusterCreate)
|
||||||
|
BuildTypeRouterCluster.set_event_cluster(BuildTypeEventClusterUpdate)
|
||||||
96
ApiServices/BuildingService/Events/type/supers_events.py
Normal file
96
ApiServices/BuildingService/Events/type/supers_events.py
Normal file
@@ -0,0 +1,96 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
|
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Schemas import BuildTypes
|
||||||
|
|
||||||
|
|
||||||
|
# List endpoint
|
||||||
|
BuildTypeListEvent = Event(
|
||||||
|
name="build_type_list",
|
||||||
|
key="e013b43e-3845-4a95-b5b0-409343659c5f",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="List events of build types endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Create endpoint
|
||||||
|
BuildTypeCreateEvent = Event(
|
||||||
|
name="build_type_create",
|
||||||
|
key="8119a07e-bbb2-4d4c-b529-f923e8cdcc60",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Create events of build types endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Update endpoint
|
||||||
|
BuildTypeUpdateEvent = Event(
|
||||||
|
name="build_type_update",
|
||||||
|
key="6b7b89d5-6406-4614-aba4-c942f0c081ac",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Update events of build types endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def build_type_list_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
List callable method
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
with BuildTypes.new_session() as db_session:
|
||||||
|
if list_options.query:
|
||||||
|
buildings_list = BuildTypes.filter_all(
|
||||||
|
*BuildTypes.convert(list_options.query), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
buildings_list = BuildTypes.filter_all(db=db_session)
|
||||||
|
pagination = Pagination(data=buildings_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(
|
||||||
|
data=buildings_list,
|
||||||
|
pagination=pagination,
|
||||||
|
# response_model="",
|
||||||
|
).pagination.as_dict
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST",
|
||||||
|
pagination_result=pagination_result,
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
BuildTypeListEvent.event_callable = build_type_list_callable
|
||||||
|
|
||||||
|
|
||||||
|
def build_type_create_callable(data: dict):
|
||||||
|
"""
|
||||||
|
Create callable method
|
||||||
|
"""
|
||||||
|
with BuildTypes.new_session() as db_session:
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Build type created",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildTypeCreateEvent.event_callable = build_type_create_callable
|
||||||
|
|
||||||
|
|
||||||
|
def build_type_update_callable(data: dict):
|
||||||
|
"""
|
||||||
|
Update callable method
|
||||||
|
"""
|
||||||
|
with BuildTypes.new_session() as db_session:
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Build type updated",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
BuildTypeUpdateEvent.event_callable = build_type_update_callable
|
||||||
@@ -0,0 +1,37 @@
|
|||||||
|
from pydantic import BaseModel
|
||||||
|
from typing import Optional
|
||||||
|
|
||||||
|
|
||||||
|
class REQUESTEWFAZCDMPVZHIWOKZEJBIEUDAFBNXFEEAEGSELVGGCDMWLQPYMRAEEABSRQJUFBIMFEEADXK(
|
||||||
|
BaseModel
|
||||||
|
):
|
||||||
|
gov_address_code: str
|
||||||
|
build_name: str
|
||||||
|
build_no: str
|
||||||
|
max_floor: int
|
||||||
|
underground_floor: int
|
||||||
|
build_date: str
|
||||||
|
decision_period_date: str
|
||||||
|
tax_no: str
|
||||||
|
lift_count: int
|
||||||
|
heating_system: bool
|
||||||
|
cooling_system: bool
|
||||||
|
hot_water_system: bool
|
||||||
|
block_service_man_count: int
|
||||||
|
security_service_man_count: int
|
||||||
|
garage_count: int
|
||||||
|
management_room_id: int
|
||||||
|
site_uu_id: str
|
||||||
|
address_uu_id: str
|
||||||
|
|
||||||
|
|
||||||
|
class REQUESTOCARDAJXLDANCXQAJWDBDIWXHUAEKQNUOSBZOCWXDAFGLAAVRBSADHUBDXAREUSESYGNGKBR(
|
||||||
|
BaseModel
|
||||||
|
):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class REQUESTAEKUDAILSFMCCLOERBHBFRCIKFCSNCBOSENCAEOIDACPRFZCCWGEDBHBFBMZBFCJHCBVKEFC(
|
||||||
|
BaseModel
|
||||||
|
):
|
||||||
|
pass
|
||||||
@@ -1,12 +1,12 @@
|
|||||||
from Controllers.Postgres.database import get_db
|
from Controllers.Postgres.database import get_db
|
||||||
from Schemas import Users, Employees, BuildLivingSpace
|
from Schemas import Users, Employees, BuildLivingSpace, Services
|
||||||
from init_service_to_events import init_service_to_event_matches_for_super_user
|
from init_service_to_events import init_service_to_event_matches_for_super_user
|
||||||
from init_applications import (
|
from init_applications import (
|
||||||
init_applications_for_super_user,
|
init_applications_for_super_user,
|
||||||
init_applications_for_general_manager,
|
# init_applications_for_general_manager,
|
||||||
init_applications_for_build_manager,
|
# init_applications_for_build_manager,
|
||||||
init_applications_for_owner,
|
# init_applications_for_owner,
|
||||||
init_applications_for_tenant,
|
# init_applications_for_tenant,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
@@ -16,62 +16,59 @@ if __name__ == "__main__":
|
|||||||
Set Events to service | Set Service to employee
|
Set Events to service | Set Service to employee
|
||||||
"""
|
"""
|
||||||
with get_db() as db_session:
|
with get_db() as db_session:
|
||||||
if super_man := Users.filter_one(
|
service_super_user = Services.filter_one(Services.service_code == "SRE-SUE", db=db_session).data
|
||||||
Users.email == "karatay.berkay.sup@evyos.com.tr", db=db_session
|
user_super_user = Users.filter_one(Users.email == "karatay.berkay.sup@evyos.com.tr", db=db_session).data
|
||||||
).data:
|
employee_super_user = Employees.filter_one(Employees.people_id == user_super_user.person_id, db=db_session).data
|
||||||
super_employee = Employees.filter_one(
|
if service_super_user and user_super_user and employee_super_user:
|
||||||
Employees.people_id == super_man.person_id, db=db_session
|
|
||||||
).data
|
|
||||||
|
|
||||||
init_service_to_event_matches_for_super_user(
|
init_service_to_event_matches_for_super_user(
|
||||||
super_user=super_employee, db_session=db_session
|
service_match=service_super_user, employee_match=employee_super_user, db_session=db_session
|
||||||
)
|
)
|
||||||
init_applications_for_super_user(
|
init_applications_for_super_user(
|
||||||
super_user=super_employee, db_session=db_session
|
service_match=service_super_user, employee_match=employee_super_user, db_session=db_session
|
||||||
)
|
)
|
||||||
|
|
||||||
with get_db() as db_session:
|
# with get_db() as db_session:
|
||||||
print("Createing GM")
|
# print("Createing GM")
|
||||||
if gen_man := Users.filter_one(
|
# if gen_man := Users.filter_one(
|
||||||
Users.email == "example.general@evyos.com.tr", db=db_session
|
# Users.email == "example.general@evyos.com.tr", db=db_session
|
||||||
).data:
|
# ).data:
|
||||||
gen_man_employee = Employees.filter_one(
|
# gen_man_employee = Employees.filter_one(
|
||||||
Employees.people_id == gen_man.person_id, db=db_session
|
# Employees.people_id == gen_man.person_id, db=db_session
|
||||||
).data
|
# ).data
|
||||||
print("General Manager : ", gen_man_employee)
|
# print("General Manager : ", gen_man_employee)
|
||||||
init_applications_for_general_manager(
|
# init_applications_for_general_manager(
|
||||||
super_user=gen_man_employee, db_session=db_session
|
# super_user=gen_man_employee, db_session=db_session
|
||||||
)
|
# )
|
||||||
|
|
||||||
with get_db() as db_session:
|
# with get_db() as db_session:
|
||||||
if build_man := Users.filter_one(
|
# if build_man := Users.filter_one(
|
||||||
Users.email == "example.build.manager@gmail.com", db=db_session
|
# Users.email == "example.build.manager@gmail.com", db=db_session
|
||||||
).data:
|
# ).data:
|
||||||
build_man_employee = BuildLivingSpace.filter_one(
|
# build_man_employee = BuildLivingSpace.filter_one(
|
||||||
BuildLivingSpace.person_id == build_man.person_id, db=db_session
|
# BuildLivingSpace.person_id == build_man.person_id, db=db_session
|
||||||
).data
|
# ).data
|
||||||
init_applications_for_build_manager(
|
# init_applications_for_build_manager(
|
||||||
super_user=build_man_employee, db_session=db_session
|
# super_user=build_man_employee, db_session=db_session
|
||||||
)
|
# )
|
||||||
|
|
||||||
with get_db() as db_session:
|
# with get_db() as db_session:
|
||||||
if own_flt := Users.filter_one(
|
# if own_flt := Users.filter_one(
|
||||||
Users.email == "example.owner@gmail.com", db=db_session
|
# Users.email == "example.owner@gmail.com", db=db_session
|
||||||
).data:
|
# ).data:
|
||||||
own_flt_employee = BuildLivingSpace.filter_one(
|
# own_flt_employee = BuildLivingSpace.filter_one(
|
||||||
BuildLivingSpace.person_id == own_flt.person_id, db=db_session
|
# BuildLivingSpace.person_id == own_flt.person_id, db=db_session
|
||||||
).data
|
# ).data
|
||||||
init_applications_for_owner(
|
# init_applications_for_owner(
|
||||||
super_user=own_flt_employee, db_session=db_session
|
# super_user=own_flt_employee, db_session=db_session
|
||||||
)
|
# )
|
||||||
|
|
||||||
with get_db() as db_session:
|
# with get_db() as db_session:
|
||||||
if ten_flt := Users.filter_one(
|
# if ten_flt := Users.filter_one(
|
||||||
Users.email == "example.tenant@gmail.com", db=db_session
|
# Users.email == "example.tenant@gmail.com", db=db_session
|
||||||
).data:
|
# ).data:
|
||||||
ten_flt_employee = BuildLivingSpace.filter_one(
|
# ten_flt_employee = BuildLivingSpace.filter_one(
|
||||||
BuildLivingSpace.person_id == ten_flt.person_id, db=db_session
|
# BuildLivingSpace.person_id == ten_flt.person_id, db=db_session
|
||||||
).data
|
# ).data
|
||||||
init_applications_for_tenant(
|
# init_applications_for_tenant(
|
||||||
super_user=ten_flt_employee, db_session=db_session
|
# super_user=ten_flt_employee, db_session=db_session
|
||||||
)
|
# )
|
||||||
|
|||||||
@@ -4,223 +4,193 @@ from Schemas import (
|
|||||||
Application2Occupant,
|
Application2Occupant,
|
||||||
Employees,
|
Employees,
|
||||||
BuildLivingSpace,
|
BuildLivingSpace,
|
||||||
|
Services,
|
||||||
|
Service2Application,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
def init_applications_for_super_user(super_user: Employees, db_session=None) -> None:
|
def init_applications_for_super_user(service_match: Services, employee_match: Employees, db_session=None) -> None:
|
||||||
list_of_created_apps = [
|
list_of_all_events = Applications.filter_all(db=db_session).data
|
||||||
dict(
|
Service2Application.filter_all(db=db_session).query.delete()
|
||||||
name="Dashboard1",
|
Service2Application.save(db=db_session)
|
||||||
application_code="app000001",
|
|
||||||
site_url="/dashboard",
|
for list_of_event_code in list_of_all_events:
|
||||||
application_type="info",
|
service_to_event_found = Service2Application.filter_one_system(
|
||||||
description="Dashboard Page",
|
Service2Application.application_id == list_of_event_code.id,
|
||||||
),
|
Service2Application.service_id == service_match.id,
|
||||||
dict(
|
|
||||||
name="Individual",
|
|
||||||
application_code="app000003",
|
|
||||||
site_url="/individual",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for people",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="User",
|
|
||||||
application_code="app000004",
|
|
||||||
site_url="/user",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for user",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="Build",
|
|
||||||
application_code="app000005",
|
|
||||||
site_url="/build",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for build",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="BuildParts",
|
|
||||||
application_code="app000006",
|
|
||||||
site_url="/build/parts",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for build parts",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="BuildArea",
|
|
||||||
application_code="app000007",
|
|
||||||
site_url="/build/area",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for build area",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="ManagementAccounting",
|
|
||||||
application_code="app000008",
|
|
||||||
site_url="/management/accounting",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for management accounting",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="ManagementBudget",
|
|
||||||
application_code="app000009",
|
|
||||||
site_url="/management/budget",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for management accounting2",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="ManagementMeetingClose",
|
|
||||||
application_code="app000010",
|
|
||||||
site_url="/annual/meeting/close",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for management accounting3",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="EmergencyMeeting",
|
|
||||||
application_code="app000011",
|
|
||||||
site_url="/emergency/meeting",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for management accounting4",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="EmergencyMeetingClose",
|
|
||||||
application_code="app000012",
|
|
||||||
site_url="/emergency/meeting/close",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for management accounting5",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="MeetingParticipation",
|
|
||||||
application_code="app000013",
|
|
||||||
site_url="/meeting/participation",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for management accounting6",
|
|
||||||
),
|
|
||||||
]
|
|
||||||
for list_of_created_app in list_of_created_apps:
|
|
||||||
created_page = Applications.find_or_create(
|
|
||||||
**list_of_created_app,
|
|
||||||
db=db_session,
|
db=db_session,
|
||||||
|
)
|
||||||
|
if service_to_event_found.data:
|
||||||
|
service_to_event_found.destroy(db=db_session)
|
||||||
|
print(
|
||||||
|
f"UUID: {service_to_event_found.uu_id} application is deleted from {service_match.service_description}"
|
||||||
|
)
|
||||||
|
|
||||||
|
employee_added_application = Service2Application.find_or_create(
|
||||||
|
service_id=service_match.id,
|
||||||
|
service_uu_id=str(service_match.uu_id),
|
||||||
|
application_id=list_of_event_code.id,
|
||||||
|
application_uu_id=str(list_of_event_code.uu_id),
|
||||||
|
application_code=list_of_event_code.application_code,
|
||||||
|
site_url=list_of_event_code.site_url,
|
||||||
is_confirmed=True,
|
is_confirmed=True,
|
||||||
)
|
active=True,
|
||||||
if created_page.meta_data.created:
|
|
||||||
created_page.save(db=db_session)
|
|
||||||
|
|
||||||
application_employee_created = Application2Employee.find_or_create(
|
|
||||||
employee_id=super_user.id,
|
|
||||||
employee_uu_id=str(super_user.uu_id),
|
|
||||||
site_url=created_page.site_url,
|
|
||||||
application_code=created_page.application_code,
|
|
||||||
application_id=created_page.id,
|
|
||||||
application_uu_id=str(created_page.uu_id),
|
|
||||||
is_confirmed=True,
|
|
||||||
db=db_session,
|
db=db_session,
|
||||||
)
|
)
|
||||||
if application_employee_created.meta_data.created:
|
if employee_added_application.meta_data.created:
|
||||||
application_employee_created.save(db=db_session)
|
employee_added_application.save(db=db_session)
|
||||||
|
print(
|
||||||
|
f"UUID: {employee_added_application.uu_id} application is saved to {service_match.service_description}"
|
||||||
|
)
|
||||||
|
|
||||||
|
employee_added_service = Application2Employee.find_or_create(
|
||||||
def init_applications_for_general_manager(
|
service_id=service_match.id,
|
||||||
super_user: Employees, db_session=None
|
service_uu_id=str(service_match.uu_id),
|
||||||
) -> None:
|
employee_id=employee_match.id,
|
||||||
list_of_created_apps = [
|
employee_uu_id=str(employee_match.uu_id),
|
||||||
dict(
|
is_confirmed=True,
|
||||||
name="Dashboard1",
|
db=db_session,
|
||||||
application_code="app000001",
|
)
|
||||||
site_url="/dashboard",
|
if employee_added_service.meta_data.created:
|
||||||
application_type="info",
|
employee_added_service.save(db=db_session)
|
||||||
description="Dashboard Page",
|
print(
|
||||||
),
|
f"UUID: {employee_added_service.uu_id} service is saved to {employee_match.uu_id}"
|
||||||
dict(
|
|
||||||
name="ManagementAccounting",
|
|
||||||
application_code="app000008",
|
|
||||||
site_url="/management/accounting",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for management accounting",
|
|
||||||
),
|
|
||||||
]
|
|
||||||
for list_of_created_app in list_of_created_apps:
|
|
||||||
created_page = Applications.find_or_create(
|
|
||||||
**list_of_created_app,
|
|
||||||
db=db_session,
|
|
||||||
)
|
)
|
||||||
print("Application : ", created_page)
|
|
||||||
if created_page.meta_data.created:
|
|
||||||
created_page.save(db=db_session)
|
|
||||||
|
|
||||||
application_employee_created = Application2Employee.find_or_create(
|
|
||||||
employee_id=super_user.id,
|
|
||||||
employee_uu_id=str(super_user.uu_id),
|
|
||||||
site_url=created_page.site_url,
|
|
||||||
application_code=created_page.application_code,
|
|
||||||
application_id=created_page.id,
|
|
||||||
application_uu_id=str(created_page.uu_id),
|
|
||||||
is_confirmed=True,
|
|
||||||
db=db_session,
|
|
||||||
)
|
|
||||||
print("Application Employee : ", application_employee_created)
|
|
||||||
if application_employee_created.meta_data.created:
|
|
||||||
application_employee_created.save(db=db_session)
|
|
||||||
|
|
||||||
|
|
||||||
def init_applications_for_build_manager(
|
# def init_applications_for_general_manager(
|
||||||
super_user: BuildLivingSpace, db_session=None
|
# super_user: Employees, db_session=None
|
||||||
) -> None:
|
# ) -> None:
|
||||||
list_of_created_apps = []
|
# list_of_created_apps = Applications.filter_all_system(db=db_session).data
|
||||||
|
# if not list_of_created_apps:
|
||||||
|
# raise Exception("No applications found")
|
||||||
|
|
||||||
|
# for list_of_created_app in list_of_created_apps:
|
||||||
|
# application_employee_created = Application2Employee.find_or_create(
|
||||||
|
# employee_id=super_user.id,
|
||||||
|
# employee_uu_id=str(super_user.uu_id),
|
||||||
|
# site_url=list_of_created_app.site_url,
|
||||||
|
# application_code=list_of_created_app.application_code,
|
||||||
|
# application_id=list_of_created_app.id,
|
||||||
|
# application_uu_id=str(list_of_created_app.uu_id),
|
||||||
|
# is_confirmed=True,
|
||||||
|
# db=db_session,
|
||||||
|
# )
|
||||||
|
# if application_employee_created.meta_data.created:
|
||||||
|
# application_employee_created.save(db=db_session)
|
||||||
|
|
||||||
|
|
||||||
def init_applications_for_owner(super_user: BuildLivingSpace, db_session=None) -> None:
|
|
||||||
pass
|
# def init_applications_for_build_manager(
|
||||||
|
# super_user: BuildLivingSpace, db_session=None
|
||||||
|
# ) -> None:
|
||||||
|
# list_of_created_apps = Applications.filter_all_system(db=db_session).data
|
||||||
|
# if not list_of_created_apps:
|
||||||
|
# raise Exception("No applications found")
|
||||||
|
|
||||||
|
# for list_of_created_app in list_of_created_apps:
|
||||||
|
# application_employee_created = Application2Employee.find_or_create(
|
||||||
|
# employee_id=super_user.id,
|
||||||
|
# employee_uu_id=str(super_user.uu_id),
|
||||||
|
# site_url=list_of_created_app.site_url,
|
||||||
|
# application_code=list_of_created_app.application_code,
|
||||||
|
# application_id=list_of_created_app.id,
|
||||||
|
# application_uu_id=str(list_of_created_app.uu_id),
|
||||||
|
# is_confirmed=True,
|
||||||
|
# db=db_session,
|
||||||
|
# )
|
||||||
|
# if application_employee_created.meta_data.created:
|
||||||
|
# application_employee_created.save(db=db_session)
|
||||||
|
|
||||||
|
|
||||||
def init_applications_for_tenant(super_user: BuildLivingSpace, db_session=None) -> None:
|
# def init_applications_for_owner(super_user: BuildLivingSpace, db_session=None) -> None:
|
||||||
list_of_created_apps = [
|
# list_of_created_apps = Applications.filter_all_system(db=db_session).data
|
||||||
dict(
|
# if not list_of_created_apps:
|
||||||
name="Dashboard1",
|
# raise Exception("No applications found")
|
||||||
application_code="app000001",
|
|
||||||
site_url="/dashboard",
|
|
||||||
application_type="info",
|
|
||||||
description="Dashboard Page",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="TenantSendMessageToBuildManager",
|
|
||||||
application_code="app000022",
|
|
||||||
site_url="/tenant/messageToBM",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for tenant send message to build manager",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="TenantSendMessageToOwner",
|
|
||||||
application_code="app000018",
|
|
||||||
site_url="/tenant/messageToOwner",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for tenant send message to owner",
|
|
||||||
),
|
|
||||||
dict(
|
|
||||||
name="TenantAccountView",
|
|
||||||
application_code="app000019",
|
|
||||||
site_url="/tenant/accounting",
|
|
||||||
application_type="Dash",
|
|
||||||
description="Individual Page for tenant account view",
|
|
||||||
),
|
|
||||||
|
|
||||||
]
|
# for list_of_created_app in list_of_created_apps:
|
||||||
|
# application_employee_created = Application2Employee.find_or_create(
|
||||||
|
# employee_id=super_user.id,
|
||||||
|
# employee_uu_id=str(super_user.uu_id),
|
||||||
|
# site_url=list_of_created_app.site_url,
|
||||||
|
# application_code=list_of_created_app.application_code,
|
||||||
|
# application_id=list_of_created_app.id,
|
||||||
|
# application_uu_id=str(list_of_created_app.uu_id),
|
||||||
|
# is_confirmed=True,
|
||||||
|
# db=db_session,
|
||||||
|
# )
|
||||||
|
# if application_employee_created.meta_data.created:
|
||||||
|
# application_employee_created.save(db=db_session)
|
||||||
|
|
||||||
for list_of_created_app in list_of_created_apps:
|
|
||||||
created_page = Applications.find_or_create(
|
|
||||||
**list_of_created_app,
|
|
||||||
db=db_session,
|
|
||||||
is_confirmed=True,
|
|
||||||
)
|
|
||||||
if created_page.meta_data.created:
|
|
||||||
created_page.save(db=db_session)
|
|
||||||
|
|
||||||
application_occupant_created = Application2Occupant.find_or_create(
|
# def init_applications_for_tenant(super_user: BuildLivingSpace, db_session=None) -> None:
|
||||||
build_living_space_id=super_user.id,
|
# list_of_created_apps = Applications.filter_all_system(db=db_session).data
|
||||||
build_living_space_uu_id=str(super_user.uu_id),
|
# if not list_of_created_apps:
|
||||||
site_url=created_page.site_url,
|
# raise Exception("No applications found")
|
||||||
application_code=created_page.application_code,
|
|
||||||
application_id=created_page.id,
|
# for list_of_created_app in list_of_created_apps:
|
||||||
application_uu_id=str(created_page.uu_id),
|
# application_employee_created = Application2Employee.find_or_create(
|
||||||
is_confirmed=True,
|
# employee_id=super_user.id,
|
||||||
db=db_session,
|
# employee_uu_id=str(super_user.uu_id),
|
||||||
)
|
# site_url=list_of_created_app.site_url,
|
||||||
if application_occupant_created.meta_data.created:
|
# application_code=list_of_created_app.application_code,
|
||||||
application_occupant_created.save(db=db_session)
|
# application_id=list_of_created_app.id,
|
||||||
|
# application_uu_id=str(list_of_created_app.uu_id),
|
||||||
|
# is_confirmed=True,
|
||||||
|
# db=db_session,
|
||||||
|
# )
|
||||||
|
# if application_employee_created.meta_data.created:
|
||||||
|
# application_employee_created.save(db=db_session)
|
||||||
|
|
||||||
|
# list_of_created_apps = [
|
||||||
|
# dict(
|
||||||
|
# name="Dashboard1",
|
||||||
|
# application_code="app000001",
|
||||||
|
# site_url="/dashboard",
|
||||||
|
# application_type="info",
|
||||||
|
# description="Dashboard Page",
|
||||||
|
# ),
|
||||||
|
# dict(
|
||||||
|
# name="TenantSendMessageToBuildManager",
|
||||||
|
# application_code="app000022",
|
||||||
|
# site_url="/tenant/messageToBM",
|
||||||
|
# application_type="Dash",
|
||||||
|
# description="Individual Page for tenant send message to build manager",
|
||||||
|
# ),
|
||||||
|
# dict(
|
||||||
|
# name="TenantSendMessageToOwner",
|
||||||
|
# application_code="app000018",
|
||||||
|
# site_url="/tenant/messageToOwner",
|
||||||
|
# application_type="Dash",
|
||||||
|
# description="Individual Page for tenant send message to owner",
|
||||||
|
# ),
|
||||||
|
# dict(
|
||||||
|
# name="TenantAccountView",
|
||||||
|
# application_code="app000019",
|
||||||
|
# site_url="/tenant/accounting",
|
||||||
|
# application_type="Dash",
|
||||||
|
# description="Individual Page for tenant account view",
|
||||||
|
# ),
|
||||||
|
# ]
|
||||||
|
|
||||||
|
# for list_of_created_app in list_of_created_apps:
|
||||||
|
# created_page = Applications.find_or_create(
|
||||||
|
# **list_of_created_app,
|
||||||
|
# db=db_session,
|
||||||
|
# is_confirmed=True,
|
||||||
|
# )
|
||||||
|
# if created_page.meta_data.created:
|
||||||
|
# created_page.save(db=db_session)
|
||||||
|
|
||||||
|
# application_occupant_created = Application2Occupant.find_or_create(
|
||||||
|
# build_living_space_id=super_user.id,
|
||||||
|
# build_living_space_uu_id=str(super_user.uu_id),
|
||||||
|
# site_url=created_page.site_url,
|
||||||
|
# application_code=created_page.application_code,
|
||||||
|
# application_id=created_page.id,
|
||||||
|
# application_uu_id=str(created_page.uu_id),
|
||||||
|
# is_confirmed=True,
|
||||||
|
# db=db_session,
|
||||||
|
# )
|
||||||
|
# if application_occupant_created.meta_data.created:
|
||||||
|
# application_occupant_created.save(db=db_session)
|
||||||
|
|||||||
@@ -11,14 +11,23 @@ from Schemas import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
def init_service_to_event_matches_for_super_user(super_user, db_session=None) -> None:
|
def init_service_to_event_matches_for_super_user(service_match: Services, employee_match: Employees, db_session=None) -> None:
|
||||||
service_match = Services.filter_one(
|
|
||||||
Services.service_name == "Super User",
|
|
||||||
db=db_session,
|
|
||||||
).data
|
|
||||||
list_of_all_events = Events.filter_all(db=db_session).data
|
list_of_all_events = Events.filter_all(db=db_session).data
|
||||||
|
Service2Events.filter_all(db=db_session).query.delete()
|
||||||
|
Service2Events.save(db=db_session)
|
||||||
|
|
||||||
for list_of_event_code in list_of_all_events:
|
for list_of_event_code in list_of_all_events:
|
||||||
created_service = Service2Events.find_or_create(
|
service_to_event_found = Service2Events.filter_one_system(
|
||||||
|
Service2Events.event_id == list_of_event_code.id,
|
||||||
|
Service2Events.service_id == service_match.id,
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
if service_to_event_found.data:
|
||||||
|
service_to_event_found.destroy(db=db_session)
|
||||||
|
print(
|
||||||
|
f"UUID: {service_to_event_found.uu_id} event is deleted from {service_match.service_description}"
|
||||||
|
)
|
||||||
|
added_service = Service2Events.find_or_create(
|
||||||
service_id=service_match.id,
|
service_id=service_match.id,
|
||||||
service_uu_id=str(service_match.uu_id),
|
service_uu_id=str(service_match.uu_id),
|
||||||
event_id=list_of_event_code.id,
|
event_id=list_of_event_code.id,
|
||||||
@@ -27,22 +36,22 @@ def init_service_to_event_matches_for_super_user(super_user, db_session=None) ->
|
|||||||
active=True,
|
active=True,
|
||||||
db=db_session,
|
db=db_session,
|
||||||
)
|
)
|
||||||
if created_service.meta_data.created:
|
if added_service.meta_data.created:
|
||||||
created_service.save(db=db_session)
|
added_service.save(db=db_session)
|
||||||
print(
|
print(
|
||||||
f"UUID: {created_service.uu_id} event is saved to {service_match.uu_id}"
|
f"UUID: {added_service.uu_id} event is saved to {service_match.service_description}"
|
||||||
)
|
)
|
||||||
|
|
||||||
employee_added_service = Event2Employee.find_or_create(
|
employee_added_service = Event2Employee.find_or_create(
|
||||||
event_service_id=service_match.id,
|
event_service_id=service_match.id,
|
||||||
event_service_uu_id=str(service_match.uu_id),
|
event_service_uu_id=str(service_match.uu_id),
|
||||||
employee_id=super_user.id,
|
employee_id=employee_match.id,
|
||||||
employee_uu_id=str(super_user.uu_id),
|
employee_uu_id=str(employee_match.uu_id),
|
||||||
is_confirmed=True,
|
is_confirmed=True,
|
||||||
db=db_session,
|
db=db_session,
|
||||||
|
)
|
||||||
|
if employee_added_service.meta_data.created:
|
||||||
|
employee_added_service.save(db=db_session)
|
||||||
|
print(
|
||||||
|
f"UUID: {employee_added_service.uu_id} event is saved to employee {employee_match.uu_id}"
|
||||||
)
|
)
|
||||||
if employee_added_service.meta_data.created:
|
|
||||||
employee_added_service.save(db=db_session)
|
|
||||||
print(
|
|
||||||
f"UUID: {employee_added_service.uu_id} event is saved to {super_user.uu_id}"
|
|
||||||
)
|
|
||||||
|
|||||||
@@ -3,24 +3,27 @@ FROM python:3.12-slim
|
|||||||
WORKDIR /
|
WORKDIR /
|
||||||
|
|
||||||
# Install system dependencies and Poetry
|
# Install system dependencies and Poetry
|
||||||
RUN apt-get update && apt-get install -y --no-install-recommends gcc \
|
RUN apt-get update && apt-get install -y --no-install-recommends gcc && rm -rf /var/lib/apt/lists/* && pip install --no-cache-dir poetry
|
||||||
&& rm -rf /var/lib/apt/lists/* && pip install --no-cache-dir poetry
|
|
||||||
|
|
||||||
# Copy Poetry configuration
|
# Copy Poetry configuration
|
||||||
COPY /pyproject.toml ./pyproject.toml
|
COPY /pyproject.toml ./pyproject.toml
|
||||||
|
|
||||||
# Configure Poetry and install dependencies with optimizations
|
# Configure Poetry and install dependencies with optimizations
|
||||||
RUN poetry config virtualenvs.create false \
|
RUN poetry config virtualenvs.create false && poetry install --no-interaction --no-ansi --no-root --only main \
|
||||||
&& poetry install --no-interaction --no-ansi --no-root --only main \
|
&& pip cache purge && rm -rf ~/.cache/pypoetry
|
||||||
&& pip cache purge && rm -rf ~/.cache/pypoetry
|
|
||||||
|
|
||||||
# Copy application code
|
# Copy application code
|
||||||
COPY /ApiServices/IdentityService /ApiServices/IdentityService
|
COPY /ApiControllers /ApiControllers
|
||||||
|
COPY /ApiDefaults /ApiDefaults
|
||||||
COPY /Controllers /Controllers
|
COPY /Controllers /Controllers
|
||||||
COPY /Schemas /Schemas
|
COPY /Schemas /Schemas
|
||||||
|
|
||||||
|
COPY /ApiServices/IdentityService/Endpoints /ApiDefaults/Endpoints
|
||||||
|
COPY /ApiServices/IdentityService/Events /ApiDefaults/Events
|
||||||
|
COPY /ApiServices/IdentityService/Validations /ApiDefaults/Validations
|
||||||
|
|
||||||
# Set Python path to include app directory
|
# Set Python path to include app directory
|
||||||
ENV PYTHONPATH=/ PYTHONUNBUFFERED=1 PYTHONDONTWRITEBYTECODE=1
|
ENV PYTHONPATH=/ PYTHONUNBUFFERED=1 PYTHONDONTWRITEBYTECODE=1
|
||||||
|
|
||||||
# Run the application using the configured uvicorn server
|
# Run the application using the configured uvicorn server
|
||||||
CMD ["poetry", "run", "python", "ApiServices/IdentityService/app.py"]
|
CMD ["poetry", "run", "python", "ApiDefaults/app.py"]
|
||||||
|
|||||||
67
ApiServices/IdentityService/Endpoints/people/route.py
Normal file
67
ApiServices/IdentityService/Endpoints/people/route.py
Normal file
@@ -0,0 +1,67 @@
|
|||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly
|
||||||
|
from Events.people.cluster import PeopleRouterCluster
|
||||||
|
|
||||||
|
|
||||||
|
people_route = APIRouter(prefix="/people", tags=["People"])
|
||||||
|
|
||||||
|
|
||||||
|
@people_route.post(
|
||||||
|
path="/list",
|
||||||
|
description="List people endpoint",
|
||||||
|
operation_id="f102db46-031a-43e4-966a-dae6896f985b",
|
||||||
|
)
|
||||||
|
def people_route_list(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List people endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = PeopleRouterCluster.get_event_cluster("PeopleList")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@people_route.post(
|
||||||
|
path="/create",
|
||||||
|
description="Create people endpoint",
|
||||||
|
operation_id="eb465fde-337f-4b81-94cf-28c6d4f2b1b6",
|
||||||
|
)
|
||||||
|
def people_route_create(
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Create people endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = PeopleRouterCluster.get_event_cluster("PeopleCreate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable()
|
||||||
|
|
||||||
|
|
||||||
|
@people_route.post(
|
||||||
|
path="/update",
|
||||||
|
description="Update people endpoint",
|
||||||
|
operation_id="c9e5ba69-6915-43f5-8f9c-a5c2aa865b89",
|
||||||
|
)
|
||||||
|
def people_route_update(
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Update people endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = PeopleRouterCluster.get_event_cluster("PeopleUpdate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable()
|
||||||
@@ -1,14 +1,11 @@
|
|||||||
from fastapi import APIRouter
|
from fastapi import APIRouter
|
||||||
|
|
||||||
# from .user.route import user_route
|
|
||||||
from .people.route import people_route
|
|
||||||
|
|
||||||
|
|
||||||
def get_routes() -> list[APIRouter]:
|
def get_routes() -> list[APIRouter]:
|
||||||
return [
|
from .people.route import people_route
|
||||||
# user_route,
|
from .user.route import user_route
|
||||||
people_route
|
|
||||||
]
|
return [user_route, people_route]
|
||||||
|
|
||||||
|
|
||||||
def get_safe_endpoint_urls() -> list[tuple[str, str]]:
|
def get_safe_endpoint_urls() -> list[tuple[str, str]]:
|
||||||
72
ApiServices/IdentityService/Endpoints/user/route.py
Normal file
72
ApiServices/IdentityService/Endpoints/user/route.py
Normal file
@@ -0,0 +1,72 @@
|
|||||||
|
import uuid
|
||||||
|
|
||||||
|
from fastapi import APIRouter, Header
|
||||||
|
from typing import Any
|
||||||
|
|
||||||
|
from ApiDefaults.config import api_config
|
||||||
|
from Events.user.cluster import UserRouterCluster
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly
|
||||||
|
|
||||||
|
user_route = APIRouter(prefix="/user", tags=["User"])
|
||||||
|
|
||||||
|
|
||||||
|
@user_route.post(
|
||||||
|
path="/list",
|
||||||
|
description="List users endpoint",
|
||||||
|
operation_id="1aca3094-fe80-4e0f-a460-1a506419082a",
|
||||||
|
)
|
||||||
|
def user_list_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders,
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List users endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = UserRouterCluster.get_event_cluster("UserList")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@user_route.post(
|
||||||
|
path="/create",
|
||||||
|
description="Create users endpoint",
|
||||||
|
operation_id="9686211f-4260-485d-8076-186c22c053aa",
|
||||||
|
)
|
||||||
|
def user_create_route(
|
||||||
|
data: Any,
|
||||||
|
headers: CommonHeaders,
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Create users endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = UserRouterCluster.get_event_cluster("UserCreate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@user_route.post(
|
||||||
|
path="/update",
|
||||||
|
description="Update users endpoint",
|
||||||
|
operation_id="268e887b-5ff5-4f99-b1be-7e127e28a198",
|
||||||
|
)
|
||||||
|
def user_update_route(
|
||||||
|
data: Any,
|
||||||
|
headers: CommonHeaders,
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Update users endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = UserRouterCluster.get_event_cluster("UserUpdate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
8
ApiServices/IdentityService/Events/__init__.py
Normal file
8
ApiServices/IdentityService/Events/__init__.py
Normal file
@@ -0,0 +1,8 @@
|
|||||||
|
from .people.cluster import PeopleRouterCluster
|
||||||
|
from .user.cluster import UserRouterCluster
|
||||||
|
|
||||||
|
|
||||||
|
__all__ = [
|
||||||
|
"PeopleRouterCluster",
|
||||||
|
"UserRouterCluster",
|
||||||
|
]
|
||||||
25
ApiServices/IdentityService/Events/people/cluster.py
Normal file
25
ApiServices/IdentityService/Events/people/cluster.py
Normal file
@@ -0,0 +1,25 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
SupersPeopleCreateEvent,
|
||||||
|
SupersPeopleUpdateEvent,
|
||||||
|
SupersPeopleListEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
PeopleRouterCluster = RouterCluster(name="PeopleRouterCluster")
|
||||||
|
|
||||||
|
PeopleEventClusterList = EventCluster(
|
||||||
|
name="PeopleList", endpoint_uu_id="f102db46-031a-43e4-966a-dae6896f985b"
|
||||||
|
)
|
||||||
|
PeopleEventClusterList.add_event(SupersPeopleListEvent)
|
||||||
|
PeopleEventClusterCreate = EventCluster(
|
||||||
|
name="PeopleCreate", endpoint_uu_id="eb465fde-337f-4b81-94cf-28c6d4f2b1b6"
|
||||||
|
)
|
||||||
|
PeopleEventClusterCreate.add_event(SupersPeopleCreateEvent)
|
||||||
|
PeopleEventClusterUpdate = EventCluster(
|
||||||
|
name="PeopleUpdate", endpoint_uu_id="c9e5ba69-6915-43f5-8f9c-a5c2aa865b89"
|
||||||
|
)
|
||||||
|
PeopleEventClusterUpdate.add_event(SupersPeopleUpdateEvent)
|
||||||
|
|
||||||
|
PeopleRouterCluster.set_event_cluster(PeopleEventClusterList)
|
||||||
|
PeopleRouterCluster.set_event_cluster(PeopleEventClusterCreate)
|
||||||
|
PeopleRouterCluster.set_event_cluster(PeopleEventClusterUpdate)
|
||||||
@@ -1,23 +1,45 @@
|
|||||||
from ApiServices.IdentityService.initializer.event_clusters import EventCluster, Event
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
from ApiServices.IdentityService.validations.people.validations import (
|
from Validations.people.validations import (
|
||||||
REQUESTAWMXNTKMGPPOJWRCTZUBADNFLQDBDYVQAORFAVCSXUUHEBQHCEPCSKFBADBODFDBPYKOVINV,
|
REQUESTAWMXNTKMGPPOJWRCTZUBADNFLQDBDYVQAORFAVCSXUUHEBQHCEPCSKFBADBODFDBPYKOVINV,
|
||||||
)
|
)
|
||||||
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
from Controllers.Postgres.pagination import (
|
||||||
|
ListOptions,
|
||||||
|
Pagination,
|
||||||
|
PaginationResult,
|
||||||
|
PaginateOnly,
|
||||||
|
)
|
||||||
from Controllers.Postgres.response import EndpointResponse
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
from Schemas.identity.identity import People
|
from Schemas import People
|
||||||
|
|
||||||
|
|
||||||
# Create endpoint
|
SupersPeopleCreateEvent = Event(
|
||||||
supers_people_create = Event(
|
name="supers_people_create",
|
||||||
name="supers_people_list",
|
|
||||||
key="ec4c2404-a61b-46c7-bbdf-ce3357e6cf41",
|
key="ec4c2404-a61b-46c7-bbdf-ce3357e6cf41",
|
||||||
request_validator=None, # TODO: Add request validator
|
request_validator=None, # TODO: Add request validator
|
||||||
response_validator=None, # TODO: Add response validator
|
response_validator=None, # TODO: Add response validator
|
||||||
description="Create events of people endpoint",
|
description="Super Users Create events of people endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Update endpoint
|
||||||
|
SupersPeopleUpdateEvent = Event(
|
||||||
|
name="supers_people_update",
|
||||||
|
key="91e77de4-9f29-4309-b121-4aad256d440c",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users Update events of people endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# List endpoint
|
||||||
|
SupersPeopleListEvent = Event(
|
||||||
|
name="supers_people_list",
|
||||||
|
key="6828d280-e587-400d-a622-c318277386c3",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users List events of people endpoint",
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
def supers_people_create_callable(list_options):
|
def supers_people_create_callable():
|
||||||
"""
|
"""
|
||||||
Example callable method
|
Example callable method
|
||||||
"""
|
"""
|
||||||
@@ -32,21 +54,7 @@ def supers_people_create_callable(list_options):
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
supers_people_create.event_callable = supers_people_create_callable
|
SupersPeopleCreateEvent.event_callable = supers_people_create_callable
|
||||||
|
|
||||||
people_event_cluster_create = EventCluster(
|
|
||||||
endpoint_uu_id="eb465fde-337f-4b81-94cf-28c6d4f2b1b6"
|
|
||||||
)
|
|
||||||
people_event_cluster_create.add_event([supers_people_create])
|
|
||||||
|
|
||||||
# Update endpoint
|
|
||||||
supers_people_update = Event(
|
|
||||||
name="supers_people_update",
|
|
||||||
key="91e77de4-9f29-4309-b121-4aad256d440c",
|
|
||||||
request_validator=None, # TODO: Add request validator
|
|
||||||
response_validator=None, # TODO: Add response validator
|
|
||||||
description="Update events of people endpoint",
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def supers_people_update_callable():
|
def supers_people_update_callable():
|
||||||
@@ -64,33 +72,15 @@ def supers_people_update_callable():
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
supers_people_update.event_callable = supers_people_update_callable
|
SupersPeopleUpdateEvent.event_callable = supers_people_update_callable
|
||||||
people_event_cluster_update = EventCluster(
|
|
||||||
endpoint_uu_id="c9e5ba69-6915-43f5-8f9c-a5c2aa865b89"
|
|
||||||
)
|
|
||||||
people_event_cluster_update.add_event([supers_people_update])
|
|
||||||
|
|
||||||
|
|
||||||
# List endpoint
|
def supers_people_list_callable(data: PaginateOnly):
|
||||||
supers_people_list = Event(
|
|
||||||
name="supers_people_list",
|
|
||||||
key="6828d280-e587-400d-a622-c318277386c3",
|
|
||||||
request_validator=None, # TODO: Add request validator
|
|
||||||
response_validator=None, # TODO: Add response validator
|
|
||||||
description="List events of people endpoint",
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def supers_people_list_callable(list_options: PaginateOnly):
|
|
||||||
"""
|
"""
|
||||||
Example callable method
|
Example callable method
|
||||||
"""
|
"""
|
||||||
list_options = PaginateOnly(**list_options.model_dump())
|
list_options = PaginateOnly(**data.model_dump())
|
||||||
with People.new_session() as db_session:
|
with People.new_session() as db_session:
|
||||||
People.pre_query = People.filter_all(
|
|
||||||
People.firstname.ilike("%B%"), db=db_session
|
|
||||||
).query
|
|
||||||
|
|
||||||
if list_options.query:
|
if list_options.query:
|
||||||
people_list = People.filter_all(
|
people_list = People.filter_all(
|
||||||
*People.convert(list_options.query), db=db_session
|
*People.convert(list_options.query), db=db_session
|
||||||
@@ -110,19 +100,4 @@ def supers_people_list_callable(list_options: PaginateOnly):
|
|||||||
).response
|
).response
|
||||||
|
|
||||||
|
|
||||||
supers_people_list.event_callable = supers_people_list_callable
|
SupersPeopleListEvent.event_callable = supers_people_list_callable
|
||||||
people_event_cluster_list = EventCluster(
|
|
||||||
endpoint_uu_id="f102db46-031a-43e4-966a-dae6896f985b"
|
|
||||||
)
|
|
||||||
|
|
||||||
people_event_cluster_list.add_event([supers_people_list])
|
|
||||||
|
|
||||||
|
|
||||||
class PeopleCluster:
|
|
||||||
"""
|
|
||||||
People Clusters
|
|
||||||
"""
|
|
||||||
|
|
||||||
PeopleListCluster = people_event_cluster_list
|
|
||||||
PeopleCreateCluster = people_event_cluster_create
|
|
||||||
PeopleUpdateCluster = people_event_cluster_update
|
|
||||||
27
ApiServices/IdentityService/Events/user/cluster.py
Normal file
27
ApiServices/IdentityService/Events/user/cluster.py
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
SuperUsersListEvent,
|
||||||
|
SuperUsersCreateEvent,
|
||||||
|
SuperUsersUpdateEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
UserRouterCluster = RouterCluster(name="UserRouterCluster")
|
||||||
|
|
||||||
|
UserEventClusterList = EventCluster(
|
||||||
|
name="UserList", endpoint_uu_id="1aca3094-fe80-4e0f-a460-1a506419082a"
|
||||||
|
)
|
||||||
|
UserEventClusterList.add_event(SuperUsersListEvent)
|
||||||
|
|
||||||
|
UserEventClusterCreate = EventCluster(
|
||||||
|
name="UserCreate", endpoint_uu_id="9686211f-4260-485d-8076-186c22c053aa"
|
||||||
|
)
|
||||||
|
UserEventClusterCreate.add_event(SuperUsersCreateEvent)
|
||||||
|
|
||||||
|
UserEventClusterUpdate = EventCluster(
|
||||||
|
name="UserUpdate", endpoint_uu_id="268e887b-5ff5-4f99-b1be-7e127e28a198"
|
||||||
|
)
|
||||||
|
UserEventClusterUpdate.add_event(SuperUsersUpdateEvent)
|
||||||
|
|
||||||
|
UserRouterCluster.set_event_cluster(UserEventClusterList)
|
||||||
|
UserRouterCluster.set_event_cluster(UserEventClusterCreate)
|
||||||
|
UserRouterCluster.set_event_cluster(UserEventClusterUpdate)
|
||||||
94
ApiServices/IdentityService/Events/user/supers_events.py
Normal file
94
ApiServices/IdentityService/Events/user/supers_events.py
Normal file
@@ -0,0 +1,94 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
|
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Schemas import Users
|
||||||
|
|
||||||
|
|
||||||
|
# List endpoint
|
||||||
|
SuperUsersListEvent = Event(
|
||||||
|
name="supers_users_list",
|
||||||
|
key="341b394f-9f11-4abb-99e7-4b27fa6bf012",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super User List events of users endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Create endpoint
|
||||||
|
SuperUsersCreateEvent = Event(
|
||||||
|
name="supers_users_create",
|
||||||
|
key="4e7e189e-e015-4ff8-902d-60138cbc77a6",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super User Create events of users endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Update endpoint
|
||||||
|
SuperUsersUpdateEvent = Event(
|
||||||
|
name="supers_users_update",
|
||||||
|
key="efa4aa4a-d414-4391-91ee-97eb617b7755",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super User Update events of users endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def supers_users_list_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
with Users.new_session() as db_session:
|
||||||
|
if list_options.query:
|
||||||
|
users_list = Users.filter_all(
|
||||||
|
*Users.convert(list_options.query), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
users_list = Users.filter_all(db=db_session)
|
||||||
|
pagination = Pagination(data=users_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(
|
||||||
|
data=users_list,
|
||||||
|
pagination=pagination,
|
||||||
|
# response_model="",
|
||||||
|
).pagination.as_dict
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST",
|
||||||
|
pagination_result=pagination_result,
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
SuperUsersListEvent.event_callable = supers_users_list_callable
|
||||||
|
|
||||||
|
|
||||||
|
def supers_users_create_callable():
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Example callable method 2",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
SuperUsersCreateEvent.event_callable = supers_users_create_callable
|
||||||
|
|
||||||
|
|
||||||
|
def supers_users_update_callable():
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "Example callable method 2",
|
||||||
|
"info": {
|
||||||
|
"host": "example_host",
|
||||||
|
"user_agent": "example_user_agent",
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
SuperUsersUpdateEvent.event_callable = supers_users_update_callable
|
||||||
26
ApiServices/IdentityService/Validations/lists/validations.py
Normal file
26
ApiServices/IdentityService/Validations/lists/validations.py
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
from pydantic import BaseModel
|
||||||
|
from typing import Optional
|
||||||
|
|
||||||
|
|
||||||
|
class ListOptions(BaseModel):
|
||||||
|
"""
|
||||||
|
Query for list option abilities
|
||||||
|
"""
|
||||||
|
|
||||||
|
page: Optional[int] = 1
|
||||||
|
size: Optional[int] = 10
|
||||||
|
order_field: Optional[str] = "id"
|
||||||
|
order_type: Optional[str] = "asc"
|
||||||
|
# include_joins: Optional[list] = None
|
||||||
|
query: Optional[dict] = None
|
||||||
|
|
||||||
|
|
||||||
|
class PaginateOnly(BaseModel):
|
||||||
|
"""
|
||||||
|
Query for list option abilities
|
||||||
|
"""
|
||||||
|
|
||||||
|
page: Optional[int] = 1
|
||||||
|
size: Optional[int] = 10
|
||||||
|
order_field: Optional[str] = "id"
|
||||||
|
order_type: Optional[str] = "asc"
|
||||||
@@ -0,0 +1,24 @@
|
|||||||
|
from pydantic import BaseModel
|
||||||
|
|
||||||
|
|
||||||
|
class REQUESTAWMXNTKMGPPOJWRCTZUBADNFLQDBDYVQAORFAVCSXUUHEBQHCEPCSKFBADBODFDBPYKOVINV(
|
||||||
|
BaseModel
|
||||||
|
):
|
||||||
|
uu_id: str
|
||||||
|
created_at: str
|
||||||
|
updated_at: str
|
||||||
|
person_tag: str
|
||||||
|
expiry_starts: str
|
||||||
|
expiry_ends: str
|
||||||
|
firstname: str
|
||||||
|
middle_name: str
|
||||||
|
surname: str
|
||||||
|
birth_date: str
|
||||||
|
birth_place: str
|
||||||
|
sex_code: str
|
||||||
|
country_code: str
|
||||||
|
tax_no: str
|
||||||
|
active: bool
|
||||||
|
deleted: bool
|
||||||
|
is_confirmed: bool
|
||||||
|
is_notification_send: bool
|
||||||
@@ -1,123 +0,0 @@
|
|||||||
import uuid
|
|
||||||
|
|
||||||
from fastapi import APIRouter, Request, Response, Header
|
|
||||||
|
|
||||||
from ApiServices.IdentityService.config import api_config
|
|
||||||
from ApiServices.IdentityService.events.people.event import PeopleCluster
|
|
||||||
from ApiServices.IdentityService.providers.token_provider import TokenProvider
|
|
||||||
from Controllers.Postgres.pagination import PaginateOnly
|
|
||||||
|
|
||||||
|
|
||||||
people_route = APIRouter(prefix="/people", tags=["People"])
|
|
||||||
|
|
||||||
|
|
||||||
@people_route.post(
|
|
||||||
path="/list",
|
|
||||||
description="Test Template Route",
|
|
||||||
operation_id="f102db46-031a-43e4-966a-dae6896f985b",
|
|
||||||
)
|
|
||||||
def people_route_list(
|
|
||||||
request: Request,
|
|
||||||
response: Response,
|
|
||||||
data: PaginateOnly,
|
|
||||||
language: str = Header(None, alias="language"),
|
|
||||||
domain: str = Header(None, alias="domain"),
|
|
||||||
tz: str = Header(None, alias="timezone"),
|
|
||||||
):
|
|
||||||
"""
|
|
||||||
Test Template Route
|
|
||||||
"""
|
|
||||||
endpoint_code = "f102db46-031a-43e4-966a-dae6896f985b"
|
|
||||||
token = request.headers.get(api_config.ACCESS_TOKEN_TAG, None)
|
|
||||||
headers = {
|
|
||||||
"language": language or "",
|
|
||||||
"domain": domain or "",
|
|
||||||
"eys-ext": f"{str(uuid.uuid4())}",
|
|
||||||
"tz": tz or "GMT+3",
|
|
||||||
"token": token,
|
|
||||||
}
|
|
||||||
token_object = TokenProvider.get_dict_from_redis(token=token)
|
|
||||||
event_key = TokenProvider.retrieve_event_codes(
|
|
||||||
endpoint_code=endpoint_code, token=token_object
|
|
||||||
)
|
|
||||||
event_cluster_matched = PeopleCluster.PeopleListCluster.match_event(
|
|
||||||
event_key=event_key
|
|
||||||
)
|
|
||||||
response.headers["X-Header"] = "Test Header GET"
|
|
||||||
if runner_callable := event_cluster_matched.event_callable(list_options=data):
|
|
||||||
return runner_callable
|
|
||||||
raise ValueError("Event key not found or multiple matches found")
|
|
||||||
|
|
||||||
|
|
||||||
@people_route.post(
|
|
||||||
path="/create",
|
|
||||||
description="Test Template Route with Post Method",
|
|
||||||
operation_id="eb465fde-337f-4b81-94cf-28c6d4f2b1b6",
|
|
||||||
)
|
|
||||||
def test_template_post(
|
|
||||||
request: Request,
|
|
||||||
response: Response,
|
|
||||||
language: str = Header(None, alias="language"),
|
|
||||||
domain: str = Header(None, alias="domain"),
|
|
||||||
tz: str = Header(None, alias="timezone"),
|
|
||||||
):
|
|
||||||
"""
|
|
||||||
Test Template Route with Post Method
|
|
||||||
"""
|
|
||||||
endpoint_code = "eb465fde-337f-4b81-94cf-28c6d4f2b1b6"
|
|
||||||
token = request.headers.get(api_config.ACCESS_TOKEN_TAG, None)
|
|
||||||
headers = {
|
|
||||||
"language": language or "",
|
|
||||||
"domain": domain or "",
|
|
||||||
"eys-ext": f"{str(uuid.uuid4())}",
|
|
||||||
"tz": tz or "GMT+3",
|
|
||||||
"token": token,
|
|
||||||
}
|
|
||||||
token_object = TokenProvider.get_dict_from_redis(token=token)
|
|
||||||
event_key = TokenProvider.retrieve_event_codes(
|
|
||||||
endpoint_code=endpoint_code, token=token_object
|
|
||||||
)
|
|
||||||
event_cluster_matched = PeopleCluster.PeopleCreateCluster.match_event(
|
|
||||||
event_key=event_key
|
|
||||||
)
|
|
||||||
response.headers["X-Header"] = "Test Header POST"
|
|
||||||
if runner_callable := event_cluster_matched.event_callable():
|
|
||||||
return runner_callable
|
|
||||||
raise ValueError("Event key not found or multiple matches found")
|
|
||||||
|
|
||||||
|
|
||||||
@people_route.post(
|
|
||||||
path="/update",
|
|
||||||
description="Test Template Route with Post Method",
|
|
||||||
operation_id="c9e5ba69-6915-43f5-8f9c-a5c2aa865b89",
|
|
||||||
)
|
|
||||||
def test_template_post(
|
|
||||||
request: Request,
|
|
||||||
response: Response,
|
|
||||||
language: str = Header(None, alias="language"),
|
|
||||||
domain: str = Header(None, alias="domain"),
|
|
||||||
tz: str = Header(None, alias="timezone"),
|
|
||||||
):
|
|
||||||
"""
|
|
||||||
Test Template Route with Post Method
|
|
||||||
"""
|
|
||||||
token = request.headers.get(api_config.ACCESS_TOKEN_TAG, None)
|
|
||||||
endpoint_code = "c9e5ba69-6915-43f5-8f9c-a5c2aa865b89"
|
|
||||||
headers = {
|
|
||||||
"language": language or "",
|
|
||||||
"domain": domain or "",
|
|
||||||
"eys-ext": f"{str(uuid.uuid4())}",
|
|
||||||
"tz": tz or "GMT+3",
|
|
||||||
"token": token,
|
|
||||||
}
|
|
||||||
token_object = TokenProvider.get_dict_from_redis(token=token)
|
|
||||||
event_key = TokenProvider.retrieve_event_codes(
|
|
||||||
endpoint_code=endpoint_code, token=token_object
|
|
||||||
)
|
|
||||||
event_cluster_matched = PeopleCluster.PeopleUpdateCluster.match_event(
|
|
||||||
event_key=event_key
|
|
||||||
)
|
|
||||||
response.headers["X-Header"] = "Test Header POST"
|
|
||||||
if runner_callable := event_cluster_matched.event_callable():
|
|
||||||
return runner_callable
|
|
||||||
raise ValueError("Event key not found or multiple matches found")
|
|
||||||
@@ -1,90 +0,0 @@
|
|||||||
import uuid
|
|
||||||
|
|
||||||
from fastapi import APIRouter, Request, Response, Header
|
|
||||||
|
|
||||||
from ApiServices.IdentityService.config import api_config
|
|
||||||
from ApiServices.IdentityService.events.user.event import supers_users_list
|
|
||||||
|
|
||||||
|
|
||||||
user_route = APIRouter(prefix="/user", tags=["User"])
|
|
||||||
|
|
||||||
|
|
||||||
@user_route.post(
|
|
||||||
path="/list",
|
|
||||||
description="Test Template Route",
|
|
||||||
operation_id="5bc09312-d3f2-4f47-baba-17c928706da8",
|
|
||||||
)
|
|
||||||
def test_template(
|
|
||||||
request: Request,
|
|
||||||
response: Response,
|
|
||||||
language: str = Header(None, alias="language"),
|
|
||||||
domain: str = Header(None, alias="domain"),
|
|
||||||
tz: str = Header(None, alias="timezone"),
|
|
||||||
):
|
|
||||||
"""
|
|
||||||
Test Template Route
|
|
||||||
"""
|
|
||||||
event_code = "bb20c8c6-a289-4cab-9da7-34ca8a36c8e5"
|
|
||||||
token = request.headers.get(api_config.ACCESS_TOKEN_TAG, None)
|
|
||||||
headers = {
|
|
||||||
"language": language or "",
|
|
||||||
"domain": domain or "",
|
|
||||||
"eys-ext": f"{str(uuid.uuid4())}",
|
|
||||||
"tz": tz or "GMT+3",
|
|
||||||
"token": token,
|
|
||||||
}
|
|
||||||
event_cluster_matched = supers_users_list.match_event(
|
|
||||||
event_keys=[
|
|
||||||
"3f510dcf-9f84-4eb9-b919-f582f30adab1",
|
|
||||||
"9f403034-deba-4e1f-b43e-b25d3c808d39",
|
|
||||||
"b8ec6e64-286a-4f60-8554-7a3865454944",
|
|
||||||
]
|
|
||||||
)
|
|
||||||
response.headers["X-Header"] = "Test Header GET"
|
|
||||||
if runner_callable := event_cluster_matched.example_callable():
|
|
||||||
return runner_callable
|
|
||||||
raise ValueError("Event key not found or multiple matches found")
|
|
||||||
|
|
||||||
|
|
||||||
@user_route.post(
|
|
||||||
path="/create",
|
|
||||||
description="Test Template Route with Post Method",
|
|
||||||
operation_id="08d4b572-1584-47bb-aa42-8d068e5514e7",
|
|
||||||
)
|
|
||||||
def test_template_post(request: Request, response: Response):
|
|
||||||
"""
|
|
||||||
Test Template Route with Post Method
|
|
||||||
"""
|
|
||||||
event_cluster_matched = supers_users_list.match_event(
|
|
||||||
event_keys=[
|
|
||||||
"3f510dcf-9f84-4eb9-b919-f582f30adab1",
|
|
||||||
"9f403034-deba-4e1f-b43e-b25d3c808d39",
|
|
||||||
"b8ec6e64-286a-4f60-8554-7a3865454944",
|
|
||||||
]
|
|
||||||
)
|
|
||||||
response.headers["X-Header"] = "Test Header POST"
|
|
||||||
if runner_callable := event_cluster_matched.example_callable():
|
|
||||||
return runner_callable
|
|
||||||
raise ValueError("Event key not found or multiple matches found")
|
|
||||||
|
|
||||||
|
|
||||||
@user_route.post(
|
|
||||||
path="/update",
|
|
||||||
description="Test Template Route with Post Method",
|
|
||||||
operation_id="b641236a-928d-4f19-a1d2-5edf611d1e56",
|
|
||||||
)
|
|
||||||
def test_template_post(request: Request, response: Response):
|
|
||||||
"""
|
|
||||||
Test Template Route with Post Method
|
|
||||||
"""
|
|
||||||
event_cluster_matched = supers_users_list.match_event(
|
|
||||||
event_keys=[
|
|
||||||
"3f510dcf-9f84-4eb9-b919-f582f30adab1",
|
|
||||||
"9f403034-deba-4e1f-b43e-b25d3c808d39",
|
|
||||||
"b8ec6e64-286a-4f60-8554-7a3865454944",
|
|
||||||
]
|
|
||||||
)
|
|
||||||
response.headers["X-Header"] = "Test Header POST"
|
|
||||||
if runner_callable := event_cluster_matched.example_callable():
|
|
||||||
return runner_callable
|
|
||||||
raise ValueError("Event key not found or multiple matches found")
|
|
||||||
@@ -1,12 +0,0 @@
|
|||||||
from .people.event import (
|
|
||||||
people_event_cluster_list,
|
|
||||||
people_event_cluster_update,
|
|
||||||
people_event_cluster_create,
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
__all__ = [
|
|
||||||
"people_event_cluster_list",
|
|
||||||
"people_event_cluster_update",
|
|
||||||
"people_event_cluster_create",
|
|
||||||
]
|
|
||||||
@@ -1,33 +0,0 @@
|
|||||||
from ApiServices.IdentityService.initializer.event_clusters import EventCluster, Event
|
|
||||||
|
|
||||||
|
|
||||||
supers_users_list = Event(
|
|
||||||
name="supers_people_list",
|
|
||||||
key="341b394f-9f11-4abb-99e7-4b27fa6bf012",
|
|
||||||
request_validator=None, # TODO: Add request validator
|
|
||||||
response_validator=None, # TODO: Add response validator
|
|
||||||
description="Example event description",
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
def supers_people_list_callable():
|
|
||||||
"""
|
|
||||||
Example callable method
|
|
||||||
"""
|
|
||||||
return {
|
|
||||||
"completed": True,
|
|
||||||
"message": "Example callable method 2",
|
|
||||||
"info": {
|
|
||||||
"host": "example_host",
|
|
||||||
"user_agent": "example_user_agent",
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
supers_users_list.event_callable = supers_people_list_callable
|
|
||||||
|
|
||||||
people_event_cluster_list = EventCluster(
|
|
||||||
endpoint_uu_id="f102db46-031a-43e4-966a-dae6896f985b"
|
|
||||||
)
|
|
||||||
|
|
||||||
people_event_cluster_list.add_event([supers_users_list])
|
|
||||||
@@ -1,53 +0,0 @@
|
|||||||
from pydantic import BaseModel
|
|
||||||
|
|
||||||
"""
|
|
||||||
"sex_code": "M",
|
|
||||||
"country_code": "TR",
|
|
||||||
"created_at": "2025-04-13 10:03:32 +00:00",
|
|
||||||
"father_name": "Father",
|
|
||||||
"birth_place": "Ankara",
|
|
||||||
"updated_credentials_token": null,
|
|
||||||
"cryp_uu_id": null,
|
|
||||||
"mother_name": "Mother",
|
|
||||||
"expiry_starts": "2025-04-13 10:03:32 +00:00",
|
|
||||||
"confirmed_credentials_token": null,
|
|
||||||
"surname": "Karatay",
|
|
||||||
"firstname": "Berkay Super User",
|
|
||||||
"birth_date": "1990-01-07 00:00:00 +00:00",
|
|
||||||
"expiry_ends": "2099-12-31 00:00:00 +00:00",
|
|
||||||
"is_confirmed": true,
|
|
||||||
"is_email_send": false,
|
|
||||||
"tax_no": "1231231232",
|
|
||||||
"person_ref": "",
|
|
||||||
"active": true,
|
|
||||||
"deleted": false,
|
|
||||||
"updated_at": "2025-04-13 10:03:32 +00:00",
|
|
||||||
"uu_id": "b5b6e68f-a4d0-4d64-aa18-634671cb1299",
|
|
||||||
"middle_name": "",
|
|
||||||
"created_credentials_token": null,
|
|
||||||
"person_tag": "BSU-System",
|
|
||||||
"is_notification_send": false
|
|
||||||
"""
|
|
||||||
|
|
||||||
|
|
||||||
class REQUESTAWMXNTKMGPPOJWRCTZUBADNFLQDBDYVQAORFAVCSXUUHEBQHCEPCSKFBADBODFDBPYKOVINV(
|
|
||||||
BaseModel
|
|
||||||
):
|
|
||||||
uu_id: str
|
|
||||||
created_at: str
|
|
||||||
updated_at: str
|
|
||||||
person_tag: str
|
|
||||||
expiry_starts: str
|
|
||||||
expiry_ends: str
|
|
||||||
firstname: str
|
|
||||||
middle_name: str
|
|
||||||
surname: str
|
|
||||||
birth_date: str
|
|
||||||
birth_place: str
|
|
||||||
sex_code: str
|
|
||||||
country_code: str
|
|
||||||
tax_no: str
|
|
||||||
active: bool
|
|
||||||
deleted: bool
|
|
||||||
is_confirmed: bool
|
|
||||||
is_notification_send: bool
|
|
||||||
@@ -9,17 +9,35 @@ from init_services import create_modules_and_services_and_actions
|
|||||||
from init_address import create_one_address
|
from init_address import create_one_address
|
||||||
from init_occ_defaults import create_occupant_defaults
|
from init_occ_defaults import create_occupant_defaults
|
||||||
|
|
||||||
set_alembic = bool(os.getenv("set_alembic", 0))
|
set_alembic = bool(int(os.getenv("SET_ALEMBIC"), 0))
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
|
print(f"Set alembic: {set_alembic}")
|
||||||
|
|
||||||
with get_db() as db_session:
|
with get_db() as db_session:
|
||||||
if set_alembic:
|
if set_alembic:
|
||||||
generate_alembic(session=db_session)
|
generate_alembic(session=db_session)
|
||||||
|
try:
|
||||||
create_one_address(db_session=db_session)
|
create_one_address(db_session=db_session)
|
||||||
init_api_enums_build_types(db_session=db_session)
|
except Exception as e:
|
||||||
create_application_defaults(db_session=db_session)
|
print(f"Error creating address: {e}")
|
||||||
create_occupant_types_defaults(db_session=db_session)
|
try:
|
||||||
create_modules_and_services_and_actions(db_session=db_session)
|
init_api_enums_build_types(db_session=db_session)
|
||||||
create_occupant_defaults(db_session=db_session)
|
except Exception as e:
|
||||||
|
print(f"Error creating enums: {e}")
|
||||||
|
try:
|
||||||
|
create_application_defaults(db_session=db_session)
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error creating application defaults: {e}")
|
||||||
|
try:
|
||||||
|
create_occupant_types_defaults(db_session=db_session)
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error creating occupant types defaults: {e}")
|
||||||
|
try:
|
||||||
|
create_modules_and_services_and_actions(db_session=db_session)
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error creating modules and services and actions: {e}")
|
||||||
|
try:
|
||||||
|
create_occupant_defaults(db_session=db_session)
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error creating occupant defaults: {e}")
|
||||||
|
|||||||
@@ -444,14 +444,29 @@ def create_application_defaults(db_session):
|
|||||||
f"{str(company_management.uu_id)}*Domain",
|
f"{str(company_management.uu_id)}*Domain",
|
||||||
)
|
)
|
||||||
with mongo_handler.collection(collection_name) as mongo_engine:
|
with mongo_handler.collection(collection_name) as mongo_engine:
|
||||||
mongo_engine.insert_one(
|
existing_record = mongo_engine.find_one(
|
||||||
document={
|
{"user_uu_id": str(gen_manager_user.uu_id)}
|
||||||
"user_uu_id": str(gen_manager_user.uu_id),
|
|
||||||
"other_domains_list": [main_domain],
|
|
||||||
"main_domain": main_domain,
|
|
||||||
"modified_at": arrow.now().timestamp(),
|
|
||||||
}
|
|
||||||
)
|
)
|
||||||
|
if not existing_record:
|
||||||
|
mongo_engine.insert_one(
|
||||||
|
document={
|
||||||
|
"user_uu_id": str(gen_manager_user.uu_id),
|
||||||
|
"other_domains_list": [main_domain],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
mongo_engine.update_one(
|
||||||
|
{"user_uu_id": str(gen_manager_user.uu_id)},
|
||||||
|
{
|
||||||
|
"$set": {
|
||||||
|
"other_domains_list": [main_domain],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
app_manager_user = Users.find_or_create(
|
app_manager_user = Users.find_or_create(
|
||||||
person_id=app_manager.id,
|
person_id=app_manager.id,
|
||||||
@@ -472,14 +487,29 @@ def create_application_defaults(db_session):
|
|||||||
app_manager_user.password_token = PasswordModule.generate_refresher_token()
|
app_manager_user.password_token = PasswordModule.generate_refresher_token()
|
||||||
|
|
||||||
with mongo_handler.collection(collection_name) as mongo_engine:
|
with mongo_handler.collection(collection_name) as mongo_engine:
|
||||||
mongo_engine.insert_one(
|
existing_record = mongo_engine.find_one(
|
||||||
document={
|
{"user_uu_id": str(app_manager_user.uu_id)}
|
||||||
"user_uu_id": str(app_manager_user.uu_id),
|
|
||||||
"other_domains_list": [main_domain],
|
|
||||||
"main_domain": main_domain,
|
|
||||||
"modified_at": arrow.now().timestamp(),
|
|
||||||
}
|
|
||||||
)
|
)
|
||||||
|
if not existing_record:
|
||||||
|
mongo_engine.insert_one(
|
||||||
|
document={
|
||||||
|
"user_uu_id": str(app_manager_user.uu_id),
|
||||||
|
"other_domains_list": [main_domain],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
mongo_engine.update_one(
|
||||||
|
{"user_uu_id": str(app_manager_user.uu_id)},
|
||||||
|
{
|
||||||
|
"$set": {
|
||||||
|
"other_domains_list": [main_domain],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
sup_manager_employee = Users.find_or_create(
|
sup_manager_employee = Users.find_or_create(
|
||||||
person_id=sup_manager.id,
|
person_id=sup_manager.id,
|
||||||
@@ -502,14 +532,32 @@ def create_application_defaults(db_session):
|
|||||||
sup_manager_employee.password_expiry_begins = str(arrow.now())
|
sup_manager_employee.password_expiry_begins = str(arrow.now())
|
||||||
sup_manager_employee.password_token = PasswordModule.generate_refresher_token()
|
sup_manager_employee.password_token = PasswordModule.generate_refresher_token()
|
||||||
with mongo_handler.collection(collection_name) as mongo_engine:
|
with mongo_handler.collection(collection_name) as mongo_engine:
|
||||||
mongo_engine.insert_one(
|
existing_record = mongo_engine.find_one(
|
||||||
document={
|
{"user_uu_id": str(sup_manager_employee.uu_id)}
|
||||||
"user_uu_id": str(sup_manager_employee.uu_id),
|
|
||||||
"other_domains_list": [main_domain],
|
|
||||||
"main_domain": main_domain,
|
|
||||||
"modified_at": arrow.now().timestamp(),
|
|
||||||
}
|
|
||||||
)
|
)
|
||||||
|
if not existing_record:
|
||||||
|
print("insert sup existing record", existing_record)
|
||||||
|
mongo_engine.insert_one(
|
||||||
|
document={
|
||||||
|
"user_uu_id": str(sup_manager_employee.uu_id),
|
||||||
|
"other_domains_list": [main_domain, "management.com.tr"],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
print("update sup existing record", existing_record)
|
||||||
|
# Optionally update the existing record if needed
|
||||||
|
mongo_engine.update_one(
|
||||||
|
{"user_uu_id": str(sup_manager_employee.uu_id)},
|
||||||
|
{
|
||||||
|
"$set": {
|
||||||
|
"other_domains_list": [main_domain, "management.com.tr"],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
},
|
||||||
|
)
|
||||||
db_session.commit()
|
db_session.commit()
|
||||||
|
|
||||||
print("All Defaults Create is now completed")
|
print("All Defaults Create is now completed")
|
||||||
|
|||||||
@@ -239,34 +239,75 @@ def create_occupant_defaults(db_session):
|
|||||||
user_tenant.password_token = PasswordModule.generate_refresher_token()
|
user_tenant.password_token = PasswordModule.generate_refresher_token()
|
||||||
|
|
||||||
with mongo_handler.collection(collection_name) as mongo_engine:
|
with mongo_handler.collection(collection_name) as mongo_engine:
|
||||||
mongo_engine.insert_one(
|
existing_record = mongo_engine.find_one(
|
||||||
document={
|
{"user_uu_id": str(user_build_manager.uu_id)}
|
||||||
"user_uu_id": str(user_build_manager.uu_id),
|
|
||||||
"other_domains_list": [main_domain],
|
|
||||||
"main_domain": main_domain,
|
|
||||||
"modified_at": arrow.now().timestamp(),
|
|
||||||
}
|
|
||||||
)
|
)
|
||||||
|
if not existing_record:
|
||||||
|
mongo_engine.insert_one(
|
||||||
|
document={
|
||||||
|
"user_uu_id": str(user_build_manager.uu_id),
|
||||||
|
"other_domains_list": [main_domain],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
mongo_engine.update_one(
|
||||||
|
{"user_uu_id": str(user_build_manager.uu_id)},
|
||||||
|
{
|
||||||
|
"$set": {
|
||||||
|
"other_domains_list": [main_domain],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
with mongo_handler.collection(collection_name) as mongo_engine:
|
with mongo_handler.collection(collection_name) as mongo_engine:
|
||||||
mongo_engine.insert_one(
|
existing_record = mongo_engine.find_one({"user_uu_id": str(user_owner.uu_id)})
|
||||||
document={
|
if not existing_record:
|
||||||
"user_uu_id": str(user_owner.uu_id),
|
mongo_engine.insert_one(
|
||||||
"other_domains_list": [main_domain],
|
document={
|
||||||
"main_domain": main_domain,
|
"user_uu_id": str(user_owner.uu_id),
|
||||||
"modified_at": arrow.now().timestamp(),
|
"other_domains_list": [main_domain],
|
||||||
}
|
"main_domain": main_domain,
|
||||||
)
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
mongo_engine.update_one(
|
||||||
|
{"user_uu_id": str(user_owner.uu_id)},
|
||||||
|
{
|
||||||
|
"$set": {
|
||||||
|
"other_domains_list": [main_domain],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
with mongo_handler.collection(collection_name) as mongo_engine:
|
with mongo_handler.collection(collection_name) as mongo_engine:
|
||||||
mongo_engine.insert_one(
|
existing_record = mongo_engine.find_one({"user_uu_id": str(user_tenant.uu_id)})
|
||||||
document={
|
if not existing_record:
|
||||||
"user_uu_id": str(user_tenant.uu_id),
|
mongo_engine.insert_one(
|
||||||
"other_domains_list": [main_domain],
|
document={
|
||||||
"main_domain": main_domain,
|
"user_uu_id": str(user_tenant.uu_id),
|
||||||
"modified_at": arrow.now().timestamp(),
|
"other_domains_list": [main_domain],
|
||||||
}
|
"main_domain": main_domain,
|
||||||
)
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
mongo_engine.update_one(
|
||||||
|
{"user_uu_id": str(user_tenant.uu_id)},
|
||||||
|
{
|
||||||
|
"$set": {
|
||||||
|
"other_domains_list": [main_domain],
|
||||||
|
"main_domain": main_domain,
|
||||||
|
"modified_at": arrow.now().timestamp(),
|
||||||
|
}
|
||||||
|
},
|
||||||
|
)
|
||||||
|
|
||||||
created_build_living_space_prs = BuildLivingSpace.find_or_create(
|
created_build_living_space_prs = BuildLivingSpace.find_or_create(
|
||||||
build_id=created_build.id,
|
build_id=created_build.id,
|
||||||
|
|||||||
29
ApiServices/ManagementService/Dockerfile
Normal file
29
ApiServices/ManagementService/Dockerfile
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
FROM python:3.12-slim
|
||||||
|
|
||||||
|
WORKDIR /
|
||||||
|
|
||||||
|
# Install system dependencies and Poetry
|
||||||
|
RUN apt-get update && apt-get install -y --no-install-recommends gcc && rm -rf /var/lib/apt/lists/* && pip install --no-cache-dir poetry
|
||||||
|
|
||||||
|
# Copy Poetry configuration
|
||||||
|
COPY /pyproject.toml ./pyproject.toml
|
||||||
|
|
||||||
|
# Configure Poetry and install dependencies with optimizations
|
||||||
|
RUN poetry config virtualenvs.create false && poetry install --no-interaction --no-ansi --no-root --only main \
|
||||||
|
&& pip cache purge && rm -rf ~/.cache/pypoetry
|
||||||
|
|
||||||
|
# Copy application code
|
||||||
|
COPY /ApiControllers /ApiControllers
|
||||||
|
COPY /ApiDefaults /ApiDefaults
|
||||||
|
COPY /Controllers /Controllers
|
||||||
|
COPY /Schemas /Schemas
|
||||||
|
|
||||||
|
COPY /ApiServices/ManagementService/Endpoints /ApiDefaults/Endpoints
|
||||||
|
COPY /ApiServices/ManagementService/Events /ApiDefaults/Events
|
||||||
|
COPY /ApiServices/ManagementService/Validations /ApiDefaults/Validations
|
||||||
|
|
||||||
|
# Set Python path to include app directory
|
||||||
|
ENV PYTHONPATH=/ PYTHONUNBUFFERED=1 PYTHONDONTWRITEBYTECODE=1
|
||||||
|
|
||||||
|
# Run the application using the configured uvicorn server
|
||||||
|
CMD ["poetry", "run", "python", "ApiDefaults/app.py"]
|
||||||
1
ApiServices/ManagementService/Endpoints/__init__.py
Normal file
1
ApiServices/ManagementService/Endpoints/__init__.py
Normal file
@@ -0,0 +1 @@
|
|||||||
|
|
||||||
197
ApiServices/ManagementService/Endpoints/application/route.py
Normal file
197
ApiServices/ManagementService/Endpoints/application/route.py
Normal file
@@ -0,0 +1,197 @@
|
|||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
from typing import Any
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly, Pagination, PaginationResult
|
||||||
|
from Controllers.Postgres.response import EndpointResponse, CreateEndpointResponse
|
||||||
|
from Schemas import Applications
|
||||||
|
from Validations.application.validations import RequestApplication
|
||||||
|
from Events.application.cluster import ApplicationRouterCluster
|
||||||
|
from Validations.application.validations import AddRemoveService
|
||||||
|
|
||||||
|
|
||||||
|
# Create API router
|
||||||
|
application_route = APIRouter(prefix="/application", tags=["Application Management"])
|
||||||
|
|
||||||
|
|
||||||
|
@application_route.post(
|
||||||
|
path="/list/all",
|
||||||
|
description="List all applications endpoint",
|
||||||
|
operation_id="fe30481d-802c-4490-897f-a4e95310e6bc",
|
||||||
|
)
|
||||||
|
def application_list_all_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List all applications with pagination and filtering options
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ApplicationRouterCluster.get_event_cluster("ApplicationListAll")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(list_options=data)
|
||||||
|
|
||||||
|
|
||||||
|
@application_route.post(
|
||||||
|
path="/list/available",
|
||||||
|
description="List available applications endpoint",
|
||||||
|
operation_id="7492bb02-a074-4320-b58c-4bc7d9fba3a6",
|
||||||
|
)
|
||||||
|
def application_list_available_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List available applications with pagination and filtering options
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ApplicationRouterCluster.get_event_cluster("ApplicationListAvailable")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(list_options=data)
|
||||||
|
|
||||||
|
|
||||||
|
@application_route.post(
|
||||||
|
path="/list/appended",
|
||||||
|
description="List appended applications endpoint",
|
||||||
|
operation_id="ea7bbd58-da09-407c-a630-c324e0272385",
|
||||||
|
)
|
||||||
|
def application_list_appended_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List appended applications with pagination and filtering options
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ApplicationRouterCluster.get_event_cluster("ApplicationListAppended")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(list_options=data)
|
||||||
|
|
||||||
|
|
||||||
|
@application_route.post(
|
||||||
|
path="/register/service",
|
||||||
|
description="Register event to service endpoint",
|
||||||
|
operation_id="92e0870f-f8bb-4879-ba03-c2901cc70ecc",
|
||||||
|
)
|
||||||
|
def application_register_service_route(
|
||||||
|
data: AddRemoveService,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Register event to service
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ApplicationRouterCluster.get_event_cluster("ApplicationRegisterService")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@application_route.post(
|
||||||
|
path="/unregister/service",
|
||||||
|
description="Unregister event from service endpoint",
|
||||||
|
operation_id="7fa1a183-4c99-4746-b675-148f65ad7ba7",
|
||||||
|
)
|
||||||
|
def application_unregister_service_route(
|
||||||
|
data: AddRemoveService,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Unregister event from service
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ApplicationRouterCluster.get_event_cluster("ApplicationUnRegisterService")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@application_route.post(
|
||||||
|
path="/create",
|
||||||
|
description="Create application endpoint",
|
||||||
|
operation_id="5570be78-030a-438e-8674-7e751447608b",
|
||||||
|
)
|
||||||
|
def application_create_route(
|
||||||
|
data: RequestApplication,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Create a new application
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ApplicationRouterCluster.get_event_cluster("ApplicationCreate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@application_route.post(
|
||||||
|
path="/update/{application_uuid}",
|
||||||
|
description="Update application endpoint",
|
||||||
|
operation_id="87cd4515-73dd-4d11-a01f-562e221d973c",
|
||||||
|
)
|
||||||
|
def application_update_route(
|
||||||
|
data: RequestApplication,
|
||||||
|
application_uuid: str,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Update an existing application
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ApplicationRouterCluster.get_event_cluster("ApplicationUpdate")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data, uu_id=application_uuid)
|
||||||
|
|
||||||
|
|
||||||
|
@application_route.post(
|
||||||
|
path="/bind/employee",
|
||||||
|
description="Bind application to employee endpoint",
|
||||||
|
operation_id="2bab94fa-becb-4d8e-80f1-f4631119a521",
|
||||||
|
)
|
||||||
|
def application_bind_employee_route(
|
||||||
|
data: Any,
|
||||||
|
headers: CommonHeaders,
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Bind application to employee endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ApplicationRouterCluster.get_event_cluster("ApplicationBindEmployee")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@application_route.post(
|
||||||
|
path="/bind/occupant",
|
||||||
|
description="Bind application to occupant endpoint",
|
||||||
|
operation_id="fccf1a59-0650-4e5c-ba8d-f389dadce01c",
|
||||||
|
)
|
||||||
|
def application_bind_occupant_route(
|
||||||
|
data: Any,
|
||||||
|
headers: CommonHeaders,
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Bind application to occupant endpoint
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ApplicationRouterCluster.get_event_cluster("ApplicationBindOccupant")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
142
ApiServices/ManagementService/Endpoints/event_endpoints/route.py
Normal file
142
ApiServices/ManagementService/Endpoints/event_endpoints/route.py
Normal file
@@ -0,0 +1,142 @@
|
|||||||
|
from typing import Any
|
||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly, Pagination, PaginationResult
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Validations.service_endpoints.validations import (
|
||||||
|
Event2Employee,
|
||||||
|
Event2Occupant,
|
||||||
|
AddRemoveService,
|
||||||
|
)
|
||||||
|
from Events.event_endpoints.cluster import EventsEndpointRouterCluster
|
||||||
|
|
||||||
|
# Create API router
|
||||||
|
event_endpoint_route = APIRouter(prefix="/events", tags=["Event Actions"])
|
||||||
|
|
||||||
|
|
||||||
|
@event_endpoint_route.post(
|
||||||
|
path="/list/available",
|
||||||
|
description="List available events endpoint",
|
||||||
|
operation_id="0659d5e4-671f-466c-a84f-47a1290a6f0d",
|
||||||
|
)
|
||||||
|
def event_list_available_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List available events with pagination and filtering options
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = EventsEndpointRouterCluster.get_event_cluster("EventsListAvailable")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(list_options=data)
|
||||||
|
|
||||||
|
|
||||||
|
@event_endpoint_route.post(
|
||||||
|
path="/list/appended",
|
||||||
|
description="List appended events endpoint",
|
||||||
|
operation_id="4d563973-cdcd-44e1-94e0-4262ffb456a1",
|
||||||
|
)
|
||||||
|
def event_list_appended_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List events with pagination and filtering options
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = EventsEndpointRouterCluster.get_event_cluster("EventsListAppended")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(list_options=data)
|
||||||
|
|
||||||
|
|
||||||
|
@event_endpoint_route.post(
|
||||||
|
path="/register/service",
|
||||||
|
description="Register event to service endpoint",
|
||||||
|
operation_id="c89a2150-db4d-4a8f-b6ec-9e0f09625f76",
|
||||||
|
)
|
||||||
|
def event_register_service_route(
|
||||||
|
data: AddRemoveService,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Register event to service
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = EventsEndpointRouterCluster.get_event_cluster("EventRegisterService")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@event_endpoint_route.post(
|
||||||
|
path="/unregister/service",
|
||||||
|
description="Unregister event from service endpoint",
|
||||||
|
operation_id="2f16dc9e-de02-449d-9c3f-1a21f87e8794",
|
||||||
|
)
|
||||||
|
def event_unregister_service_route(
|
||||||
|
data: AddRemoveService,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Unregister event from service
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = EventsEndpointRouterCluster.get_event_cluster(
|
||||||
|
"EventUnregisterService"
|
||||||
|
)
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@event_endpoint_route.post(
|
||||||
|
path="/bind/extra/employee",
|
||||||
|
description="Bind event to employee extra endpoint",
|
||||||
|
operation_id="58ef3640-04ec-43f9-8f3e-f86be3ce4a24",
|
||||||
|
)
|
||||||
|
def event_bind_employee_extra_route(
|
||||||
|
data: Any,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Bind event to employee extra
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = EventsEndpointRouterCluster.get_event_cluster(
|
||||||
|
"EventBindEmployeeExtra"
|
||||||
|
)
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@event_endpoint_route.post(
|
||||||
|
path="/bind/extra/occupant",
|
||||||
|
description="Bind event to occupant extra endpoint",
|
||||||
|
operation_id="7794a550-3073-43e3-b0c5-80128f8d3e4b",
|
||||||
|
)
|
||||||
|
def event_bind_occupant_extra_route(
|
||||||
|
data: Any,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
Bind event to occupant extra
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = EventsEndpointRouterCluster.get_event_cluster(
|
||||||
|
"EventBindOccupantExtra"
|
||||||
|
)
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
25
ApiServices/ManagementService/Endpoints/routes.py
Normal file
25
ApiServices/ManagementService/Endpoints/routes.py
Normal file
@@ -0,0 +1,25 @@
|
|||||||
|
from fastapi import APIRouter
|
||||||
|
|
||||||
|
|
||||||
|
def get_routes() -> list[APIRouter]:
|
||||||
|
from .application.route import application_route
|
||||||
|
from .service_endpoints.route import service_endpoint_route
|
||||||
|
from .service_managements.route import service_management_route
|
||||||
|
from .event_endpoints.route import event_endpoint_route
|
||||||
|
|
||||||
|
return [
|
||||||
|
application_route,
|
||||||
|
service_endpoint_route,
|
||||||
|
service_management_route,
|
||||||
|
event_endpoint_route,
|
||||||
|
]
|
||||||
|
|
||||||
|
|
||||||
|
def get_safe_endpoint_urls() -> list[tuple[str, str]]:
|
||||||
|
return [
|
||||||
|
("/", "GET"),
|
||||||
|
("/docs", "GET"),
|
||||||
|
("/redoc", "GET"),
|
||||||
|
("/openapi.json", "GET"),
|
||||||
|
("/metrics", "GET"),
|
||||||
|
]
|
||||||
@@ -0,0 +1,52 @@
|
|||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly, Pagination, PaginationResult
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Events.service_endpoints.cluster import ServiceEndpointRouterCluster
|
||||||
|
|
||||||
|
|
||||||
|
# Create API router
|
||||||
|
service_endpoint_route = APIRouter(prefix="/service", tags=["Service Actions"])
|
||||||
|
|
||||||
|
|
||||||
|
@service_endpoint_route.post(
|
||||||
|
path="/list",
|
||||||
|
description="List services endpoint",
|
||||||
|
operation_id="f4e4d332-70b1-4121-9fcc-a08850b72aaa",
|
||||||
|
)
|
||||||
|
def service_list_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List services with pagination and filtering options
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ServiceEndpointRouterCluster.get_event_cluster("ServiceList")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
|
|
||||||
|
|
||||||
|
@service_endpoint_route.post(
|
||||||
|
path="/to/events",
|
||||||
|
description="List events of a service endpoint given service UUID",
|
||||||
|
operation_id="7b6b0c6a-e3db-4353-a7df-ea49d2a67f8a",
|
||||||
|
)
|
||||||
|
def service_to_events_route(
|
||||||
|
data: PaginateOnly,
|
||||||
|
headers: CommonHeaders = Depends(CommonHeaders.as_dependency),
|
||||||
|
):
|
||||||
|
"""
|
||||||
|
List events of a service given service UUID
|
||||||
|
"""
|
||||||
|
token_object = TokenProvider.get_dict_from_redis(token=headers.token)
|
||||||
|
event_founder_dict = dict(endpoint_code=headers.operation_id, token=token_object)
|
||||||
|
event_key = TokenProvider.retrieve_event_codes(**event_founder_dict)
|
||||||
|
FoundCluster = ServiceEndpointRouterCluster.get_event_cluster("ServiceToEvents")
|
||||||
|
event_cluster_matched = FoundCluster.match_event(event_key=event_key)
|
||||||
|
return event_cluster_matched.event_callable(data=data)
|
||||||
@@ -0,0 +1,26 @@
|
|||||||
|
from fastapi import APIRouter, Depends
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.default_validations import CommonHeaders
|
||||||
|
from ApiControllers.providers.token_provider import TokenProvider
|
||||||
|
|
||||||
|
from Controllers.Postgres.pagination import PaginateOnly, Pagination, PaginationResult
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Schemas import (
|
||||||
|
Services,
|
||||||
|
Employees,
|
||||||
|
Event2Employee,
|
||||||
|
Users,
|
||||||
|
Events,
|
||||||
|
Service2Events,
|
||||||
|
Applications,
|
||||||
|
Application2Employee,
|
||||||
|
Application2Occupant,
|
||||||
|
)
|
||||||
|
from Validations.application.validations import (
|
||||||
|
RequestApplication,
|
||||||
|
)
|
||||||
|
|
||||||
|
# Create API router
|
||||||
|
service_management_route = APIRouter(
|
||||||
|
prefix="/managements/service", tags=["Service Management"]
|
||||||
|
)
|
||||||
9
ApiServices/ManagementService/Events/__init__.py
Normal file
9
ApiServices/ManagementService/Events/__init__.py
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
from .service_endpoints.cluster import ServiceEndpointRouterCluster
|
||||||
|
from .event_endpoints.cluster import EventsEndpointRouterCluster
|
||||||
|
from .application.cluster import ApplicationRouterCluster
|
||||||
|
|
||||||
|
__all__ = [
|
||||||
|
"ServiceEndpointRouterCluster",
|
||||||
|
"EventsEndpointRouterCluster",
|
||||||
|
"ApplicationRouterCluster",
|
||||||
|
]
|
||||||
55
ApiServices/ManagementService/Events/application/cluster.py
Normal file
55
ApiServices/ManagementService/Events/application/cluster.py
Normal file
@@ -0,0 +1,55 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
ApplicationListAllEvent,
|
||||||
|
ApplicationListAvailableEvent,
|
||||||
|
ApplicationListAppendedEvent,
|
||||||
|
ApplicationRegisterServiceEvent,
|
||||||
|
ApplicationUnRegisterServiceEvent,
|
||||||
|
ApplicationCreateEvent,
|
||||||
|
ApplicationUpdateEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
ApplicationRouterCluster = RouterCluster(name="ApplicationRouterCluster")
|
||||||
|
|
||||||
|
ApplicationEventClusterListAll = EventCluster(
|
||||||
|
name="ApplicationListAll", endpoint_uu_id="fe30481d-802c-4490-897f-a4e95310e6bc"
|
||||||
|
)
|
||||||
|
ApplicationEventClusterListAll.add_event(ApplicationListAllEvent)
|
||||||
|
|
||||||
|
ApplicationEventClusterListAvailable = EventCluster(
|
||||||
|
name="ApplicationListAvailable", endpoint_uu_id="7492bb02-a074-4320-b58c-4bc7d9fba3a6"
|
||||||
|
)
|
||||||
|
ApplicationEventClusterListAvailable.add_event(ApplicationListAvailableEvent)
|
||||||
|
|
||||||
|
ApplicationEventClusterListAppended = EventCluster(
|
||||||
|
name="ApplicationListAppended", endpoint_uu_id="ea7bbd58-da09-407c-a630-c324e0272385"
|
||||||
|
)
|
||||||
|
ApplicationEventClusterListAppended.add_event(ApplicationListAppendedEvent)
|
||||||
|
|
||||||
|
ApplicationEventClusterRegisterService = EventCluster(
|
||||||
|
name="ApplicationRegisterService", endpoint_uu_id="92e0870f-f8bb-4879-ba03-c2901cc70ecc"
|
||||||
|
)
|
||||||
|
ApplicationEventClusterRegisterService.add_event(ApplicationRegisterServiceEvent)
|
||||||
|
|
||||||
|
ApplicationEventClusterUnregisterService = EventCluster(
|
||||||
|
name="ApplicationUnRegisterService", endpoint_uu_id="7fa1a183-4c99-4746-b675-148f65ad7ba7"
|
||||||
|
)
|
||||||
|
ApplicationEventClusterUnregisterService.add_event(ApplicationUnRegisterServiceEvent)
|
||||||
|
|
||||||
|
ApplicationEventClusterCreate = EventCluster(
|
||||||
|
name="ApplicationCreate", endpoint_uu_id="5570be78-030a-438e-8674-7e751447608b"
|
||||||
|
)
|
||||||
|
ApplicationEventClusterCreate.add_event(ApplicationCreateEvent)
|
||||||
|
|
||||||
|
ApplicationEventClusterUpdate = EventCluster(
|
||||||
|
name="ApplicationUpdate", endpoint_uu_id="87cd4515-73dd-4d11-a01f-562e221d973c"
|
||||||
|
)
|
||||||
|
ApplicationEventClusterUpdate.add_event(ApplicationUpdateEvent)
|
||||||
|
|
||||||
|
ApplicationRouterCluster.set_event_cluster(ApplicationEventClusterListAvailable)
|
||||||
|
ApplicationRouterCluster.set_event_cluster(ApplicationEventClusterListAppended)
|
||||||
|
ApplicationRouterCluster.set_event_cluster(ApplicationEventClusterListAll)
|
||||||
|
ApplicationRouterCluster.set_event_cluster(ApplicationEventClusterRegisterService)
|
||||||
|
ApplicationRouterCluster.set_event_cluster(ApplicationEventClusterUnregisterService)
|
||||||
|
ApplicationRouterCluster.set_event_cluster(ApplicationEventClusterCreate)
|
||||||
|
ApplicationRouterCluster.set_event_cluster(ApplicationEventClusterUpdate)
|
||||||
@@ -0,0 +1,320 @@
|
|||||||
|
from typing import Any
|
||||||
|
|
||||||
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
|
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Schemas import (
|
||||||
|
Applications,
|
||||||
|
Application2Employee,
|
||||||
|
Application2Occupant,
|
||||||
|
Service2Application,
|
||||||
|
Services,
|
||||||
|
)
|
||||||
|
|
||||||
|
# List all endpoint
|
||||||
|
ApplicationListAllEvent = Event(
|
||||||
|
name="application_list_all",
|
||||||
|
key="1971ce4d-4f59-4aa8-83e2-ca19d7da6d11",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users List all applications endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# List available endpoint
|
||||||
|
ApplicationListAvailableEvent = Event(
|
||||||
|
name="application_list_available",
|
||||||
|
key="d8e733f5-b53a-4c36-9082-12579bf9cc4a",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users List available applications endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# List appended endpoint
|
||||||
|
ApplicationListAppendedEvent = Event(
|
||||||
|
name="application_list_appended",
|
||||||
|
key="ea7bbd58-da09-407c-a630-c324e0272385",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users List appended applications endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Register application to service endpoint
|
||||||
|
ApplicationRegisterServiceEvent = Event(
|
||||||
|
name="application_register_service",
|
||||||
|
key="47d7cfc8-6004-4442-8357-16ceac5d9d18",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users Register application to service endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Unregister application to service endpoint
|
||||||
|
ApplicationUnRegisterServiceEvent = Event(
|
||||||
|
name="application_unregister_service",
|
||||||
|
key="d228ab26-0b74-440f-8f1f-8f40be5a22f2",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users Unregister application to service endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Create endpoint
|
||||||
|
ApplicationCreateEvent = Event(
|
||||||
|
name="application_create",
|
||||||
|
key="f53ca9aa-5536-4d77-9129-78d67e61db4a",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users Create applications endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Update endpoint
|
||||||
|
ApplicationUpdateEvent = Event(
|
||||||
|
name="application_update",
|
||||||
|
key="0e9a855e-4e69-44b5-8ac2-825daa32840c",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users Update applications endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def application_list_all_callable(list_options: PaginateOnly):
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
with Applications.new_session() as db_session:
|
||||||
|
if list_options.query:
|
||||||
|
applications_list = Applications.filter_all(*Applications.convert(list_options.query), db=db_session)
|
||||||
|
else:
|
||||||
|
applications_list = Applications.filter_all(db=db_session)
|
||||||
|
pagination = Pagination(data=applications_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(data=applications_list, pagination=pagination)
|
||||||
|
return EndpointResponse(message="MSG0003-LIST", pagination_result=pagination_result).response
|
||||||
|
|
||||||
|
|
||||||
|
ApplicationListAllEvent.event_callable = application_list_all_callable
|
||||||
|
|
||||||
|
|
||||||
|
def application_list_available_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
service_uu_id = list_options.query.get("service_uu_id__ilike", None)
|
||||||
|
if not service_uu_id:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-PARAM-MISSING",
|
||||||
|
"data": list_options.query,
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
list_options.query.pop("service_uu_id__ilike", None)
|
||||||
|
list_options.query.pop("service_uu_id", None)
|
||||||
|
with Applications.new_session() as db_session:
|
||||||
|
service2applications = Service2Application.filter_all(
|
||||||
|
*Service2Application.convert({"service_uu_id__ilike": service_uu_id}),
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
already_events = [
|
||||||
|
service_to_application.application_id for service_to_application in service2applications.data
|
||||||
|
]
|
||||||
|
if list_options.query:
|
||||||
|
applications_list = Applications.filter_all(
|
||||||
|
*Applications.convert(list_options.query), Applications.id.not_in(already_events), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
applications_list = Applications.filter_all(Applications.id.not_in(already_events), db=db_session)
|
||||||
|
pagination = Pagination(data=applications_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(data=applications_list, pagination=pagination)
|
||||||
|
return EndpointResponse(message="MSG0003-LIST", pagination_result=pagination_result).response
|
||||||
|
|
||||||
|
|
||||||
|
ApplicationListAvailableEvent.event_callable = application_list_available_callable
|
||||||
|
|
||||||
|
|
||||||
|
def application_list_appended_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
Example callable method
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
service_uu_id = list_options.query.get("service_uu_id__ilike", None)
|
||||||
|
if not service_uu_id:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-PARAM-MISSING",
|
||||||
|
"data": list_options.query,
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
list_options.query.pop("service_uu_id__ilike", None)
|
||||||
|
list_options.query.pop("service_uu_id", None)
|
||||||
|
|
||||||
|
with Applications.new_session() as db_session:
|
||||||
|
service2applications = Service2Application.filter_all(
|
||||||
|
*Service2Application.convert({"service_uu_id__ilike": service_uu_id}),
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
already_events = [
|
||||||
|
service_to_application.application_id for service_to_application in service2applications.data
|
||||||
|
]
|
||||||
|
if list_options.query:
|
||||||
|
applications_list = Applications.filter_all(
|
||||||
|
*Applications.convert(list_options.query), Applications.id.in_(already_events), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
applications_list = Applications.filter_all(Applications.id.in_(already_events), db=db_session)
|
||||||
|
pagination = Pagination(data=applications_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(data=applications_list, pagination=pagination)
|
||||||
|
return EndpointResponse(message="MSG0003-LIST", pagination_result=pagination_result).response
|
||||||
|
|
||||||
|
|
||||||
|
ApplicationListAppendedEvent.event_callable = application_list_appended_callable
|
||||||
|
|
||||||
|
|
||||||
|
def application_create_callable(data: Any):
|
||||||
|
"""
|
||||||
|
Create a new application
|
||||||
|
"""
|
||||||
|
with Applications.new_session() as db_session:
|
||||||
|
created_application_dict = data.model_dump()
|
||||||
|
created_application = Applications.find_or_create(
|
||||||
|
db=db_session,
|
||||||
|
include_args=[Applications.application_for, Applications.application_code, Applications.site_url],
|
||||||
|
**created_application_dict,
|
||||||
|
)
|
||||||
|
if created_application.meta_data.created:
|
||||||
|
created_application.save(db=db_session)
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "MSG0001-INSERT",
|
||||||
|
"data": created_application,
|
||||||
|
}
|
||||||
|
return {
|
||||||
|
"completed": False,
|
||||||
|
"message": "MSG0002-ERROR",
|
||||||
|
"data": created_application,
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
ApplicationCreateEvent.event_callable = application_create_callable
|
||||||
|
|
||||||
|
|
||||||
|
def application_update_callable(data: Any, uu_id: str):
|
||||||
|
"""
|
||||||
|
Update an existing application
|
||||||
|
"""
|
||||||
|
with Applications.new_session() as db_session:
|
||||||
|
updated_application_dict = data.model_dump(
|
||||||
|
exclude_unset=True, exclude_none=True
|
||||||
|
)
|
||||||
|
found_application = Applications.filter_one(
|
||||||
|
Applications.uu_id == uu_id, db=db_session
|
||||||
|
).data
|
||||||
|
if not found_application:
|
||||||
|
return {
|
||||||
|
"completed": False,
|
||||||
|
"message": "MSG0002-FOUND",
|
||||||
|
"data": found_application,
|
||||||
|
}
|
||||||
|
updated_application = found_application.update(
|
||||||
|
db=db_session, **updated_application_dict
|
||||||
|
)
|
||||||
|
updated_application.save(db_session)
|
||||||
|
if updated_application.meta_data.updated:
|
||||||
|
return {
|
||||||
|
"completed": True,
|
||||||
|
"message": "MSG0003-UPDATE",
|
||||||
|
"data": updated_application,
|
||||||
|
}
|
||||||
|
return {
|
||||||
|
"completed": False,
|
||||||
|
"message": "MSG0003-UPDATE",
|
||||||
|
"data": updated_application,
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
ApplicationUpdateEvent.event_callable = application_update_callable
|
||||||
|
|
||||||
|
|
||||||
|
def application_register_service_callable(data: Any):
|
||||||
|
"""
|
||||||
|
Register an application to a service
|
||||||
|
"""
|
||||||
|
with Applications.new_session() as db_session:
|
||||||
|
event = Applications.filter_one_system(Applications.uu_id == data.application_uu_id, db=db_session)
|
||||||
|
if not event.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service = Services.filter_one_system(Services.uu_id == data.service_uu_id, db=db_session)
|
||||||
|
if not service.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service_to_application = Service2Application.find_or_create(
|
||||||
|
db=db_session,
|
||||||
|
include_args=[Service2Application.service_uu_id, Service2Application.application_uu_id],
|
||||||
|
service_id=service.data.id,
|
||||||
|
service_uu_id=str(service.data.uu_id),
|
||||||
|
application_id=event.data.id,
|
||||||
|
application_uu_id=str(event.data.uu_id),
|
||||||
|
application_code=event.data.application_code,
|
||||||
|
site_url=event.data.site_url,
|
||||||
|
is_confirmed=True,
|
||||||
|
)
|
||||||
|
if not service_to_application.meta_data.created:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-ALREADY-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service_to_application.save(db=db_session)
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-REGISTER",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": True,
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
ApplicationRegisterServiceEvent.event_callable = application_register_service_callable
|
||||||
|
|
||||||
|
|
||||||
|
def application_unregister_service_callable(data: Any):
|
||||||
|
"""
|
||||||
|
Unregister an application from a service
|
||||||
|
"""
|
||||||
|
with Applications.new_session() as db_session:
|
||||||
|
application = Applications.filter_one_system(Applications.uu_id == data.application_uu_id, db=db_session)
|
||||||
|
if not application.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service = Services.filter_one_system(Services.uu_id == data.service_uu_id, db=db_session)
|
||||||
|
if not service.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service_to_application = Service2Application.filter_one_system(
|
||||||
|
Service2Application.service_id == service.data.id,
|
||||||
|
Service2Application.application_id == application.data.id,
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
if not service_to_application.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service_to_application.query.delete()
|
||||||
|
db_session.commit()
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-UNREGISTER",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": True,
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
ApplicationUnRegisterServiceEvent.event_callable = application_unregister_service_callable
|
||||||
@@ -0,0 +1,54 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
EventsListAvailableEvent,
|
||||||
|
EventsListAppendedEvent,
|
||||||
|
EventRegisterServiceEvent,
|
||||||
|
EventUnRegisterServiceEvent,
|
||||||
|
EventBindEmployeeExtraEvent,
|
||||||
|
EventBindOccupantExtraEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
EventsEndpointRouterCluster = RouterCluster(name="EventsEndpointRouterCluster")
|
||||||
|
|
||||||
|
EventsEndpointEventClusterListAvailable = EventCluster(
|
||||||
|
name="EventsListAvailable", endpoint_uu_id="0659d5e4-671f-466c-a84f-47a1290a6f0d"
|
||||||
|
)
|
||||||
|
EventsEndpointEventClusterListAvailable.add_event(EventsListAvailableEvent)
|
||||||
|
|
||||||
|
EventsEndpointEventClusterListAppended = EventCluster(
|
||||||
|
name="EventsListAppended", endpoint_uu_id="4d563973-cdcd-44e1-94e0-4262ffb456a1"
|
||||||
|
)
|
||||||
|
EventsEndpointEventClusterListAppended.add_event(EventsListAppendedEvent)
|
||||||
|
|
||||||
|
EventsEndpointEventClusterRegisterService = EventCluster(
|
||||||
|
name="EventRegisterService", endpoint_uu_id="c89a2150-db4d-4a8f-b6ec-9e0f09625f76"
|
||||||
|
)
|
||||||
|
EventsEndpointEventClusterRegisterService.add_event(EventRegisterServiceEvent)
|
||||||
|
|
||||||
|
EventsEndpointEventClusterUnregisterService = EventCluster(
|
||||||
|
name="EventUnregisterService", endpoint_uu_id="2f16dc9e-de02-449d-9c3f-1a21f87e8794"
|
||||||
|
)
|
||||||
|
EventsEndpointEventClusterUnregisterService.add_event(EventUnRegisterServiceEvent)
|
||||||
|
|
||||||
|
EventsEndpointEventClusterBindEmployeeExtra = EventCluster(
|
||||||
|
name="EventBindEmployeeExtra", endpoint_uu_id="58ef3640-04ec-43f9-8f3e-f86be3ce4a24"
|
||||||
|
)
|
||||||
|
EventsEndpointEventClusterBindEmployeeExtra.add_event(EventBindEmployeeExtraEvent)
|
||||||
|
|
||||||
|
EventsEndpointEventClusterBindOccupantExtra = EventCluster(
|
||||||
|
name="EventBindOccupantExtra", endpoint_uu_id="7794a550-3073-43e3-b0c5-80128f8d3e4b"
|
||||||
|
)
|
||||||
|
EventsEndpointEventClusterBindOccupantExtra.add_event(EventBindOccupantExtraEvent)
|
||||||
|
|
||||||
|
EventsEndpointRouterCluster.set_event_cluster(EventsEndpointEventClusterListAvailable)
|
||||||
|
EventsEndpointRouterCluster.set_event_cluster(EventsEndpointEventClusterListAppended)
|
||||||
|
EventsEndpointRouterCluster.set_event_cluster(EventsEndpointEventClusterRegisterService)
|
||||||
|
EventsEndpointRouterCluster.set_event_cluster(
|
||||||
|
EventsEndpointEventClusterUnregisterService
|
||||||
|
)
|
||||||
|
EventsEndpointRouterCluster.set_event_cluster(
|
||||||
|
EventsEndpointEventClusterBindEmployeeExtra
|
||||||
|
)
|
||||||
|
EventsEndpointRouterCluster.set_event_cluster(
|
||||||
|
EventsEndpointEventClusterBindOccupantExtra
|
||||||
|
)
|
||||||
@@ -0,0 +1,280 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
|
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from typing import Any
|
||||||
|
from Schemas import (
|
||||||
|
Events,
|
||||||
|
Event2Employee,
|
||||||
|
Event2Occupant,
|
||||||
|
Event2EmployeeExtra,
|
||||||
|
Event2OccupantExtra,
|
||||||
|
Service2Events,
|
||||||
|
Services,
|
||||||
|
)
|
||||||
|
|
||||||
|
# List available events endpoint
|
||||||
|
EventsListAvailableEvent = Event(
|
||||||
|
name="event_endpoint_list_available",
|
||||||
|
key="d39af512-ec71-4c0f-9b35-e53b0d06d3a4",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users List available events endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# List appended events endpoint
|
||||||
|
EventsListAppendedEvent = Event(
|
||||||
|
name="event_endpoint_list_appended",
|
||||||
|
key="bea77d6a-d99f-468b-9002-b3bda6bb6ad0",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users List appended events endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Event Register endpoint
|
||||||
|
EventRegisterServiceEvent = Event(
|
||||||
|
name="event_endpoint_register_service",
|
||||||
|
key="e18e7f89-5708-4a15-9258-99b0903ed43d",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users Register service endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Event Unregister endpoint
|
||||||
|
EventUnRegisterServiceEvent = Event(
|
||||||
|
name="service_endpoint_unregister_service",
|
||||||
|
key="4d693774-4857-435b-a63c-c39baebfe916",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users Unregister service endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Bind employee extra endpoint
|
||||||
|
EventBindEmployeeExtraEvent = Event(
|
||||||
|
name="service_endpoint_bind_employee_extra",
|
||||||
|
key="cd452928-4256-4fb4-b81e-0ca41d723616",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users Bind service to employee extra endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
# Bind occupant extra endpoint
|
||||||
|
EventBindOccupantExtraEvent = Event(
|
||||||
|
name="service_endpoint_bind_occupant_extra",
|
||||||
|
key="cb11a150-8049-45c9-8cf3-d5290ffd2e4a",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users Bind service to occupant extra endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def events_list_available_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
List available events with pagination and filtering options
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
service_uu_id = list_options.query.get("service_uu_id__ilike", None)
|
||||||
|
if not service_uu_id:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-PARAM-MISSING",
|
||||||
|
"data": list_options.query,
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
list_options.query.pop("service_uu_id__ilike", None)
|
||||||
|
list_options.query.pop("service_uu_id", None)
|
||||||
|
with Events.new_session() as db_session:
|
||||||
|
service2events = Service2Events.filter_all(
|
||||||
|
*Service2Events.convert({"service_uu_id__ilike": service_uu_id}),
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
already_events = [
|
||||||
|
service_to_event.event_id for service_to_event in service2events.data
|
||||||
|
]
|
||||||
|
if list_options.query:
|
||||||
|
events_list = Events.filter_all(
|
||||||
|
*Events.convert(list_options.query),
|
||||||
|
Events.id.not_in(already_events),
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
events_list = Events.filter_all(
|
||||||
|
Events.id.not_in(already_events), db=db_session
|
||||||
|
)
|
||||||
|
pagination = Pagination(data=events_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(data=events_list, pagination=pagination)
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST",
|
||||||
|
pagination_result=pagination_result,
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
EventsListAvailableEvent.event_callable = events_list_available_callable
|
||||||
|
|
||||||
|
|
||||||
|
def events_list_appended_callable(list_options: PaginateOnly):
|
||||||
|
"""
|
||||||
|
List appended events with pagination and filtering options
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**list_options.model_dump())
|
||||||
|
service_uu_id = list_options.query.get("service_uu_id__ilike", None)
|
||||||
|
if not service_uu_id:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-PARAM-MISSING",
|
||||||
|
"data": list_options.query,
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
list_options.query.pop("service_uu_id__ilike", None)
|
||||||
|
list_options.query.pop("service_uu_id", None)
|
||||||
|
with Events.new_session() as db_session:
|
||||||
|
service2events = Service2Events.filter_all(
|
||||||
|
*Service2Events.convert({"service_uu_id__ilike": service_uu_id}),
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
already_events = [
|
||||||
|
service_to_event.event_id for service_to_event in service2events.data
|
||||||
|
]
|
||||||
|
|
||||||
|
if list_options.query:
|
||||||
|
events_list = Events.filter_all(
|
||||||
|
*Events.convert(list_options.query),
|
||||||
|
Events.id.in_(already_events),
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
events_list = Events.filter_all(
|
||||||
|
Events.id.in_(already_events), db=db_session
|
||||||
|
)
|
||||||
|
pagination = Pagination(data=events_list)
|
||||||
|
pagination.change(**list_options.model_dump())
|
||||||
|
pagination_result = PaginationResult(data=events_list, pagination=pagination)
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST",
|
||||||
|
pagination_result=pagination_result,
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
EventsListAppendedEvent.event_callable = events_list_appended_callable
|
||||||
|
|
||||||
|
|
||||||
|
def event_register_service_callable(data: Any):
|
||||||
|
"""
|
||||||
|
Register event to service
|
||||||
|
"""
|
||||||
|
with Events.new_session() as db_session:
|
||||||
|
event = Events.filter_one_system(
|
||||||
|
Events.uu_id == data.event_uu_id, db=db_session
|
||||||
|
)
|
||||||
|
if not event.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service = Services.filter_one_system(
|
||||||
|
Services.uu_id == data.service_uu_id, db=db_session
|
||||||
|
)
|
||||||
|
if not service.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service_to_event = Service2Events.find_or_create(
|
||||||
|
db=db_session,
|
||||||
|
include_args=[
|
||||||
|
Service2Events.service_uu_id,
|
||||||
|
Service2Events.event_uu_id,
|
||||||
|
],
|
||||||
|
service_id=service.data.id,
|
||||||
|
event_id=event.data.id,
|
||||||
|
is_confirmed=True,
|
||||||
|
service_uu_id=str(service.data.uu_id),
|
||||||
|
event_uu_id=str(event.data.uu_id),
|
||||||
|
)
|
||||||
|
if not service_to_event.meta_data.created:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-ALREADY-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service_to_event.save(db=db_session)
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-REGISTER",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": True,
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
EventRegisterServiceEvent.event_callable = event_register_service_callable
|
||||||
|
|
||||||
|
|
||||||
|
def event_unregister_service_callable(data: Any):
|
||||||
|
"""
|
||||||
|
Unregister event from service
|
||||||
|
"""
|
||||||
|
with Events.new_session() as db_session:
|
||||||
|
event = Events.filter_one_system(
|
||||||
|
Events.uu_id == data.event_uu_id, db=db_session
|
||||||
|
)
|
||||||
|
if not event.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service = Services.filter_one_system(
|
||||||
|
Services.uu_id == data.service_uu_id, db=db_session
|
||||||
|
)
|
||||||
|
if not service.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service_to_event = Service2Events.filter_one_system(
|
||||||
|
Service2Events.service_id == service.data.id,
|
||||||
|
Service2Events.event_id == event.data.id,
|
||||||
|
db=db_session,
|
||||||
|
)
|
||||||
|
if not service_to_event.data:
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-NOT-FOUND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": False,
|
||||||
|
}
|
||||||
|
service_to_event.query.delete()
|
||||||
|
db_session.commit()
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-UNREGISTER",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": True,
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
EventUnRegisterServiceEvent.event_callable = event_unregister_service_callable
|
||||||
|
|
||||||
|
|
||||||
|
def event_bind_employee_extra_callable(data: Any):
|
||||||
|
"""
|
||||||
|
Bind event to employee extra
|
||||||
|
"""
|
||||||
|
return {
|
||||||
|
"message": "MSG0003-BIND",
|
||||||
|
"data": data.model_dump(),
|
||||||
|
"completed": True,
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
EventBindEmployeeExtraEvent.event_callable = event_bind_employee_extra_callable
|
||||||
|
|
||||||
|
|
||||||
|
def event_bind_occupant_extra_callable(data: Any):
|
||||||
|
"""
|
||||||
|
Bind event to occupant extra
|
||||||
|
"""
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-BIND",
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
EventBindOccupantExtraEvent.event_callable = event_bind_occupant_extra_callable
|
||||||
@@ -0,0 +1,19 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import EventCluster, RouterCluster
|
||||||
|
from .supers_events import (
|
||||||
|
ServiceEndpointListEvent,
|
||||||
|
ServiceEndpointToEventsEvent,
|
||||||
|
)
|
||||||
|
|
||||||
|
ServiceEndpointRouterCluster = RouterCluster(name="ServiceEndpointRouterCluster")
|
||||||
|
ServiceEndpointEventClusterList = EventCluster(
|
||||||
|
name="ServiceList", endpoint_uu_id="f4e4d332-70b1-4121-9fcc-a08850b72aaa"
|
||||||
|
)
|
||||||
|
ServiceEndpointEventClusterList.add_event(ServiceEndpointListEvent)
|
||||||
|
|
||||||
|
ServiceEndpointEventClusterToService = EventCluster(
|
||||||
|
name="ServiceToEvents", endpoint_uu_id="7b6b0c6a-e3db-4353-a7df-ea49d2a67f8a"
|
||||||
|
)
|
||||||
|
ServiceEndpointEventClusterToService.add_event(ServiceEndpointToEventsEvent)
|
||||||
|
|
||||||
|
ServiceEndpointRouterCluster.set_event_cluster(ServiceEndpointEventClusterList)
|
||||||
|
ServiceEndpointRouterCluster.set_event_cluster(ServiceEndpointEventClusterToService)
|
||||||
@@ -0,0 +1,69 @@
|
|||||||
|
from ApiControllers.abstracts.event_clusters import Event
|
||||||
|
from Controllers.Postgres.pagination import Pagination, PaginationResult, PaginateOnly
|
||||||
|
from Controllers.Postgres.response import EndpointResponse
|
||||||
|
from Schemas import Services, Service2Events
|
||||||
|
|
||||||
|
|
||||||
|
# List endpoint
|
||||||
|
ServiceEndpointListEvent = Event(
|
||||||
|
name="service_endpoint_list",
|
||||||
|
key="7da6ceac-925a-4faa-9cc5-3f34396b5684",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users List services endpoint",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def service_endpoint_list_callable(data: PaginateOnly):
|
||||||
|
"""
|
||||||
|
List services endpoint callable method
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**data.model_dump())
|
||||||
|
with Services.new_session() as db_session:
|
||||||
|
if data.query:
|
||||||
|
services_list = Services.filter_all_system(
|
||||||
|
*Services.convert(data.query), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
services_list = Services.filter_all_system(db=db_session)
|
||||||
|
pagination = Pagination(data=services_list)
|
||||||
|
pagination.change(**data.model_dump())
|
||||||
|
pagination_result = PaginationResult(data=services_list, pagination=pagination)
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST", pagination_result=pagination_result
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
ServiceEndpointListEvent.event_callable = service_endpoint_list_callable
|
||||||
|
|
||||||
|
# To events endpoint
|
||||||
|
ServiceEndpointToEventsEvent = Event(
|
||||||
|
name="service_endpoint_to_events",
|
||||||
|
key="7b6b0c6a-e3db-4353-a7df-ea49d2a67f8a",
|
||||||
|
request_validator=None, # TODO: Add request validator
|
||||||
|
response_validator=None, # TODO: Add response validator
|
||||||
|
description="Super Users List events of a service endpoint given service UUID",
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
|
def service_endpoint_to_events_callable(data: PaginateOnly):
|
||||||
|
"""
|
||||||
|
List events of a service given service UUID
|
||||||
|
"""
|
||||||
|
list_options = PaginateOnly(**data.model_dump())
|
||||||
|
with Service2Events.new_session() as db_session:
|
||||||
|
if data.query:
|
||||||
|
services_list = Service2Events.filter_all_system(
|
||||||
|
*Service2Events.convert(data.query), db=db_session
|
||||||
|
)
|
||||||
|
else:
|
||||||
|
services_list = Service2Events.filter_all_system(db=db_session)
|
||||||
|
pagination = Pagination(data=services_list)
|
||||||
|
pagination.change(**data.model_dump())
|
||||||
|
pagination_result = PaginationResult(data=services_list, pagination=pagination)
|
||||||
|
return EndpointResponse(
|
||||||
|
message="MSG0003-LIST", pagination_result=pagination_result
|
||||||
|
).response
|
||||||
|
|
||||||
|
|
||||||
|
ServiceEndpointToEventsEvent.event_callable = service_endpoint_to_events_callable
|
||||||
1
ApiServices/ManagementService/Validations/__init__.py
Normal file
1
ApiServices/ManagementService/Validations/__init__.py
Normal file
@@ -0,0 +1 @@
|
|||||||
|
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
from pydantic import BaseModel, Field
|
||||||
|
from typing import Optional
|
||||||
|
|
||||||
|
|
||||||
|
class RequestApplication(BaseModel):
|
||||||
|
"""Base model for application data"""
|
||||||
|
|
||||||
|
name: str = Field(..., description="Application name")
|
||||||
|
application_code: str = Field(..., description="Unique application code")
|
||||||
|
site_url: str = Field(..., description="Application site URL")
|
||||||
|
application_type: str = Field(
|
||||||
|
..., description="Application type (info, Dash, Admin)"
|
||||||
|
)
|
||||||
|
application_for: str = Field(..., description="Application for (EMP, OCC)")
|
||||||
|
description: Optional[str] = Field(None, description="Application description")
|
||||||
|
|
||||||
|
|
||||||
|
class AddRemoveService(BaseModel):
|
||||||
|
"""Base model for add/remove service data"""
|
||||||
|
|
||||||
|
application_uu_id: str = Field(..., description="Application UUID")
|
||||||
|
service_uu_id: str = Field(..., description="Service UUID")
|
||||||
@@ -0,0 +1,14 @@
|
|||||||
|
from pydantic import BaseModel
|
||||||
|
|
||||||
|
|
||||||
|
class Event2Employee(BaseModel):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class Event2Occupant(BaseModel):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
|
class AddRemoveService(BaseModel):
|
||||||
|
event_uu_id: str
|
||||||
|
service_uu_id: str
|
||||||
13
ApiServices/ManagementService/__init__.py
Normal file
13
ApiServices/ManagementService/__init__.py
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
from fastapi import APIRouter
|
||||||
|
|
||||||
|
# Import all routes
|
||||||
|
from ApiServices.ManagementService.Endpoints.application.route import application_route
|
||||||
|
|
||||||
|
# Create main router for ManagementService
|
||||||
|
management_service_router = APIRouter(prefix="/management", tags=["Management Service"])
|
||||||
|
|
||||||
|
# Include all routes
|
||||||
|
management_service_router.include_router(application_route)
|
||||||
|
|
||||||
|
# Export the router
|
||||||
|
__all__ = ["management_service_router"]
|
||||||
@@ -1,5 +0,0 @@
|
|||||||
from .template.event import template_event_cluster
|
|
||||||
|
|
||||||
__all__ = [
|
|
||||||
"template_event_cluster",
|
|
||||||
]
|
|
||||||
@@ -1,88 +0,0 @@
|
|||||||
class EventCluster:
|
|
||||||
|
|
||||||
def __init__(self, endpoint_uu_id: str):
|
|
||||||
self.endpoint_uu_id = endpoint_uu_id
|
|
||||||
self.events = []
|
|
||||||
|
|
||||||
def add_event(self, list_of_events: list["Event"]):
|
|
||||||
"""
|
|
||||||
Add an event to the cluster
|
|
||||||
"""
|
|
||||||
for event in list_of_events:
|
|
||||||
self.events.append(event)
|
|
||||||
self.events = list(set(self.events))
|
|
||||||
|
|
||||||
def get_event(self, event_key: str):
|
|
||||||
"""
|
|
||||||
Get an event by its key
|
|
||||||
"""
|
|
||||||
|
|
||||||
for event in self.events:
|
|
||||||
if event.key == event_key:
|
|
||||||
return event
|
|
||||||
return None
|
|
||||||
|
|
||||||
def set_events_to_database(self):
|
|
||||||
from Schemas import Events, EndpointRestriction
|
|
||||||
|
|
||||||
with Events.new_session() as db_session:
|
|
||||||
if to_save_endpoint := EndpointRestriction.filter_one(
|
|
||||||
EndpointRestriction.operation_uu_id == self.endpoint_uu_id,
|
|
||||||
db=db_session,
|
|
||||||
).data:
|
|
||||||
for event in self.events:
|
|
||||||
event_to_save_database = Events.find_or_create(
|
|
||||||
function_code=event.key,
|
|
||||||
function_class=event.name,
|
|
||||||
description=event.description,
|
|
||||||
endpoint_code=self.endpoint_uu_id,
|
|
||||||
endpoint_id=to_save_endpoint.id,
|
|
||||||
endpoint_uu_id=str(to_save_endpoint.uu_id),
|
|
||||||
is_confirmed=True,
|
|
||||||
active=True,
|
|
||||||
db=db_session,
|
|
||||||
)
|
|
||||||
if event_to_save_database.meta_data.created:
|
|
||||||
event_to_save_database.save(db=db_session)
|
|
||||||
print(
|
|
||||||
f"UUID: {event_to_save_database.uu_id} event is saved to {to_save_endpoint.uu_id}"
|
|
||||||
)
|
|
||||||
|
|
||||||
def match_event(self, event_keys: list[str]) -> "Event":
|
|
||||||
"""
|
|
||||||
Match an event by its key
|
|
||||||
"""
|
|
||||||
# print('set(event_keys)', set(event_keys))
|
|
||||||
# print('event.keys', set([event.key for event in self.events]))
|
|
||||||
intersection_of_key: set[str] = set(event_keys) & set(
|
|
||||||
[event.key for event in self.events]
|
|
||||||
)
|
|
||||||
if not len(intersection_of_key) == 1:
|
|
||||||
raise ValueError(
|
|
||||||
f"Event key not found or multiple matches found: {intersection_of_key}"
|
|
||||||
)
|
|
||||||
return self.get_event(event_key=list(intersection_of_key)[0])
|
|
||||||
|
|
||||||
|
|
||||||
class Event:
|
|
||||||
|
|
||||||
def __init__(
|
|
||||||
self,
|
|
||||||
name: str,
|
|
||||||
key: str,
|
|
||||||
request_validator: str = None,
|
|
||||||
response_validator: str = None,
|
|
||||||
description: str = "",
|
|
||||||
):
|
|
||||||
self.name = name
|
|
||||||
self.key = key
|
|
||||||
self.request_validator = request_validator
|
|
||||||
self.response_validator = response_validator
|
|
||||||
self.description = description
|
|
||||||
|
|
||||||
def event_callable(self):
|
|
||||||
"""
|
|
||||||
Example callable method
|
|
||||||
"""
|
|
||||||
print(self.name)
|
|
||||||
return {}
|
|
||||||
@@ -43,28 +43,28 @@ class EmailProcessingContext:
|
|||||||
if exc_type is not None or not self.success:
|
if exc_type is not None or not self.success:
|
||||||
# If an exception occurred or processing wasn't successful, mark as unread
|
# If an exception occurred or processing wasn't successful, mark as unread
|
||||||
try:
|
try:
|
||||||
if hasattr(self.email_message, 'mark_as_unread'):
|
if hasattr(self.email_message, "mark_as_unread"):
|
||||||
self.email_message.mark_as_unread()
|
self.email_message.mark_as_unread()
|
||||||
print(f"[EMAIL_SERVICE] Marked email as UNREAD due to processing error: {exc_val if exc_val else 'Unknown error'}")
|
print(
|
||||||
|
f"[EMAIL_SERVICE] Marked email as UNREAD due to processing error: {exc_val if exc_val else 'Unknown error'}"
|
||||||
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[EMAIL_SERVICE] Failed to mark email as unread: {str(e)}")
|
print(f"[EMAIL_SERVICE] Failed to mark email as unread: {str(e)}")
|
||||||
elif self.mark_as_read:
|
elif self.mark_as_read:
|
||||||
# If processing was successful and mark_as_read is True, ensure it's marked as read
|
# If processing was successful and mark_as_read is True, ensure it's marked as read
|
||||||
try:
|
try:
|
||||||
if hasattr(self.email_message, 'mark_as_read'):
|
if hasattr(self.email_message, "mark_as_read"):
|
||||||
self.email_message.mark_as_read()
|
self.email_message.mark_as_read()
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[EMAIL_SERVICE] Failed to mark email as read: {str(e)}")
|
print(f"[EMAIL_SERVICE] Failed to mark email as read: {str(e)}")
|
||||||
return False # Don't suppress exceptions
|
return False # Don't suppress exceptions
|
||||||
|
|
||||||
|
|
||||||
def publish_payload_to_redis(
|
def publish_payload_to_redis(payload, filename: str, mail_info: dict) -> bool:
|
||||||
payload, filename: str, mail_info: dict
|
|
||||||
) -> bool:
|
|
||||||
# Create message document
|
# Create message document
|
||||||
# Use base64 encoding for binary payloads to ensure proper transmission
|
# Use base64 encoding for binary payloads to ensure proper transmission
|
||||||
if isinstance(payload, bytes):
|
if isinstance(payload, bytes):
|
||||||
encoded_payload = base64.b64encode(payload).decode('utf-8')
|
encoded_payload = base64.b64encode(payload).decode("utf-8")
|
||||||
is_base64 = True
|
is_base64 = True
|
||||||
else:
|
else:
|
||||||
encoded_payload = payload
|
encoded_payload = payload
|
||||||
@@ -84,7 +84,9 @@ def publish_payload_to_redis(
|
|||||||
result = redis_pubsub.publisher.publish(REDIS_CHANNEL, message)
|
result = redis_pubsub.publisher.publish(REDIS_CHANNEL, message)
|
||||||
|
|
||||||
if result.status:
|
if result.status:
|
||||||
print(f"[EMAIL_SERVICE] Published message with filename: {filename} to channel: {REDIS_CHANNEL}")
|
print(
|
||||||
|
f"[EMAIL_SERVICE] Published message with filename: {filename} to channel: {REDIS_CHANNEL}"
|
||||||
|
)
|
||||||
return True
|
return True
|
||||||
else:
|
else:
|
||||||
print(f"[EMAIL_SERVICE] Publish error: {result.error}")
|
print(f"[EMAIL_SERVICE] Publish error: {result.error}")
|
||||||
@@ -136,7 +138,7 @@ def app():
|
|||||||
filter_mail = OR(FROM(Config.MAILBOX), FROM(Config.MAIN_MAIL))
|
filter_mail = OR(FROM(Config.MAILBOX), FROM(Config.MAIN_MAIL))
|
||||||
filter_print = f"{Config.MAILBOX} & {Config.MAIN_MAIL}"
|
filter_print = f"{Config.MAILBOX} & {Config.MAIN_MAIL}"
|
||||||
|
|
||||||
# Determine if this is the first run of the day
|
# Determine if this is the first run of the day
|
||||||
# Store last run date in a file
|
# Store last run date in a file
|
||||||
last_run_file = "/tmp/email_service_last_run.json"
|
last_run_file = "/tmp/email_service_last_run.json"
|
||||||
current_date = datetime.now().strftime("%Y-%m-%d")
|
current_date = datetime.now().strftime("%Y-%m-%d")
|
||||||
@@ -144,32 +146,42 @@ def app():
|
|||||||
|
|
||||||
try:
|
try:
|
||||||
if os.path.exists(last_run_file):
|
if os.path.exists(last_run_file):
|
||||||
with open(last_run_file, 'r') as f:
|
with open(last_run_file, "r") as f:
|
||||||
last_run_data = json.load(f)
|
last_run_data = json.load(f)
|
||||||
last_run_date = last_run_data.get('last_run_date')
|
last_run_date = last_run_data.get("last_run_date")
|
||||||
|
|
||||||
# If this is the first run of a new day, check 90 days
|
# If this is the first run of a new day, check 90 days
|
||||||
if last_run_date != current_date:
|
if last_run_date != current_date:
|
||||||
days_to_check = full_check
|
days_to_check = full_check
|
||||||
print(f"[EMAIL_SERVICE] First run of the day. Checking emails from the past {days_to_check} days")
|
print(
|
||||||
|
f"[EMAIL_SERVICE] First run of the day. Checking emails from the past {days_to_check} days"
|
||||||
|
)
|
||||||
else:
|
else:
|
||||||
print(f"[EMAIL_SERVICE] Subsequent run today. Checking emails from the past {days_to_check} days")
|
print(
|
||||||
|
f"[EMAIL_SERVICE] Subsequent run today. Checking emails from the past {days_to_check} days"
|
||||||
|
)
|
||||||
else:
|
else:
|
||||||
# If no last run file exists, this is the first run ever - check 90 days
|
# If no last run file exists, this is the first run ever - check 90 days
|
||||||
days_to_check = full_check
|
days_to_check = full_check
|
||||||
print(f"[EMAIL_SERVICE] First run detected. Checking emails from the past {days_to_check} days")
|
print(
|
||||||
|
f"[EMAIL_SERVICE] First run detected. Checking emails from the past {days_to_check} days"
|
||||||
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[EMAIL_SERVICE] Error reading last run file: {str(e)}. Using default of {days_to_check} days")
|
print(
|
||||||
|
f"[EMAIL_SERVICE] Error reading last run file: {str(e)}. Using default of {days_to_check} days"
|
||||||
|
)
|
||||||
|
|
||||||
# Update the last run file
|
# Update the last run file
|
||||||
try:
|
try:
|
||||||
with open(last_run_file, 'w') as f:
|
with open(last_run_file, "w") as f:
|
||||||
json.dump({'last_run_date': current_date}, f)
|
json.dump({"last_run_date": current_date}, f)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[EMAIL_SERVICE] Error writing last run file: {str(e)}")
|
print(f"[EMAIL_SERVICE] Error writing last run file: {str(e)}")
|
||||||
|
|
||||||
# Calculate the date to check from
|
# Calculate the date to check from
|
||||||
check_since_date = (datetime.now() - timedelta(days=days_to_check)).strftime("%d-%b-%Y")
|
check_since_date = (datetime.now() - timedelta(days=days_to_check)).strftime(
|
||||||
|
"%d-%b-%Y"
|
||||||
|
)
|
||||||
|
|
||||||
for folder in mail_folders:
|
for folder in mail_folders:
|
||||||
if folder.name == "INBOX":
|
if folder.name == "INBOX":
|
||||||
@@ -184,7 +196,9 @@ def app():
|
|||||||
# Use context manager to handle errors and mark email as unread if needed
|
# Use context manager to handle errors and mark email as unread if needed
|
||||||
with EmailProcessingContext(banks_mail) as ctx:
|
with EmailProcessingContext(banks_mail) as ctx:
|
||||||
try:
|
try:
|
||||||
headers = {k.lower(): v for k, v in banks_mail.headers.items()}
|
headers = {
|
||||||
|
k.lower(): v for k, v in banks_mail.headers.items()
|
||||||
|
}
|
||||||
mail_info = {
|
mail_info = {
|
||||||
"from": headers["from"],
|
"from": headers["from"],
|
||||||
"to": headers["to"],
|
"to": headers["to"],
|
||||||
@@ -201,9 +215,13 @@ def app():
|
|||||||
ctx.success = success
|
ctx.success = success
|
||||||
|
|
||||||
if success:
|
if success:
|
||||||
print(f"[EMAIL_SERVICE] Successfully processed email with subject: {mail_info['subject']}")
|
print(
|
||||||
|
f"[EMAIL_SERVICE] Successfully processed email with subject: {mail_info['subject']}"
|
||||||
|
)
|
||||||
else:
|
else:
|
||||||
print(f"[EMAIL_SERVICE] No matching attachments found in email with subject: {mail_info['subject']}")
|
print(
|
||||||
|
f"[EMAIL_SERVICE] No matching attachments found in email with subject: {mail_info['subject']}"
|
||||||
|
)
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[EMAIL_SERVICE] Error processing email: {str(e)}")
|
print(f"[EMAIL_SERVICE] Error processing email: {str(e)}")
|
||||||
@@ -213,7 +231,7 @@ def app():
|
|||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
print("=== Starting Email Service with Redis Pub/Sub ===")
|
print("=== Starting Email Service with Redis Pub/Sub ===")
|
||||||
print(f"Publishing to channel: {REDIS_CHANNEL}")
|
print(f"Publishing to channel: {REDIS_CHANNEL}")
|
||||||
time.sleep(20) # Wait for 20 seconds to other services to kick in
|
time.sleep(20) # Wait for 20 seconds to other services to kick in
|
||||||
|
|
||||||
while True:
|
while True:
|
||||||
print("\n[EMAIL_SERVICE] Checking for new emails...")
|
print("\n[EMAIL_SERVICE] Checking for new emails...")
|
||||||
|
|||||||
@@ -18,7 +18,9 @@ REDIS_CHANNEL_OUT = "parser" # Publish to Parser Service channel
|
|||||||
delimiter = "|"
|
delimiter = "|"
|
||||||
|
|
||||||
|
|
||||||
def publish_parsed_data_to_redis(data, collected_data_dict: list[dict], filename: str) -> bool:
|
def publish_parsed_data_to_redis(
|
||||||
|
data, collected_data_dict: list[dict], filename: str
|
||||||
|
) -> bool:
|
||||||
"""Publish parsed data to Redis.
|
"""Publish parsed data to Redis.
|
||||||
|
|
||||||
Args:
|
Args:
|
||||||
@@ -49,7 +51,9 @@ def publish_parsed_data_to_redis(data, collected_data_dict: list[dict], filename
|
|||||||
result = redis_pubsub.publisher.publish(REDIS_CHANNEL_OUT, message)
|
result = redis_pubsub.publisher.publish(REDIS_CHANNEL_OUT, message)
|
||||||
|
|
||||||
if result.status:
|
if result.status:
|
||||||
print(f"[PARSER_SERVICE] Published parsed data for {filename} with stage: {message['stage']}")
|
print(
|
||||||
|
f"[PARSER_SERVICE] Published parsed data for {filename} with stage: {message['stage']}"
|
||||||
|
)
|
||||||
return True
|
return True
|
||||||
else:
|
else:
|
||||||
print(f"[PARSER_SERVICE] Publish error: {result.error}")
|
print(f"[PARSER_SERVICE] Publish error: {result.error}")
|
||||||
@@ -76,13 +80,17 @@ def parse_excel_file(excel_frame: DataFrame) -> list[dict]:
|
|||||||
dict(
|
dict(
|
||||||
iban=str(iban),
|
iban=str(iban),
|
||||||
bank_date=arrow.get(
|
bank_date=arrow.get(
|
||||||
datetime.datetime.strptime(str(row[1]), "%d/%m/%Y-%H:%M:%S")
|
datetime.datetime.strptime(
|
||||||
|
str(row[1]), "%d/%m/%Y-%H:%M:%S"
|
||||||
|
)
|
||||||
).__str__(),
|
).__str__(),
|
||||||
channel_branch=unidecode(str(row[3])),
|
channel_branch=unidecode(str(row[3])),
|
||||||
currency_value=(
|
currency_value=(
|
||||||
float(str(row[4]).replace(",", "")) if row[4] else 0
|
float(str(row[4]).replace(",", "")) if row[4] else 0
|
||||||
),
|
),
|
||||||
balance=float(str(row[5]).replace(",", "")) if row[5] else 0,
|
balance=(
|
||||||
|
float(str(row[5]).replace(",", "")) if row[5] else 0
|
||||||
|
),
|
||||||
additional_balance=(
|
additional_balance=(
|
||||||
float(str(row[6]).replace(",", "")) if row[6] else 0
|
float(str(row[6]).replace(",", "")) if row[6] else 0
|
||||||
),
|
),
|
||||||
@@ -92,7 +100,9 @@ def parse_excel_file(excel_frame: DataFrame) -> list[dict]:
|
|||||||
bank_reference_code=str(row[15]),
|
bank_reference_code=str(row[15]),
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
print(f"[PARSER_SERVICE] Successfully parsed {len(data_list)} records from Excel file")
|
print(
|
||||||
|
f"[PARSER_SERVICE] Successfully parsed {len(data_list)} records from Excel file"
|
||||||
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[PARSER_SERVICE] Error parsing Excel file: {str(e)}")
|
print(f"[PARSER_SERVICE] Error parsing Excel file: {str(e)}")
|
||||||
return data_list
|
return data_list
|
||||||
@@ -128,12 +138,14 @@ def process_message(message):
|
|||||||
try:
|
try:
|
||||||
# Decode base64 string to bytes
|
# Decode base64 string to bytes
|
||||||
payload = base64.b64decode(payload)
|
payload = base64.b64decode(payload)
|
||||||
print(f"[PARSER_SERVICE] Successfully decoded base64 payload, size: {len(payload)} bytes")
|
print(
|
||||||
|
f"[PARSER_SERVICE] Successfully decoded base64 payload, size: {len(payload)} bytes"
|
||||||
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[PARSER_SERVICE] Error decoding base64 payload: {str(e)}")
|
print(f"[PARSER_SERVICE] Error decoding base64 payload: {str(e)}")
|
||||||
# Convert regular string payload to bytes if needed
|
# Convert regular string payload to bytes if needed
|
||||||
elif isinstance(payload, str):
|
elif isinstance(payload, str):
|
||||||
payload = payload.encode('utf-8')
|
payload = payload.encode("utf-8")
|
||||||
|
|
||||||
# Create an in-memory file-like object and try multiple approaches
|
# Create an in-memory file-like object and try multiple approaches
|
||||||
excel_frame = None
|
excel_frame = None
|
||||||
@@ -142,20 +154,32 @@ def process_message(message):
|
|||||||
# Save payload to a temporary file for debugging if needed
|
# Save payload to a temporary file for debugging if needed
|
||||||
temp_file_path = f"/tmp/{filename}"
|
temp_file_path = f"/tmp/{filename}"
|
||||||
try:
|
try:
|
||||||
with open(temp_file_path, 'wb') as f:
|
with open(temp_file_path, "wb") as f:
|
||||||
f.write(payload)
|
f.write(payload)
|
||||||
print(f"[PARSER_SERVICE] Saved payload to {temp_file_path} for debugging")
|
print(
|
||||||
|
f"[PARSER_SERVICE] Saved payload to {temp_file_path} for debugging"
|
||||||
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[PARSER_SERVICE] Could not save debug file: {str(e)}")
|
print(f"[PARSER_SERVICE] Could not save debug file: {str(e)}")
|
||||||
|
|
||||||
# Try different approaches to read the Excel file
|
# Try different approaches to read the Excel file
|
||||||
approaches = [
|
approaches = [
|
||||||
# Approach 1: Try xlrd for .xls files
|
# Approach 1: Try xlrd for .xls files
|
||||||
lambda: DataFrame(read_excel(io.BytesIO(payload), engine='xlrd')) if filename.lower().endswith('.xls') else None,
|
lambda: (
|
||||||
|
DataFrame(read_excel(io.BytesIO(payload), engine="xlrd"))
|
||||||
|
if filename.lower().endswith(".xls")
|
||||||
|
else None
|
||||||
|
),
|
||||||
# Approach 2: Try openpyxl for .xlsx files
|
# Approach 2: Try openpyxl for .xlsx files
|
||||||
lambda: DataFrame(read_excel(io.BytesIO(payload), engine='openpyxl')) if filename.lower().endswith('.xlsx') else None,
|
lambda: (
|
||||||
|
DataFrame(read_excel(io.BytesIO(payload), engine="openpyxl"))
|
||||||
|
if filename.lower().endswith(".xlsx")
|
||||||
|
else None
|
||||||
|
),
|
||||||
# Approach 3: Try xlrd with explicit sheet name
|
# Approach 3: Try xlrd with explicit sheet name
|
||||||
lambda: DataFrame(read_excel(io.BytesIO(payload), engine='xlrd', sheet_name=0)),
|
lambda: DataFrame(
|
||||||
|
read_excel(io.BytesIO(payload), engine="xlrd", sheet_name=0)
|
||||||
|
),
|
||||||
# Approach 4: Try with temporary file
|
# Approach 4: Try with temporary file
|
||||||
lambda: DataFrame(read_excel(temp_file_path)),
|
lambda: DataFrame(read_excel(temp_file_path)),
|
||||||
]
|
]
|
||||||
@@ -166,7 +190,9 @@ def process_message(message):
|
|||||||
result = approach()
|
result = approach()
|
||||||
if result is not None:
|
if result is not None:
|
||||||
excel_frame = result
|
excel_frame = result
|
||||||
print(f"[PARSER_SERVICE] Successfully read Excel file using approach {i+1}")
|
print(
|
||||||
|
f"[PARSER_SERVICE] Successfully read Excel file using approach {i+1}"
|
||||||
|
)
|
||||||
break
|
break
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
errors.append(f"Approach {i+1}: {str(e)}")
|
errors.append(f"Approach {i+1}: {str(e)}")
|
||||||
@@ -174,21 +200,23 @@ def process_message(message):
|
|||||||
# If all approaches failed, raise an exception
|
# If all approaches failed, raise an exception
|
||||||
if excel_frame is None:
|
if excel_frame is None:
|
||||||
error_details = "\n".join(errors)
|
error_details = "\n".join(errors)
|
||||||
raise Exception(f"Failed to read Excel file using all approaches:\n{error_details}")
|
raise Exception(
|
||||||
|
f"Failed to read Excel file using all approaches:\n{error_details}"
|
||||||
|
)
|
||||||
|
|
||||||
# Extract data from the Excel file
|
# Extract data from the Excel file
|
||||||
collected_data_dict = parse_excel_file(excel_frame)
|
collected_data_dict = parse_excel_file(excel_frame)
|
||||||
|
|
||||||
# Publish parsed data to Redis
|
# Publish parsed data to Redis
|
||||||
publish_parsed_data_to_redis(
|
publish_parsed_data_to_redis(
|
||||||
data=data,
|
data=data, collected_data_dict=collected_data_dict, filename=filename
|
||||||
collected_data_dict=collected_data_dict,
|
|
||||||
filename=filename
|
|
||||||
)
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[PARSER_SERVICE] Error processing message: {str(e)}")
|
print(f"[PARSER_SERVICE] Error processing message: {str(e)}")
|
||||||
else:
|
else:
|
||||||
print(f"[PARSER_SERVICE] Skipped message with UUID: {data.get('uuid')} (stage is not 'red')")
|
print(
|
||||||
|
f"[PARSER_SERVICE] Skipped message with UUID: {data.get('uuid')} (stage is not 'red')"
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
def app():
|
def app():
|
||||||
|
|||||||
@@ -14,12 +14,12 @@ RUN poetry config virtualenvs.create false && poetry install --no-interaction --
|
|||||||
# Install cron for scheduling tasks
|
# Install cron for scheduling tasks
|
||||||
RUN apt-get update && apt-get install -y cron
|
RUN apt-get update && apt-get install -y cron
|
||||||
|
|
||||||
# 11:00 Istanbul Time (UTC+3) system time is 08:00 UTC
|
|
||||||
RUN echo "0 8 * * * /usr/local/bin/python /app.py >> /var/log/cron.log 2>&1" > /tmp/crontab_list && crontab /tmp/crontab_list
|
|
||||||
|
|
||||||
# Copy application code
|
# Copy application code
|
||||||
COPY /BankServices/RoutineEmailService /
|
COPY /BankServices/RoutineEmailService /
|
||||||
|
|
||||||
|
# Make run_app.sh executable
|
||||||
|
RUN chmod +x /run_app.sh
|
||||||
|
|
||||||
COPY /Schemas /Schemas
|
COPY /Schemas /Schemas
|
||||||
COPY /Controllers /Controllers
|
COPY /Controllers /Controllers
|
||||||
COPY /BankServices/ServiceDepends /
|
COPY /BankServices/ServiceDepends /
|
||||||
@@ -30,5 +30,8 @@ ENV PYTHONPATH=/ PYTHONUNBUFFERED=1 PYTHONDONTWRITEBYTECODE=1
|
|||||||
# Create log file to grab cron logs
|
# Create log file to grab cron logs
|
||||||
RUN touch /var/log/cron.log
|
RUN touch /var/log/cron.log
|
||||||
|
|
||||||
# Run cron setup and tail the log file for user to monitor logs
|
# Make entrypoint script executable
|
||||||
CMD cron && tail -f /var/log/cron.log
|
RUN chmod +x /entrypoint.sh
|
||||||
|
|
||||||
|
# Use entrypoint script to update run_app.sh with environment variables and start cron
|
||||||
|
ENTRYPOINT ["/entrypoint.sh"]
|
||||||
|
|||||||
@@ -0,0 +1,69 @@
|
|||||||
|
# Routine Email Service
|
||||||
|
|
||||||
|
## Overview
|
||||||
|
This service sends automated email reports about account records at scheduled times using cron. It retrieves account records from a PostgreSQL database, formats them into an HTML email, and sends them to specified recipients.
|
||||||
|
|
||||||
|
## Environment Setup
|
||||||
|
The service requires the following environment variables:
|
||||||
|
|
||||||
|
### Email Configuration
|
||||||
|
- `EMAIL_HOST`: SMTP server address (e.g., "10.10.2.34")
|
||||||
|
- `EMAIL_USERNAME`: Email sender address (e.g., "example@domain.com")
|
||||||
|
- `EMAIL_PASSWORD`: Email password (sensitive)
|
||||||
|
- `EMAIL_PORT`: SMTP port (e.g., 587)
|
||||||
|
- `EMAIL_SEND`: Flag to enable/disable email sending (1 = enabled)
|
||||||
|
|
||||||
|
### Database Configuration
|
||||||
|
- `DB_HOST`: PostgreSQL server address (e.g., "10.10.2.14")
|
||||||
|
- `DB_USER`: Database username (e.g., "postgres")
|
||||||
|
- `DB_PASSWORD`: Database password (sensitive)
|
||||||
|
- `DB_PORT`: Database port (e.g., 5432)
|
||||||
|
- `DB_NAME`: Database name (e.g., "postgres")
|
||||||
|
|
||||||
|
## Cron Job Configuration
|
||||||
|
The service is configured to run daily at 11:00 Istanbul Time (08:00 UTC). This is set up in the entrypoint.sh script.
|
||||||
|
|
||||||
|
## Docker Container Setup
|
||||||
|
|
||||||
|
### Key Files
|
||||||
|
|
||||||
|
1. **Dockerfile**: Defines the container image with Python and cron
|
||||||
|
|
||||||
|
2. **entrypoint.sh**: Container entrypoint script that:
|
||||||
|
- Creates an environment file (/env.sh) with all configuration variables
|
||||||
|
- Sets up the crontab to run run_app.sh at the scheduled time
|
||||||
|
- Starts the cron service
|
||||||
|
- Tails the log file for monitoring
|
||||||
|
|
||||||
|
3. **run_app.sh**: Script executed by cron that:
|
||||||
|
- Sources the environment file to get all configuration
|
||||||
|
- Exports variables to make them available to the Python script
|
||||||
|
- Runs the Python application
|
||||||
|
- Logs environment and execution results
|
||||||
|
|
||||||
|
### Environment Variable Handling
|
||||||
|
Cron jobs run with a minimal environment that doesn't automatically include Docker container environment variables. Our solution:
|
||||||
|
|
||||||
|
1. Captures all environment variables from Docker to a file at container startup
|
||||||
|
2. Has the run_app.sh script source this file before execution
|
||||||
|
3. Explicitly exports all variables to ensure they're available to the Python script
|
||||||
|
|
||||||
|
## Logs
|
||||||
|
Logs are written to `/var/log/cron.log` and can be viewed with:
|
||||||
|
```bash
|
||||||
|
docker exec routine_email_service tail -f /var/log/cron.log
|
||||||
|
```
|
||||||
|
|
||||||
|
## Manual Execution
|
||||||
|
To run the service manually:
|
||||||
|
```bash
|
||||||
|
docker exec routine_email_service /run_app.sh
|
||||||
|
```
|
||||||
|
|
||||||
|
## Docker Compose Configuration
|
||||||
|
In the docker-compose.yml file, the service needs an explicit entrypoint configuration:
|
||||||
|
```yaml
|
||||||
|
entrypoint: ["/entrypoint.sh"]
|
||||||
|
```
|
||||||
|
|
||||||
|
This ensures the entrypoint script runs when the container starts.
|
||||||
|
|||||||
@@ -35,8 +35,7 @@ def render_email_template(
|
|||||||
today=str(arrow.now().date()),
|
today=str(arrow.now().date()),
|
||||||
)
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print('Exception render template:',e)
|
print("Exception render template:", e)
|
||||||
err = e
|
|
||||||
raise
|
raise
|
||||||
|
|
||||||
|
|
||||||
@@ -59,17 +58,16 @@ def send_email_to_given_address(send_to: str, html_template: str) -> bool:
|
|||||||
subject=subject,
|
subject=subject,
|
||||||
html=html_template,
|
html=html_template,
|
||||||
receivers=[send_to],
|
receivers=[send_to],
|
||||||
text=f"Gunes Apt. Cari Durum Bilgilendirme Raporu - {today.date()}"
|
text=f"Gunes Apt. Cari Durum Bilgilendirme Raporu - {today.date()}",
|
||||||
)
|
)
|
||||||
|
|
||||||
try:
|
try:
|
||||||
# Use the context manager to handle connection errors
|
# Use the context manager to handle connection errors
|
||||||
with EmailService.new_session() as email_session:
|
with EmailService.new_session() as email_session:
|
||||||
# Send email through the service
|
# Send email through the service
|
||||||
EmailService.send_email(email_session, email_params)
|
return EmailService.send_email(email_session, email_params)
|
||||||
return True
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f'Exception send email: {e}')
|
print(f"Exception send email: {e}")
|
||||||
return False
|
return False
|
||||||
|
|
||||||
|
|
||||||
@@ -88,10 +86,10 @@ def set_account_records_to_send_email() -> bool:
|
|||||||
account_records_query = AccountRecords.filter_all(db=db_session).query
|
account_records_query = AccountRecords.filter_all(db=db_session).query
|
||||||
|
|
||||||
# Get the 3 most recent records
|
# Get the 3 most recent records
|
||||||
account_records: List[AccountRecords] | [] = (
|
account_records: List[AccountRecords] = (
|
||||||
account_records_query.order_by(
|
account_records_query.order_by(
|
||||||
AccountRecords.bank_date.desc(),
|
AccountRecords.bank_date.desc(),
|
||||||
AccountRecords.bank_reference_code.desc()
|
AccountRecords.iban.desc(),
|
||||||
)
|
)
|
||||||
.limit(3)
|
.limit(3)
|
||||||
.all()
|
.all()
|
||||||
@@ -99,29 +97,43 @@ def set_account_records_to_send_email() -> bool:
|
|||||||
|
|
||||||
# Check if we have enough records
|
# Check if we have enough records
|
||||||
if len(account_records) < 2:
|
if len(account_records) < 2:
|
||||||
|
print(f"Not enough records found: {len(account_records)}")
|
||||||
return False
|
return False
|
||||||
|
|
||||||
# Check for balance discrepancy
|
# Check for balance discrepancy
|
||||||
first_record, second_record = account_records[0], account_records[1]
|
first_record, second_record = account_records[0], account_records[1]
|
||||||
expected_second_balance = first_record.bank_balance - first_record.currency_value
|
expected_second_balance = (
|
||||||
|
first_record.bank_balance - first_record.currency_value
|
||||||
|
)
|
||||||
balance_error = expected_second_balance != second_record.bank_balance
|
balance_error = expected_second_balance != second_record.bank_balance
|
||||||
|
|
||||||
if balance_error:
|
if balance_error:
|
||||||
return False
|
print(
|
||||||
|
f"Balance error detected {expected_second_balance} != {second_record.bank_balance}"
|
||||||
|
)
|
||||||
|
|
||||||
# Format rows for the email template
|
# Format rows for the email template
|
||||||
list_of_rows = []
|
list_of_rows = []
|
||||||
for record in account_records:
|
for record in account_records:
|
||||||
list_of_rows.append([
|
list_of_rows.append(
|
||||||
record.bank_date.strftime("%d/%m/%Y %H:%M"),
|
[
|
||||||
record.process_comment,
|
record.bank_date.strftime("%d/%m/%Y %H:%M"),
|
||||||
f"{record.currency_value:,.2f}",
|
record.process_comment,
|
||||||
f"{record.bank_balance:,.2f}"
|
f"{record.currency_value:,.2f}",
|
||||||
])
|
f"{record.bank_balance:,.2f}",
|
||||||
|
]
|
||||||
|
)
|
||||||
# Get the most recent bank balance
|
# Get the most recent bank balance
|
||||||
last_bank_balance = sorted(account_records, key=lambda x: x.bank_date, reverse=True)[0].bank_balance
|
last_bank_balance = sorted(
|
||||||
|
account_records, key=lambda x: x.bank_date, reverse=True
|
||||||
|
)[0].bank_balance
|
||||||
# Define headers for the table
|
# Define headers for the table
|
||||||
headers = ["Ulaştığı Tarih", "Banka Transaksiyonu Ek Bilgi", "Aktarım Değeri", "Banka Bakiyesi"]
|
headers = [
|
||||||
|
"Ulaştığı Tarih",
|
||||||
|
"Banka Transaksiyonu Ek Bilgi",
|
||||||
|
"Aktarım Değeri",
|
||||||
|
"Banka Bakiyesi",
|
||||||
|
]
|
||||||
|
|
||||||
# Recipient email address
|
# Recipient email address
|
||||||
send_to = "karatay@mehmetkaratay.com.tr"
|
send_to = "karatay@mehmetkaratay.com.tr"
|
||||||
@@ -140,5 +152,6 @@ def set_account_records_to_send_email() -> bool:
|
|||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
success = set_account_records_to_send_email()
|
success = set_account_records_to_send_email()
|
||||||
|
print("Email sent successfully" if success else "Failed to send email")
|
||||||
exit_code = 0 if success else 1
|
exit_code = 0 if success else 1
|
||||||
exit(exit_code)
|
exit(exit_code)
|
||||||
|
|||||||
29
BankServices/RoutineEmailService/entrypoint.sh
Normal file
29
BankServices/RoutineEmailService/entrypoint.sh
Normal file
@@ -0,0 +1,29 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# Create environment file that will be available to cron jobs
|
||||||
|
echo "# Environment variables for cron jobs" > /env.sh
|
||||||
|
echo "EMAIL_HOST=\"$EMAIL_HOST\"" >> /env.sh
|
||||||
|
echo "EMAIL_USERNAME=\"$EMAIL_USERNAME\"" >> /env.sh
|
||||||
|
echo "EMAIL_PASSWORD=\"$EMAIL_PASSWORD\"" >> /env.sh
|
||||||
|
echo "EMAIL_PORT=$EMAIL_PORT" >> /env.sh
|
||||||
|
echo "EMAIL_SEND=$EMAIL_SEND" >> /env.sh
|
||||||
|
echo "DB_HOST=\"$DB_HOST\"" >> /env.sh
|
||||||
|
echo "DB_USER=\"$DB_USER\"" >> /env.sh
|
||||||
|
echo "DB_PASSWORD=\"$DB_PASSWORD\"" >> /env.sh
|
||||||
|
echo "DB_PORT=$DB_PORT" >> /env.sh
|
||||||
|
echo "DB_NAME=\"$DB_NAME\"" >> /env.sh
|
||||||
|
|
||||||
|
# Add Python environment variables
|
||||||
|
echo "PYTHONPATH=/" >> /env.sh
|
||||||
|
echo "PYTHONUNBUFFERED=1" >> /env.sh
|
||||||
|
echo "PYTHONDONTWRITEBYTECODE=1" >> /env.sh
|
||||||
|
|
||||||
|
# Make the environment file available to cron
|
||||||
|
echo "0 8 * * * /run_app.sh >> /var/log/cron.log 2>&1" > /tmp/crontab_list
|
||||||
|
crontab /tmp/crontab_list
|
||||||
|
|
||||||
|
# Start cron
|
||||||
|
cron
|
||||||
|
|
||||||
|
# Tail the log file
|
||||||
|
tail -f /var/log/cron.log
|
||||||
24
BankServices/RoutineEmailService/run_app.sh
Normal file
24
BankServices/RoutineEmailService/run_app.sh
Normal file
@@ -0,0 +1,24 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
# Source the environment file directly
|
||||||
|
. /env.sh
|
||||||
|
|
||||||
|
# Re-export all variables to ensure they're available to the Python script
|
||||||
|
export EMAIL_HOST
|
||||||
|
export EMAIL_USERNAME
|
||||||
|
export EMAIL_PASSWORD
|
||||||
|
export EMAIL_PORT
|
||||||
|
export EMAIL_SEND
|
||||||
|
export DB_HOST
|
||||||
|
export DB_USER
|
||||||
|
export DB_PASSWORD
|
||||||
|
export DB_PORT
|
||||||
|
export DB_NAME
|
||||||
|
|
||||||
|
# Python environment variables
|
||||||
|
export PYTHONPATH
|
||||||
|
export PYTHONUNBUFFERED
|
||||||
|
export PYTHONDONTWRITEBYTECODE
|
||||||
|
|
||||||
|
env >> /var/log/cron.log
|
||||||
|
/usr/local/bin/python /app.py
|
||||||
@@ -35,11 +35,13 @@ def render_email_template(
|
|||||||
today=str(arrow.now().date()),
|
today=str(arrow.now().date()),
|
||||||
)
|
)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f'Template rendering failed: {e}')
|
print(f"Template rendering failed: {e}")
|
||||||
raise
|
raise
|
||||||
|
|
||||||
|
|
||||||
def send_email_to_given_address(send_to: str, html_template: str, count_of_records: int) -> bool:
|
def send_email_to_given_address(
|
||||||
|
send_to: str, html_template: str, count_of_records: int
|
||||||
|
) -> bool:
|
||||||
"""
|
"""
|
||||||
Send email with the rendered HTML template to the specified address.
|
Send email with the rendered HTML template to the specified address.
|
||||||
|
|
||||||
@@ -58,7 +60,7 @@ def send_email_to_given_address(send_to: str, html_template: str, count_of_recor
|
|||||||
subject=subject + f" ({count_of_records} kayıt)",
|
subject=subject + f" ({count_of_records} kayıt)",
|
||||||
html=html_template,
|
html=html_template,
|
||||||
receivers=[send_to],
|
receivers=[send_to],
|
||||||
text=f"Gunes Apt. Cari Durum Kayıt Giriş Raporu - {today.date()}"
|
text=f"Gunes Apt. Cari Durum Kayıt Giriş Raporu - {today.date()}",
|
||||||
)
|
)
|
||||||
|
|
||||||
try:
|
try:
|
||||||
@@ -69,7 +71,7 @@ def send_email_to_given_address(send_to: str, html_template: str, count_of_recor
|
|||||||
print(f"Email successfully sent to: {send_to}")
|
print(f"Email successfully sent to: {send_to}")
|
||||||
return True
|
return True
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f'Failed to send email: {e}')
|
print(f"Failed to send email: {e}")
|
||||||
return False
|
return False
|
||||||
|
|
||||||
|
|
||||||
@@ -87,10 +89,14 @@ def process_unsent_email_records() -> bool:
|
|||||||
# Use the context manager to handle database connections
|
# Use the context manager to handle database connections
|
||||||
with AccountRecords.new_session() as db_session:
|
with AccountRecords.new_session() as db_session:
|
||||||
# Query un-sent mail rows - with limit for display only
|
# Query un-sent mail rows - with limit for display only
|
||||||
account_records_query = AccountRecords.filter_all(
|
account_records_query = (
|
||||||
AccountRecords.is_email_send == False,
|
AccountRecords.filter_all(
|
||||||
db=db_session,
|
AccountRecords.is_email_send == False,
|
||||||
).query.order_by(AccountRecords.bank_date.asc()).limit(20)
|
db=db_session,
|
||||||
|
)
|
||||||
|
.query.order_by(AccountRecords.bank_date.asc())
|
||||||
|
.limit(20)
|
||||||
|
)
|
||||||
|
|
||||||
account_records: List[AccountRecords] = account_records_query.all()
|
account_records: List[AccountRecords] = account_records_query.all()
|
||||||
if not account_records:
|
if not account_records:
|
||||||
@@ -99,27 +105,35 @@ def process_unsent_email_records() -> bool:
|
|||||||
|
|
||||||
# Get the IDs of the records we're processing
|
# Get the IDs of the records we're processing
|
||||||
record_ids = [record.id for record in account_records]
|
record_ids = [record.id for record in account_records]
|
||||||
|
|
||||||
print(f"Found {len(account_records)} unsent email records")
|
print(f"Found {len(account_records)} unsent email records")
|
||||||
|
|
||||||
# Format rows for the email template
|
# Format rows for the email template
|
||||||
list_of_rows = []
|
list_of_rows = []
|
||||||
for record in account_records:
|
for record in account_records:
|
||||||
list_of_rows.append([
|
list_of_rows.append(
|
||||||
record.bank_date.strftime("%d/%m/%Y %H:%M"),
|
[
|
||||||
record.process_comment,
|
record.bank_date.strftime("%d/%m/%Y %H:%M"),
|
||||||
f"{record.currency_value:,.2f}",
|
record.process_comment,
|
||||||
f"{record.bank_balance:,.2f}"
|
f"{record.currency_value:,.2f}",
|
||||||
])
|
f"{record.bank_balance:,.2f}",
|
||||||
|
]
|
||||||
|
)
|
||||||
|
|
||||||
# Reverse list by date
|
# Reverse list by date
|
||||||
list_of_rows = list_of_rows[::-1]
|
list_of_rows = list_of_rows[::-1]
|
||||||
|
|
||||||
# Get the most recent bank balance
|
# Get the most recent bank balance
|
||||||
last_bank_balance = sorted(account_records, key=lambda x: x.bank_date, reverse=True)[0].bank_balance
|
last_bank_balance = sorted(
|
||||||
|
account_records, key=lambda x: x.bank_date, reverse=True
|
||||||
|
)[0].bank_balance
|
||||||
|
|
||||||
# Define headers for the table
|
# Define headers for the table
|
||||||
headers = ["Ulaştığı Tarih", "Banka Transaksiyonu Ek Bilgi", "Aktarım Değeri", "Banka Bakiyesi"]
|
headers = [
|
||||||
|
"Ulaştığı Tarih",
|
||||||
|
"Banka Transaksiyonu Ek Bilgi",
|
||||||
|
"Aktarım Değeri",
|
||||||
|
"Banka Bakiyesi",
|
||||||
|
]
|
||||||
|
|
||||||
# Recipient email address
|
# Recipient email address
|
||||||
send_to = "karatay@mehmetkaratay.com.tr"
|
send_to = "karatay@mehmetkaratay.com.tr"
|
||||||
@@ -133,11 +147,14 @@ def process_unsent_email_records() -> bool:
|
|||||||
)
|
)
|
||||||
|
|
||||||
# Send the email
|
# Send the email
|
||||||
if send_email_to_given_address(send_to=send_to, html_template=html_template, count_of_records=len(list_of_rows)):
|
if send_email_to_given_address(
|
||||||
|
send_to=send_to,
|
||||||
|
html_template=html_template,
|
||||||
|
count_of_records=len(list_of_rows),
|
||||||
|
):
|
||||||
# Create a new query without limit for updating
|
# Create a new query without limit for updating
|
||||||
update_query = AccountRecords.filter_all(
|
update_query = AccountRecords.filter_all(
|
||||||
AccountRecords.id.in_(record_ids),
|
AccountRecords.id.in_(record_ids), db=db_session
|
||||||
db=db_session
|
|
||||||
).query
|
).query
|
||||||
|
|
||||||
# Update records as sent
|
# Update records as sent
|
||||||
@@ -150,7 +167,7 @@ def process_unsent_email_records() -> bool:
|
|||||||
return False
|
return False
|
||||||
|
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f'Error processing unsent email records: {e}')
|
print(f"Error processing unsent email records: {e}")
|
||||||
return False
|
return False
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ class Config:
|
|||||||
|
|
||||||
class EmailConfig:
|
class EmailConfig:
|
||||||
|
|
||||||
EMAIL_HOST: str = os.getenv("EMAIL_HOST", "10.10.2.34")
|
EMAIL_HOST: str = os.getenv("EMAIL_HOST", "10.10.2.34")
|
||||||
EMAIL_USERNAME: str = Config.EMAIL_SENDER_USERNAME
|
EMAIL_USERNAME: str = Config.EMAIL_SENDER_USERNAME
|
||||||
EMAIL_PASSWORD: str = Config.EMAIL_PASSWORD
|
EMAIL_PASSWORD: str = Config.EMAIL_PASSWORD
|
||||||
EMAIL_PORT: int = Config.EMAIL_SEND_PORT
|
EMAIL_PORT: int = Config.EMAIL_SEND_PORT
|
||||||
|
|||||||
@@ -39,7 +39,9 @@ def publish_written_data_to_redis(data: Dict[str, Any], file_name: str) -> bool:
|
|||||||
result = redis_pubsub.publisher.publish(REDIS_CHANNEL_OUT, message)
|
result = redis_pubsub.publisher.publish(REDIS_CHANNEL_OUT, message)
|
||||||
|
|
||||||
if result.status:
|
if result.status:
|
||||||
print(f"[WRITER_SERVICE] Published written status for {file_name} with stage: written")
|
print(
|
||||||
|
f"[WRITER_SERVICE] Published written status for {file_name} with stage: written"
|
||||||
|
)
|
||||||
return True
|
return True
|
||||||
else:
|
else:
|
||||||
print(f"[WRITER_SERVICE] Publish error: {result.error}")
|
print(f"[WRITER_SERVICE] Publish error: {result.error}")
|
||||||
@@ -61,7 +63,7 @@ def write_parsed_data_to_account_records(data_dict: dict, file_name: str) -> boo
|
|||||||
data_dict["bank_balance"] = data_dict.pop("balance")
|
data_dict["bank_balance"] = data_dict.pop("balance")
|
||||||
data_dict["import_file_name"] = file_name
|
data_dict["import_file_name"] = file_name
|
||||||
data_dict = BankReceive(**data_dict).model_dump()
|
data_dict = BankReceive(**data_dict).model_dump()
|
||||||
print('data_dict', data_dict)
|
print("data_dict", data_dict)
|
||||||
|
|
||||||
# Process date fields
|
# Process date fields
|
||||||
bank_date = arrow.get(str(data_dict["bank_date"]))
|
bank_date = arrow.get(str(data_dict["bank_date"]))
|
||||||
@@ -90,16 +92,20 @@ def write_parsed_data_to_account_records(data_dict: dict, file_name: str) -> boo
|
|||||||
AccountRecords.bank_date,
|
AccountRecords.bank_date,
|
||||||
AccountRecords.iban,
|
AccountRecords.iban,
|
||||||
AccountRecords.bank_reference_code,
|
AccountRecords.bank_reference_code,
|
||||||
AccountRecords.bank_balance
|
AccountRecords.bank_balance,
|
||||||
]
|
],
|
||||||
)
|
)
|
||||||
if new_account_record.meta_data.created:
|
if new_account_record.meta_data.created:
|
||||||
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)
|
||||||
print(f"[WRITER_SERVICE] Created new record in database: {new_account_record.id}")
|
print(
|
||||||
|
f"[WRITER_SERVICE] Created new record in database: {new_account_record.id}"
|
||||||
|
)
|
||||||
return True
|
return True
|
||||||
else:
|
else:
|
||||||
print(f"[WRITER_SERVICE] Record already exists in database: {new_account_record.id}")
|
print(
|
||||||
|
f"[WRITER_SERVICE] Record already exists in database: {new_account_record.id}"
|
||||||
|
)
|
||||||
return False
|
return False
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[WRITER_SERVICE] Error writing to database: {str(e)}")
|
print(f"[WRITER_SERVICE] Error writing to database: {str(e)}")
|
||||||
@@ -138,7 +144,9 @@ def process_message(message):
|
|||||||
# Process each parsed data item
|
# Process each parsed data item
|
||||||
success = True
|
success = True
|
||||||
for item in parsed_data:
|
for item in parsed_data:
|
||||||
result = write_parsed_data_to_account_records(data_dict=item, file_name=file_name)
|
result = write_parsed_data_to_account_records(
|
||||||
|
data_dict=item, file_name=file_name
|
||||||
|
)
|
||||||
if not result:
|
if not result:
|
||||||
success = False
|
success = False
|
||||||
|
|
||||||
@@ -148,7 +156,9 @@ def process_message(message):
|
|||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"[WRITER_SERVICE] Error processing message: {str(e)}")
|
print(f"[WRITER_SERVICE] Error processing message: {str(e)}")
|
||||||
else:
|
else:
|
||||||
print(f"[WRITER_SERVICE] Skipped message with UUID: {data.get('uuid')} (stage is not 'parsed')")
|
print(
|
||||||
|
f"[WRITER_SERVICE] Skipped message with UUID: {data.get('uuid')} (stage is not 'parsed')"
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
def app():
|
def app():
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ class Configs(BaseSettings):
|
|||||||
USERNAME: str = ""
|
USERNAME: str = ""
|
||||||
PASSWORD: str = ""
|
PASSWORD: str = ""
|
||||||
PORT: int = 0
|
PORT: int = 0
|
||||||
SEND: bool = 0
|
SEND: bool = True
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def is_send(self):
|
def is_send(self):
|
||||||
|
|||||||
@@ -27,17 +27,27 @@ class EmailSession:
|
|||||||
print("Email sending is disabled", params)
|
print("Email sending is disabled", params)
|
||||||
return False
|
return False
|
||||||
receivers = [email_configs.USERNAME]
|
receivers = [email_configs.USERNAME]
|
||||||
self.email_sender.send(
|
|
||||||
subject=params.subject,
|
# Ensure connection is established before sending
|
||||||
receivers=receivers,
|
try:
|
||||||
text=params.text + f" : Gonderilen [{str(receivers)}]",
|
# Check if connection exists, if not establish it
|
||||||
html=params.html,
|
if not hasattr(self.email_sender, '_connected') or not self.email_sender._connected:
|
||||||
cc=params.cc,
|
self.email_sender.connect()
|
||||||
bcc=params.bcc,
|
|
||||||
headers=params.headers or {},
|
self.email_sender.send(
|
||||||
attachments=params.attachments or {},
|
subject=params.subject,
|
||||||
)
|
receivers=receivers,
|
||||||
return True
|
text=params.text + f" : Gonderilen [{str(receivers)}]",
|
||||||
|
html=params.html,
|
||||||
|
cc=params.cc,
|
||||||
|
bcc=params.bcc,
|
||||||
|
headers=params.headers or {},
|
||||||
|
attachments=params.attachments or {},
|
||||||
|
)
|
||||||
|
return True
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error sending email: {e}")
|
||||||
|
raise
|
||||||
|
|
||||||
|
|
||||||
class EmailService:
|
class EmailService:
|
||||||
@@ -54,14 +64,25 @@ class EmailService:
|
|||||||
"""Create and yield a new email session with active connection."""
|
"""Create and yield a new email session with active connection."""
|
||||||
email_sender = EmailSender(**email_configs.as_dict())
|
email_sender = EmailSender(**email_configs.as_dict())
|
||||||
session = EmailSession(email_sender)
|
session = EmailSession(email_sender)
|
||||||
|
connection_established = False
|
||||||
try:
|
try:
|
||||||
|
# Establish connection and set flag
|
||||||
email_sender.connect()
|
email_sender.connect()
|
||||||
|
# Set a flag to track connection state
|
||||||
|
email_sender._connected = True
|
||||||
|
connection_established = True
|
||||||
yield session
|
yield session
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
print(f"Error with email connection: {e}")
|
print(f"Error with email connection: {e}")
|
||||||
raise
|
raise
|
||||||
finally:
|
finally:
|
||||||
email_sender.close()
|
# Only close if connection was successfully established
|
||||||
|
if connection_established:
|
||||||
|
try:
|
||||||
|
email_sender.close()
|
||||||
|
email_sender._connected = False
|
||||||
|
except Exception as e:
|
||||||
|
print(f"Error closing email connection: {e}")
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
def send_email(cls, session: EmailSession, params: EmailSendModel) -> bool:
|
def send_email(cls, session: EmailSession, params: EmailSendModel) -> bool:
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user