#!/usr/bin/env python3 """Alibaba Cloud billing anomaly analyzer CLI.""" from __future__ import annotations import argparse import json import sys from pathlib import Path from typing import List, Optional from alibaba_cloud.src.analysis.analyzer import AlibabaCloudBillingAnalyzer def parse_args(argv: Optional[List[str]] = None) -> argparse.Namespace: parser = argparse.ArgumentParser( description="Analyze Alibaba Cloud billing exports and send Feishu alerts.", formatter_class=argparse.ArgumentDefaultsHelpFormatter, ) parser.add_argument( "--date", type=str, help="Target analysis date (YYYY-MM-DD). Defaults to two days ago.", ) parser.add_argument( "--config", type=str, help="Path to config.json. Defaults to alibaba_cloud/config.json.", ) parser.add_argument( "--data-dir", type=Path, help="Override the billing export directory.", ) parser.add_argument( "--env", action="append", dest="environments", help="Environment filter; repeatable. Use 'all' for every environment.", ) parser.add_argument( "--account-id", action="append", dest="account_ids", help="Analyze specified account IDs only.", ) parser.add_argument( "--dry-run", action="store_true", help="Run analysis without sending Feishu notifications.", ) parser.add_argument( "--no-notify", action="store_true", help="Skip Feishu notifications even if webhooks are configured.", ) parser.add_argument( "--output-json", action="store_true", help="Print the raw analysis results as JSON.", ) return parser.parse_args(argv) def main(argv: Optional[List[str]] = None) -> int: args = parse_args(argv) try: analyzer = AlibabaCloudBillingAnalyzer( config_path=args.config, data_dir=str(args.data_dir) if args.data_dir else None, ) results = analyzer.analyze( target_date=args.date, environments=args.environments, account_ids=args.account_ids, dry_run=args.dry_run, send_notifications=not args.no_notify, ) if args.output_json or args.dry_run: print(json.dumps(results, indent=2, ensure_ascii=False)) else: for env_name, result in results.items(): print( f"[{env_name}] {result['target_date']} total {result['total_cost']:.2f} " f"{result['currency']} anomalies {result['total_anomalies']}" ) return 0 except Exception as exc: # pylint: disable=broad-except print(f"Alibaba Cloud analysis failed: {exc}") return 1 if __name__ == "__main__": sys.exit(main())