"""Configuration loading for Splitwise MCP Server."""
import json
import os
from pathlib import Path
class ConfigurationError(Exception):
"""Raised when required configuration is missing or invalid."""
pass
def load_config() -> dict:
"""
Load configuration from environment variables or config file.
Priority:
1. Environment variables (SPLITWISE_API_KEY, SPLITWISE_GROUP_ID, etc.)
2. Config file at SPLITWISE_CONFIG_PATH
3. Config file at ./config.json
Returns:
dict: Configuration with keys: api_key, group_id, payer_id, partner_id
Raises:
ConfigurationError: If required configuration is missing
"""
config = {}
# Try to load from config file first (will be overridden by env vars)
config_file_path = None
# Check SPLITWISE_CONFIG_PATH
if os.environ.get("SPLITWISE_CONFIG_PATH"):
config_file_path = Path(os.environ["SPLITWISE_CONFIG_PATH"])
# Check ./config.json
elif Path("config.json").exists():
config_file_path = Path("config.json")
if config_file_path and config_file_path.exists():
try:
with open(config_file_path) as f:
file_config = json.load(f)
splitwise_config = file_config.get("splitwise", {})
config["api_key"] = splitwise_config.get("api_key", "")
config["group_id"] = splitwise_config.get("group_id", "")
config["payer_id"] = splitwise_config.get("payer_id", "")
config["partner_id"] = splitwise_config.get("partner_id", "")
except (json.JSONDecodeError, IOError) as e:
raise ConfigurationError(f"Failed to read config file {config_file_path}: {e}")
# Environment variables override file config
if os.environ.get("SPLITWISE_API_KEY"):
config["api_key"] = os.environ["SPLITWISE_API_KEY"]
if os.environ.get("SPLITWISE_GROUP_ID"):
config["group_id"] = os.environ["SPLITWISE_GROUP_ID"]
if os.environ.get("SPLITWISE_PAYER_ID"):
config["payer_id"] = os.environ["SPLITWISE_PAYER_ID"]
if os.environ.get("SPLITWISE_PARTNER_ID"):
config["partner_id"] = os.environ["SPLITWISE_PARTNER_ID"]
# Validate required fields
required_fields = ["api_key", "group_id", "payer_id", "partner_id"]
missing_fields = [f for f in required_fields if not config.get(f)]
if missing_fields:
raise ConfigurationError(
f"Missing required configuration fields: {', '.join(missing_fields)}\n\n"
"Set environment variables:\n"
" SPLITWISE_API_KEY=your_api_key\n"
" SPLITWISE_GROUP_ID=your_group_id\n"
" SPLITWISE_PAYER_ID=your_user_id\n"
" SPLITWISE_PARTNER_ID=partner_user_id\n\n"
"Or create config.json (see config.example.json for template)"
)
return config