Skip to content

Commit da0a8cc

Browse files
committed
config: Implement singleton pattern
Signed-off-by: Phoevos Kalemkeris <[email protected]>
1 parent 75c110a commit da0a8cc

File tree

3 files changed

+32
-25
lines changed

3 files changed

+32
-25
lines changed

cogstack_model_gateway/common/config.py

Lines changed: 27 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -69,30 +69,35 @@ def to_dict(self):
6969
}
7070

7171

72-
def load_config() -> Config:
73-
"""Load configuration from the provided JSON file and environment variables."""
74-
try:
75-
with open(CONFIG_FILE) as f:
76-
config = json.load(f)
77-
except FileNotFoundError:
78-
print(f"Config file {CONFIG_FILE} not found.")
79-
raise
80-
except json.JSONDecodeError:
81-
print(f"Config file {CONFIG_FILE} is not a valid JSON file.")
82-
raise
83-
84-
load_dotenv()
85-
config["env"] = {
86-
var.replace(ACCEPTED_ENVIRONMENT_VARIABLE_PREFIX, "", 1).lower(): value
87-
for var in ACCEPTED_ENVIRONMENT_VARIABLES
88-
if (value := os.getenv(var))
89-
}
90-
log.info(f"Loaded config: {config}")
91-
return Config(config)
72+
_config_instance: Config = None
9273

9374

94-
config = load_config()
75+
def load_config() -> Config:
76+
"""Load configuration from the provided JSON file and environment variables."""
77+
global _config_instance
78+
if _config_instance is None:
79+
try:
80+
with open(CONFIG_FILE) as f:
81+
config = json.load(f)
82+
except FileNotFoundError:
83+
log.error(f"Config file {CONFIG_FILE} not found.")
84+
raise
85+
except json.JSONDecodeError:
86+
log.error(f"Config file {CONFIG_FILE} is not a valid JSON file.")
87+
raise
88+
89+
load_dotenv()
90+
config["env"] = {
91+
var.replace(ACCEPTED_ENVIRONMENT_VARIABLE_PREFIX, "", 1).lower(): value
92+
for var in ACCEPTED_ENVIRONMENT_VARIABLES
93+
if (value := os.getenv(var))
94+
}
95+
log.info(f"Loaded config: {config}")
96+
_config_instance = Config(config)
97+
return _config_instance
9598

9699

97100
def get_config() -> Config:
98-
return config
101+
if _config_instance is None:
102+
raise RuntimeError("Config not initialized. Call load_config() first.")
103+
return _config_instance

cogstack_model_gateway/gateway/main.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33

44
from fastapi import FastAPI
55

6-
from cogstack_model_gateway.common.config import config
6+
from cogstack_model_gateway.common.config import load_config
77
from cogstack_model_gateway.common.db import DatabaseManager
88
from cogstack_model_gateway.common.object_store import ObjectStoreManager
99
from cogstack_model_gateway.common.queue import QueueManager
@@ -18,7 +18,7 @@
1818
async def lifespan(app: FastAPI):
1919
log.info("Initializing database and queue connections")
2020

21-
global config
21+
config = load_config()
2222
dbm = DatabaseManager(
2323
user=config.env.db_user,
2424
password=config.env.db_password,

tests/unit/common/test_config.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ def test_config_set():
6363
assert config.nested.inner_key == "inner_value"
6464

6565

66-
@patch("cogstack_model_gateway.common.config.config", new=Config({"key": "value"}))
66+
@patch("cogstack_model_gateway.common.config._config_instance", new=Config({"key": "value"}))
6767
def test_get_config():
6868
config = get_config()
6969
assert isinstance(config, Config)
@@ -73,6 +73,7 @@ def test_get_config():
7373
@patch("builtins.open", new_callable=mock_open, read_data='{"key": "value"}')
7474
@patch("os.getenv", side_effect=lambda k, d=None: TEST_ENV_VARS.get(k, d))
7575
@patch("cogstack_model_gateway.common.config.load_dotenv")
76+
@patch("cogstack_model_gateway.common.config._config_instance", new=None)
7677
def test_load_config(mock_load_dotenv, mock_getenv, mock_open):
7778
config = load_config()
7879
assert isinstance(config, Config)
@@ -87,6 +88,7 @@ def test_load_config(mock_load_dotenv, mock_getenv, mock_open):
8788
@patch("builtins.open", new_callable=mock_open, read_data='{"key": "value"}')
8889
@patch("os.getenv", side_effect=lambda k, d=None: None)
8990
@patch("cogstack_model_gateway.common.config.load_dotenv")
91+
@patch("cogstack_model_gateway.common.config._config_instance", new=None)
9092
def test_load_config_no_env_vars(mock_load_dotenv, mock_getenv, mock_open):
9193
config = load_config()
9294
assert isinstance(config, Config)

0 commit comments

Comments
 (0)