Compare commits

..

2 Commits

Author SHA1 Message Date
Alexey
4acb5ac3bb backedn dev 2025-09-18 14:00:05 +02:00
root
c7e3dbf6b4 dev schema 2025-09-18 12:11:52 +02:00
4 changed files with 38 additions and 12 deletions

View File

@@ -1,6 +1,9 @@
import json import json
import logging import logging
from redis import Redis, ConnectionError from redis import Redis, ConnectionError
from typing import List
from pydantic import TypeAdapter
from schema import ConfigSchema
def setup_db_conn(redishost, redisport: str): def setup_db_conn(redishost, redisport: str):
@@ -8,7 +11,11 @@ def setup_db_conn(redishost, redisport: str):
log = logging.getLogger('uvicorn') log = logging.getLogger('uvicorn')
try: try:
redisclient = Redis(host=redishost, port=redisport, decode_responses=True) redisclient = Redis(host=redishost, port=redisport, decode_responses=True)
log.info(f"Connected to Redis DB {redishost} on port {redisport}") if redisclient.ping():
log.info(f"Connected to Redis DB {redishost} on port {redisport}")
else:
log.error(f"Cannot connect to Redis DB {redishost} on port {redisport}")
exit(1)
return redisclient return redisclient
except ConnectionError as e: except ConnectionError as e:
print(f"FATAL: Redis DB {redishost} is unreachable on port {redisport}. Err: {e}") print(f"FATAL: Redis DB {redishost} is unreachable on port {redisport}. Err: {e}")
@@ -24,7 +31,10 @@ def get_inventory_from_redis(redisclient: Redis):
return json.loads(cluster_inv['inventory']) return json.loads(cluster_inv['inventory'])
return {} return {}
def read_config_from_db(redisclient: Redis): def get_config_from_db(redisclient: Redis) -> ConfigSchema:
''' Load inventory to global vars''' ''' Load inventory to global vars'''
global_inventory = get_inventory_from_redis(redisclient) GLOBAL_INVENTORY = get_inventory_from_redis(redisclient)
return global_inventory
GLOBAL_INVENTORY_VALID = TypeAdapter(List[ConfigSchema]).validate_python(GLOBAL_INVENTORY)
return GLOBAL_INVENTORY_VALID

View File

@@ -6,6 +6,9 @@ import yaml
from pathlib import Path from pathlib import Path
from dotenv import load_dotenv from dotenv import load_dotenv
from database import setup_db_conn from database import setup_db_conn
from schema import ConfigSchema
from typing import List
from pydantic import TypeAdapter
def initialize_config(): def initialize_config():
load_dotenv() load_dotenv()
@@ -14,7 +17,7 @@ def initialize_config():
ENV_REDISHOST = os.getenv('redis_host') ENV_REDISHOST = os.getenv('redis_host')
ENV_REDISPORT = os.getenv('redis_port') ENV_REDISPORT = os.getenv('redis_port')
log.info(f"Fount Cluster Inventory file at: {ENV_INVENTORYPATH}") log.info(f"Found Cluster Inventory file at: {ENV_INVENTORYPATH}")
if not ENV_INVENTORYPATH or not Path(ENV_INVENTORYPATH).is_file(): if not ENV_INVENTORYPATH or not Path(ENV_INVENTORYPATH).is_file():
print(f"FATAL: Inventory file {ENV_INVENTORYPATH} is missing or not a file.") print(f"FATAL: Inventory file {ENV_INVENTORYPATH} is missing or not a file.")
return False return False
@@ -28,11 +31,12 @@ def initialize_config():
print(f'[INFO] Importing configuration to DB...') print(f'[INFO] Importing configuration to DB...')
try: try:
GLOBAL_INVENTORY_VALID = TypeAdapter(List[ConfigSchema]).validate_python(inv)
redis_conn = setup_db_conn(ENV_REDISHOST, ENV_REDISPORT) redis_conn = setup_db_conn(ENV_REDISHOST, ENV_REDISPORT)
redis_conn.hset('cluster_inventory', mapping={'inventory': inventory}) redis_conn.hset('cluster_inventory', mapping={'inventory': inventory})
redis_conn.close() redis_conn.close()
log.info("Configuration has been loaded.") log.info("Configuration has been loaded.")
return True return True
except Exception as e: except Exception as e:

View File

@@ -13,9 +13,9 @@ from typing import Optional, Literal, List, Union
from fastapi import FastAPI from fastapi import FastAPI
from database import setup_db_conn, get_inventory_from_redis, read_config_from_db from database import setup_db_conn, get_inventory_from_redis, get_config_from_db
from initialize import initialize_config from src.initialize import initialize_config
from utils import setup_logging from utils import setup_logging
@asynccontextmanager @asynccontextmanager
@@ -23,12 +23,17 @@ async def lifespan(app: FastAPI):
''' make loading it async''' ''' make loading it async'''
log = logging.getLogger('uvicorn') log = logging.getLogger('uvicorn')
cfg_init_result = initialize_config() cfg_init_result = initialize_config()
shared_redis_conn = setup_db_conn(os.getenv('redis_host'), os.getenv('redis_port'))
if not shared_redis_conn:
log.error("Cannot connect to Redis DB. Exiting...")
exit(1)
inv_check = read_config_from_db(setup_db_conn(os.getenv('redis_host'), os.getenv('redis_port'))) inv_check = get_config_from_db(shared_redis_conn)
log.info(f"Data validity check (DEVELOPER MODE): {inv_check}") log.info(f"[DEBUG] Data validity healthcheck (DEVELOPER MODE): {inv_check}")
if not cfg_init_result: if not cfg_init_result:
log.error("Configuration initialization failed. Exiting...") log.error("Configuration initialization failed. Exiting...")
exit(1) # exit(1)
yield yield
log.info("Shutting down FastAPI app...") log.info("Shutting down FastAPI app...")

7
src/schema.py Normal file
View File

@@ -0,0 +1,7 @@
from pydantic import BaseModel
class ConfigSchema(BaseModel):
hostname: str
username: str
password: str