#!/usr/bin/env python3
"""
Test script for configuration functionality
Tests YAML/TOML configuration loading, environment variable overrides,
and configuration validation.
"""
import os
import tempfile
import shutil
from pathlib import Path
from config import ConfigurationManager, UnimusConfig, load_config
def test_yaml_config():
"""Test YAML configuration loading"""
print("๐งช Testing YAML configuration...")
# Clean environment variables for clean test
old_env = {}
env_vars = ['UNIMUS_URL', 'UNIMUS_TOKEN', 'UNIMUS_TIMEOUT', 'UNIMUS_LOG_LEVEL']
for key in env_vars:
old_env[key] = os.environ.get(key)
if key in os.environ:
del os.environ[key]
yaml_content = """
url: "https://test.example.com"
token: "test-token-123"
timeout: 45
verify_ssl: false
log_level: "DEBUG"
health_check_port: 9090
"""
with tempfile.NamedTemporaryFile(mode='w', suffix='.yaml', delete=False) as f:
f.write(yaml_content)
temp_path = f.name
try:
config = load_config(temp_path)
assert config.url == "https://test.example.com"
assert config.token == "test-token-123"
assert config.timeout == 45
assert config.verify_ssl == False
assert config.log_level == "DEBUG"
assert config.health_check_port == 9090
print(" โ
YAML configuration loaded successfully")
finally:
os.unlink(temp_path)
# Restore environment variables
for key, old_value in old_env.items():
if old_value is None:
os.environ.pop(key, None)
else:
os.environ[key] = old_value
def test_toml_config():
"""Test TOML configuration loading"""
print("๐งช Testing TOML configuration...")
# Clean environment variables for clean test
old_env = {}
env_vars = ['UNIMUS_URL', 'UNIMUS_TOKEN', 'UNIMUS_TIMEOUT', 'UNIMUS_LOG_LEVEL']
for key in env_vars:
old_env[key] = os.environ.get(key)
if key in os.environ:
del os.environ[key]
toml_content = """
url = "https://toml.example.com"
token = "toml-token-456"
timeout = 60
verify_ssl = true
log_level = "WARNING"
health_check_port = 8888
enable_health_server = false
[custom_headers]
"User-Agent" = "Test-Agent/1.0"
"""
with tempfile.NamedTemporaryFile(mode='w', suffix='.toml', delete=False) as f:
f.write(toml_content)
temp_path = f.name
try:
config = load_config(temp_path)
assert config.url == "https://toml.example.com"
assert config.token == "toml-token-456"
assert config.timeout == 60
assert config.verify_ssl == True
assert config.log_level == "WARNING"
assert config.health_check_port == 8888
assert config.enable_health_server == False
assert config.custom_headers.get("User-Agent") == "Test-Agent/1.0"
print(" โ
TOML configuration loaded successfully")
finally:
os.unlink(temp_path)
# Restore environment variables
for key, old_value in old_env.items():
if old_value is None:
os.environ.pop(key, None)
else:
os.environ[key] = old_value
def test_environment_override():
"""Test environment variable override functionality"""
print("๐งช Testing environment variable overrides...")
# Create basic config file
yaml_content = """
url: "https://file.example.com"
token: "file-token"
timeout: 30
log_level: "INFO"
"""
with tempfile.NamedTemporaryFile(mode='w', suffix='.yaml', delete=False) as f:
f.write(yaml_content)
temp_path = f.name
# Set environment variables to override config
old_env = {}
env_vars = {
'UNIMUS_URL': 'https://env.example.com',
'UNIMUS_TOKEN': 'env-token-override',
'UNIMUS_TIMEOUT': '90',
'UNIMUS_LOG_LEVEL': 'ERROR'
}
for key, value in env_vars.items():
old_env[key] = os.environ.get(key)
os.environ[key] = value
try:
config = load_config(temp_path)
# Environment variables should override file values
assert config.url == "https://env.example.com"
assert config.token == "env-token-override"
assert config.timeout == 90
assert config.log_level == "ERROR"
print(" โ
Environment variable overrides working correctly")
finally:
# Restore original environment
for key, old_value in old_env.items():
if old_value is None:
os.environ.pop(key, None)
else:
os.environ[key] = old_value
os.unlink(temp_path)
def test_config_validation():
"""Test configuration validation"""
print("๐งช Testing configuration validation...")
# Test missing required values
try:
config = UnimusConfig(url="", token="test")
assert False, "Should have raised ValueError for empty URL"
except ValueError:
print(" โ
Empty URL validation working")
try:
config = UnimusConfig(url="https://test.com", token="")
assert False, "Should have raised ValueError for empty token"
except ValueError:
print(" โ
Empty token validation working")
# Test invalid log level
try:
config = UnimusConfig(url="https://test.com", token="test", log_level="INVALID")
assert False, "Should have raised ValueError for invalid log level"
except ValueError:
print(" โ
Invalid log level validation working")
# Test invalid numeric values
try:
config = UnimusConfig(url="https://test.com", token="test", timeout=-5)
assert False, "Should have raised ValueError for negative timeout"
except ValueError:
print(" โ
Negative timeout validation working")
try:
config = UnimusConfig(url="https://test.com", token="test", health_check_port=70000)
assert False, "Should have raised ValueError for invalid port"
except ValueError:
print(" โ
Invalid port validation working")
def test_config_search_paths():
"""Test configuration file search functionality"""
print("๐งช Testing configuration file search paths...")
# Clean environment variables for clean test
old_env = {}
env_vars = ['UNIMUS_URL', 'UNIMUS_TOKEN', 'UNIMUS_TIMEOUT', 'UNIMUS_LOG_LEVEL']
for key in env_vars:
old_env[key] = os.environ.get(key)
if key in os.environ:
del os.environ[key]
# Create temporary directory structure
with tempfile.TemporaryDirectory() as temp_dir:
config_dir = Path(temp_dir) / "config"
config_dir.mkdir()
# Create config file in subdirectory
config_path = config_dir / "unimus-mcp.yaml"
config_content = """
url: "https://search.example.com"
token: "search-token"
"""
config_path.write_text(config_content)
# Change to temp directory so search finds the config
old_cwd = os.getcwd()
os.chdir(temp_dir)
try:
config = load_config() # Should find config/unimus-mcp.yaml
assert config.url == "https://search.example.com"
assert config.token == "search-token"
print(" โ
Configuration file search working")
finally:
os.chdir(old_cwd)
# Restore environment variables
for key, old_value in old_env.items():
if old_value is None:
os.environ.pop(key, None)
else:
os.environ[key] = old_value
def test_fallback_to_env():
"""Test fallback to environment variables when no config file exists"""
print("๐งช Testing fallback to environment variables...")
# Set environment variables
old_env = {}
env_vars = {
'UNIMUS_URL': 'https://fallback.example.com',
'UNIMUS_TOKEN': 'fallback-token'
}
for key, value in env_vars.items():
old_env[key] = os.environ.get(key)
os.environ[key] = value
try:
# Try to load config from non-existent path
config = load_config("/non/existent/path.yaml")
# Should fall back to environment variables
assert config.url == "https://fallback.example.com"
assert config.token == "fallback-token"
print(" โ
Fallback to environment variables working")
finally:
# Restore environment
for key, old_value in old_env.items():
if old_value is None:
os.environ.pop(key, None)
else:
os.environ[key] = old_value
if __name__ == "__main__":
print("๐ง Testing Unimus MCP Configuration System")
print("=" * 50)
try:
test_yaml_config()
test_toml_config()
test_environment_override()
test_config_validation()
test_config_search_paths()
test_fallback_to_env()
print("\n" + "=" * 50)
print("๐ All configuration tests passed!")
print("\n๐ Configuration system features tested:")
print(" โ
YAML configuration file loading")
print(" โ
TOML configuration file loading")
print(" โ
Environment variable overrides")
print(" โ
Configuration validation")
print(" โ
Configuration file search paths")
print(" โ
Fallback to environment variables")
except Exception as e:
print(f"\nโ Test failed: {e}")
import traceback
traceback.print_exc()
exit(1)