""" Command-Line Interface for CoDA. Provides a CLI for running the CoDA visualization pipeline locally. """ import argparse import logging import sys from pathlib import Path logging.basicConfig( level=logging.INFO, format="%(asctime)s - %(name)s - %(levelname)s - %(message)s" ) logger = logging.getLogger(__name__) def main(): """Main entry point for the CLI.""" parser = argparse.ArgumentParser( description="CoDA - Collaborative Data Visualization Agents", formatter_class=argparse.RawDescriptionHelpFormatter, epilog=""" Examples: python main.py --query "Show sales trends" --data sales.csv python main.py -q "Bar chart of categories" -d data.xlsx python main.py --query "Scatter plot" --data file1.csv file2.csv """ ) parser.add_argument( "-q", "--query", type=str, required=True, help="Natural language visualization query" ) parser.add_argument( "-d", "--data", type=str, nargs="+", required=True, help="Path(s) to data file(s)" ) parser.add_argument( "-o", "--output", type=str, default="outputs", help="Output directory for visualizations (default: outputs)" ) parser.add_argument( "--max-iterations", type=int, default=3, help="Maximum refinement iterations (default: 3)" ) parser.add_argument( "--min-score", type=float, default=7.0, help="Minimum quality score threshold (default: 7.0)" ) parser.add_argument( "-v", "--verbose", action="store_true", help="Enable verbose logging" ) args = parser.parse_args() if args.verbose: logging.getLogger().setLevel(logging.DEBUG) for path in args.data: if not Path(path).exists(): logger.error(f"Data file not found: {path}") sys.exit(1) try: from coda.config import Config, ExecutionConfig, QualityThresholds from coda.orchestrator import CodaOrchestrator except ImportError as e: logger.error(f"Failed to import CoDA modules: {e}") logger.error("Make sure you have installed all dependencies: pip install -r requirements.txt") sys.exit(1) try: config = Config( execution=ExecutionConfig( max_refinement_iterations=args.max_iterations, output_directory=args.output, ), quality=QualityThresholds( minimum_overall_score=args.min_score, ), ) except ValueError as e: logger.error(f"Configuration error: {e}") sys.exit(1) def progress_callback(status: str, progress: float): bar_length = 30 filled = int(bar_length * progress) bar = "ā–ˆ" * filled + "ā–‘" * (bar_length - filled) print(f"\r[{bar}] {progress:.0%} - {status}", end="", flush=True) if progress >= 1.0: print() print(f"\n{'='*60}") print("CoDA - Collaborative Data Visualization Agents") print(f"{'='*60}\n") print(f"Query: {args.query}") print(f"Data: {', '.join(args.data)}") print(f"Output: {args.output}/") print() orchestrator = CodaOrchestrator( config=config, progress_callback=progress_callback, ) result = orchestrator.run( query=args.query, data_paths=args.data, ) print() print(f"{'='*60}") print("Results") print(f"{'='*60}\n") if result.success: print(f"āœ… Visualization generated successfully!") print(f"šŸ“ Output: {result.output_file}") print(f"šŸ”„ Iterations: {result.iterations}") if result.scores: print(f"\nšŸ“Š Quality Scores:") for key, value in result.scores.items(): emoji = "🟢" if value >= 7 else "🟔" if value >= 5 else "šŸ”“" print(f" {key.title()}: {emoji} {value:.1f}/10") if result.evaluation and result.evaluation.strengths: print(f"\nšŸ’Ŗ Strengths:") for s in result.evaluation.strengths[:3]: print(f" • {s}") else: print(f"āŒ Visualization failed!") if result.error: print(f" Error: {result.error}") sys.exit(1) print() if __name__ == "__main__": main()