Source code for ensemble_analyzer.cli.check_setup

#!/usr/bin/env python3
import shutil
import os
import sys
import importlib.util
from pathlib import Path

# Colors for output
GREEN = '\033[92m'
RED = '\033[91m'
YELLOW = '\033[93m'
RESET = '\033[0m'

[docs] def log_pass(msg) -> None: """Print a success message in green.""" print(f"[{GREEN}PASS{RESET}] {msg}")
[docs] def log_fail(msg) -> None: """Print a failure message in red.""" print(f"[{RED}FAIL{RESET}] {msg}")
[docs] def log_warn(msg) -> None: """Print a warning message in yellow.""" print(f"[{YELLOW}WARN{RESET}] {msg}")
[docs] def check_python_dependencies() -> bool: """ Verify that all required Python libraries are installed and importable. Returns: bool: True if all critical dependencies are found. """ print(f"\n{'-'*20} 1. Checking Python Dependencies {'-'*20}") required = ['numpy', 'scipy', 'matplotlib', 'ase', 'numba', 'sklearn'] all_pass = True for lib in required: if importlib.util.find_spec(lib) is not None: log_pass(f"Library found: {lib}") else: log_fail(f"Library MISSING: {lib}") all_pass = False # Check EnAn package itself if importlib.util.find_spec("ensemble_analyzer") is not None: log_pass("Ensemble Analyzer package is installed and importable.") else: log_fail("Ensemble Analyzer package NOT found. Did you run 'pip install .'?") all_pass = False return all_pass
[docs] def check_orca() -> bool: """ Verify ORCA installation and environment configuration. Checks: 1. 'orca' executable in PATH. 2. 'ORCAVERSION' environment variable. Returns: bool: True if ORCA is correctly configured. """ print(f"\n{'-'*20} 2. Checking ORCA Configuration {'-'*20}") # Check 1: Executable in PATH orca_path = shutil.which("orca") if orca_path: log_pass(f"ORCA executable found at: {orca_path}") else: log_fail("ORCA executable NOT found in PATH.") return False # Check 2: Environment Variable version_env = os.environ.get("ORCAVERSION") if version_env: log_pass(f"ORCAVERSION environment variable is set to: {version_env}") else: log_fail("ORCAVERSION environment variable is MISSING.") print(f" {YELLOW}Hint: export ORCAVERSION='x.y.z' in your shell config.{RESET}") return False return True
[docs] def check_gaussian() -> None: """ Check for Gaussian availability (Optional). Looks for 'g16' or 'g09' in PATH. """ print(f"\n{'-'*20} 3. Checking Gaussian Configuration {'-'*20}") g16_path = shutil.which("g16") g09_path = shutil.which("g09") if g16_path: log_pass(f"Gaussian 16 found at: {g16_path}") elif g09_path: log_pass(f"Gaussian 09 found at: {g09_path}") else: log_warn("Gaussian executable (g16/g09) NOT found. (Optional if using ORCA)")
[docs] def check_ml_potentials() -> None: """ Check optional ML potential dependencies (TBLite, AIMNet). """ print(f"\n{'-'*20} 4. Checking ML Potentials {'-'*20}") # TBLite if importlib.util.find_spec("tblite") is not None: log_pass("TBLite library found.") else: log_warn("TBLite NOT installed. Install: pip install \"ensemble-analyzer[tblite]\"") # AIMNet try: import aimnet log_pass("aimnet found.") except ImportError: log_warn("aimnet NOT installed. Install: pip install \"ensemble-analyzer[aimnet]\"")
[docs] def check_models_dir() -> None: """Check ENAN_MODELS_DIR environment variable.""" models_dir = os.environ.get("ENAN_MODELS_DIR") if models_dir: p = Path(models_dir) if p.is_dir(): log_pass(f"ENAN_MODELS_DIR = {models_dir}") else: log_warn(f"ENAN_MODELS_DIR = {models_dir} (directory does not exist yet)") else: log_warn("ENAN_MODELS_DIR not set. ML models default to ~/.ensemble_analyzer/models/")
[docs] def main() -> None: """Run the complete installation check suite.""" print(f"Running Ensemble Analyzer Installation Check...\n") deps_ok = check_python_dependencies() orca_ok = check_orca() check_gaussian() check_ml_potentials() check_models_dir() print(f"\n{'-'*50}") if deps_ok and orca_ok: print(f"{GREEN}SUCCESS: Installation looks correct! You are ready to run EnAn.{RESET}") sys.exit(0) else: print(f"{RED}FAILURE: Critical issues found. Please fix the errors above.{RESET}") sys.exit(1)
if __name__ == "__main__": main()