diegobeyl/backtesting
2
1"""
2Configuration management for Backtesting App V2
3Loads settings from .env file and provides typed access to configuration values.
4"""
5import os
6from typing import List
7from pathlib import Path
8from dotenv import load_dotenv
9
10# Load environment variables from .env file
11load_dotenv()
12
13# Base directory
14BASE_DIR = Path(__file__).resolve().parent
15
16
17class Config:
18 """Application configuration loaded from environment variables."""
19
20 # Application Settings
21 DEBUG: bool = os.getenv('DEBUG', 'False').lower() == 'true'
22 LOG_LEVEL: str = os.getenv('LOG_LEVEL', 'WARNING').upper()
23 ENVIRONMENT: str = os.getenv('ENVIRONMENT', 'development')
24
25 # Server Configuration
26 API_HOST: str = os.getenv('API_HOST', '0.0.0.0')
27 API_PORT: int = int(os.getenv('API_PORT', '8000'))
28 STREAMLIT_PORT: int = int(os.getenv('STREAMLIT_PORT', '8501'))
29
30 # CORS Configuration
31 CORS_ORIGINS: List[str] = [
32 origin.strip()
33 for origin in os.getenv('CORS_ORIGINS', 'http://localhost:8501').split(',')
34 ]
35
36 # Rate Limiting
37 RATE_LIMIT_PER_MINUTE: int = int(os.getenv('RATE_LIMIT_PER_MINUTE', '60'))
38 RATE_LIMIT_PER_HOUR: int = int(os.getenv('RATE_LIMIT_PER_HOUR', '1000'))
39
40 # Cache Configuration
41 ENABLE_CACHE: bool = os.getenv('ENABLE_CACHE', 'True').lower() == 'true'
42 CACHE_DIR: Path = BASE_DIR / os.getenv('CACHE_DIR', 'cache')
43 CACHE_EXPIRY_HOURS: int = int(os.getenv('CACHE_EXPIRY_HOURS', '24'))
44
45 # Logging Configuration
46 LOG_FILE: Path = BASE_DIR / os.getenv('LOG_FILE', 'logs/app.log')
47 LOG_MAX_BYTES: int = int(os.getenv('LOG_MAX_BYTES', '10485760')) # 10MB
48 LOG_BACKUP_COUNT: int = int(os.getenv('LOG_BACKUP_COUNT', '5'))
49 LOG_FORMAT: str = os.getenv('LOG_FORMAT', 'json') # 'json' or 'text'
50
51 @classmethod
52 def ensure_directories(cls):
53 """Create necessary directories if they don't exist."""
54 cls.CACHE_DIR.mkdir(parents=True, exist_ok=True)
55 cls.LOG_FILE.parent.mkdir(parents=True, exist_ok=True)
56
57 @classmethod
58 def validate(cls):
59 """Validate configuration values."""
60 assert cls.LOG_LEVEL in ['DEBUG', 'INFO', 'WARNING', 'ERROR', 'CRITICAL'], \
61 f"Invalid LOG_LEVEL: {cls.LOG_LEVEL}"
62 assert cls.ENVIRONMENT in ['development', 'staging', 'production'], \
63 f"Invalid ENVIRONMENT: {cls.ENVIRONMENT}"
64 assert cls.API_PORT > 0 and cls.API_PORT < 65536, \
65 f"Invalid API_PORT: {cls.API_PORT}"
66 assert cls.RATE_LIMIT_PER_MINUTE > 0, \
67 f"Invalid RATE_LIMIT_PER_MINUTE: {cls.RATE_LIMIT_PER_MINUTE}"
68
69
70# Initialize configuration on import
71Config.ensure_directories()
72Config.validate()
73
74
75# Export singleton instance
76config = Config()
77 