runbooks 1.1.3__py3-none-any.whl → 1.1.5__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (247) hide show
  1. runbooks/__init__.py +31 -2
  2. runbooks/__init___optimized.py +18 -4
  3. runbooks/_platform/__init__.py +1 -5
  4. runbooks/_platform/core/runbooks_wrapper.py +141 -138
  5. runbooks/aws2/accuracy_validator.py +812 -0
  6. runbooks/base.py +7 -0
  7. runbooks/cfat/WEIGHT_CONFIG_README.md +1 -1
  8. runbooks/cfat/assessment/compliance.py +8 -8
  9. runbooks/cfat/assessment/runner.py +1 -0
  10. runbooks/cfat/cloud_foundations_assessment.py +227 -239
  11. runbooks/cfat/models.py +6 -2
  12. runbooks/cfat/tests/__init__.py +6 -1
  13. runbooks/cli/__init__.py +13 -0
  14. runbooks/cli/commands/cfat.py +274 -0
  15. runbooks/cli/commands/finops.py +1164 -0
  16. runbooks/cli/commands/inventory.py +379 -0
  17. runbooks/cli/commands/operate.py +239 -0
  18. runbooks/cli/commands/security.py +248 -0
  19. runbooks/cli/commands/validation.py +825 -0
  20. runbooks/cli/commands/vpc.py +310 -0
  21. runbooks/cli/registry.py +107 -0
  22. runbooks/cloudops/__init__.py +23 -30
  23. runbooks/cloudops/base.py +96 -107
  24. runbooks/cloudops/cost_optimizer.py +549 -547
  25. runbooks/cloudops/infrastructure_optimizer.py +5 -4
  26. runbooks/cloudops/interfaces.py +226 -227
  27. runbooks/cloudops/lifecycle_manager.py +5 -4
  28. runbooks/cloudops/mcp_cost_validation.py +252 -235
  29. runbooks/cloudops/models.py +78 -53
  30. runbooks/cloudops/monitoring_automation.py +5 -4
  31. runbooks/cloudops/notebook_framework.py +179 -215
  32. runbooks/cloudops/security_enforcer.py +125 -159
  33. runbooks/common/accuracy_validator.py +11 -0
  34. runbooks/common/aws_pricing.py +349 -326
  35. runbooks/common/aws_pricing_api.py +211 -212
  36. runbooks/common/aws_profile_manager.py +341 -0
  37. runbooks/common/aws_utils.py +75 -80
  38. runbooks/common/business_logic.py +127 -105
  39. runbooks/common/cli_decorators.py +36 -60
  40. runbooks/common/comprehensive_cost_explorer_integration.py +456 -464
  41. runbooks/common/cross_account_manager.py +198 -205
  42. runbooks/common/date_utils.py +27 -39
  43. runbooks/common/decorators.py +235 -0
  44. runbooks/common/dry_run_examples.py +173 -208
  45. runbooks/common/dry_run_framework.py +157 -155
  46. runbooks/common/enhanced_exception_handler.py +15 -4
  47. runbooks/common/enhanced_logging_example.py +50 -64
  48. runbooks/common/enhanced_logging_integration_example.py +65 -37
  49. runbooks/common/env_utils.py +16 -16
  50. runbooks/common/error_handling.py +40 -38
  51. runbooks/common/lazy_loader.py +41 -23
  52. runbooks/common/logging_integration_helper.py +79 -86
  53. runbooks/common/mcp_cost_explorer_integration.py +478 -495
  54. runbooks/common/mcp_integration.py +63 -74
  55. runbooks/common/memory_optimization.py +140 -118
  56. runbooks/common/module_cli_base.py +37 -58
  57. runbooks/common/organizations_client.py +176 -194
  58. runbooks/common/patterns.py +204 -0
  59. runbooks/common/performance_monitoring.py +67 -71
  60. runbooks/common/performance_optimization_engine.py +283 -274
  61. runbooks/common/profile_utils.py +248 -39
  62. runbooks/common/rich_utils.py +643 -92
  63. runbooks/common/sre_performance_suite.py +177 -186
  64. runbooks/enterprise/__init__.py +1 -1
  65. runbooks/enterprise/logging.py +144 -106
  66. runbooks/enterprise/security.py +187 -204
  67. runbooks/enterprise/validation.py +43 -56
  68. runbooks/finops/__init__.py +29 -33
  69. runbooks/finops/account_resolver.py +1 -1
  70. runbooks/finops/advanced_optimization_engine.py +980 -0
  71. runbooks/finops/automation_core.py +268 -231
  72. runbooks/finops/business_case_config.py +184 -179
  73. runbooks/finops/cli.py +660 -139
  74. runbooks/finops/commvault_ec2_analysis.py +157 -164
  75. runbooks/finops/compute_cost_optimizer.py +336 -320
  76. runbooks/finops/config.py +20 -20
  77. runbooks/finops/cost_optimizer.py +488 -622
  78. runbooks/finops/cost_processor.py +332 -214
  79. runbooks/finops/dashboard_runner.py +1006 -172
  80. runbooks/finops/ebs_cost_optimizer.py +991 -657
  81. runbooks/finops/elastic_ip_optimizer.py +317 -257
  82. runbooks/finops/enhanced_mcp_integration.py +340 -0
  83. runbooks/finops/enhanced_progress.py +40 -37
  84. runbooks/finops/enhanced_trend_visualization.py +3 -2
  85. runbooks/finops/enterprise_wrappers.py +230 -292
  86. runbooks/finops/executive_export.py +203 -160
  87. runbooks/finops/helpers.py +130 -288
  88. runbooks/finops/iam_guidance.py +1 -1
  89. runbooks/finops/infrastructure/__init__.py +80 -0
  90. runbooks/finops/infrastructure/commands.py +506 -0
  91. runbooks/finops/infrastructure/load_balancer_optimizer.py +866 -0
  92. runbooks/finops/infrastructure/vpc_endpoint_optimizer.py +832 -0
  93. runbooks/finops/markdown_exporter.py +338 -175
  94. runbooks/finops/mcp_validator.py +1952 -0
  95. runbooks/finops/nat_gateway_optimizer.py +1513 -482
  96. runbooks/finops/network_cost_optimizer.py +657 -587
  97. runbooks/finops/notebook_utils.py +226 -188
  98. runbooks/finops/optimization_engine.py +1136 -0
  99. runbooks/finops/optimizer.py +25 -29
  100. runbooks/finops/rds_snapshot_optimizer.py +367 -411
  101. runbooks/finops/reservation_optimizer.py +427 -363
  102. runbooks/finops/scenario_cli_integration.py +77 -78
  103. runbooks/finops/scenarios.py +1278 -439
  104. runbooks/finops/schemas.py +218 -182
  105. runbooks/finops/snapshot_manager.py +2289 -0
  106. runbooks/finops/tests/test_finops_dashboard.py +3 -3
  107. runbooks/finops/tests/test_reference_images_validation.py +2 -2
  108. runbooks/finops/tests/test_single_account_features.py +17 -17
  109. runbooks/finops/tests/validate_test_suite.py +1 -1
  110. runbooks/finops/types.py +3 -3
  111. runbooks/finops/validation_framework.py +263 -269
  112. runbooks/finops/vpc_cleanup_exporter.py +191 -146
  113. runbooks/finops/vpc_cleanup_optimizer.py +593 -575
  114. runbooks/finops/workspaces_analyzer.py +171 -182
  115. runbooks/hitl/enhanced_workflow_engine.py +1 -1
  116. runbooks/integration/__init__.py +89 -0
  117. runbooks/integration/mcp_integration.py +1920 -0
  118. runbooks/inventory/CLAUDE.md +816 -0
  119. runbooks/inventory/README.md +3 -3
  120. runbooks/inventory/Tests/common_test_data.py +30 -30
  121. runbooks/inventory/__init__.py +2 -2
  122. runbooks/inventory/cloud_foundations_integration.py +144 -149
  123. runbooks/inventory/collectors/aws_comprehensive.py +28 -11
  124. runbooks/inventory/collectors/aws_networking.py +111 -101
  125. runbooks/inventory/collectors/base.py +4 -0
  126. runbooks/inventory/core/collector.py +495 -313
  127. runbooks/inventory/discovery.md +2 -2
  128. runbooks/inventory/drift_detection_cli.py +69 -96
  129. runbooks/inventory/find_ec2_security_groups.py +1 -1
  130. runbooks/inventory/inventory_mcp_cli.py +48 -46
  131. runbooks/inventory/list_rds_snapshots_aggregator.py +192 -208
  132. runbooks/inventory/mcp_inventory_validator.py +549 -465
  133. runbooks/inventory/mcp_vpc_validator.py +359 -442
  134. runbooks/inventory/organizations_discovery.py +56 -52
  135. runbooks/inventory/rich_inventory_display.py +33 -32
  136. runbooks/inventory/unified_validation_engine.py +278 -251
  137. runbooks/inventory/vpc_analyzer.py +733 -696
  138. runbooks/inventory/vpc_architecture_validator.py +293 -348
  139. runbooks/inventory/vpc_dependency_analyzer.py +382 -378
  140. runbooks/inventory/vpc_flow_analyzer.py +3 -3
  141. runbooks/main.py +152 -9147
  142. runbooks/main_final.py +91 -60
  143. runbooks/main_minimal.py +22 -10
  144. runbooks/main_optimized.py +131 -100
  145. runbooks/main_ultra_minimal.py +7 -2
  146. runbooks/mcp/__init__.py +36 -0
  147. runbooks/mcp/integration.py +679 -0
  148. runbooks/metrics/dora_metrics_engine.py +2 -2
  149. runbooks/monitoring/performance_monitor.py +9 -4
  150. runbooks/operate/dynamodb_operations.py +3 -1
  151. runbooks/operate/ec2_operations.py +145 -137
  152. runbooks/operate/iam_operations.py +146 -152
  153. runbooks/operate/mcp_integration.py +1 -1
  154. runbooks/operate/networking_cost_heatmap.py +33 -10
  155. runbooks/operate/privatelink_operations.py +1 -1
  156. runbooks/operate/rds_operations.py +223 -254
  157. runbooks/operate/s3_operations.py +107 -118
  158. runbooks/operate/vpc_endpoints.py +1 -1
  159. runbooks/operate/vpc_operations.py +648 -618
  160. runbooks/remediation/base.py +1 -1
  161. runbooks/remediation/commons.py +10 -7
  162. runbooks/remediation/commvault_ec2_analysis.py +71 -67
  163. runbooks/remediation/ec2_unattached_ebs_volumes.py +1 -0
  164. runbooks/remediation/multi_account.py +24 -21
  165. runbooks/remediation/rds_snapshot_list.py +91 -65
  166. runbooks/remediation/remediation_cli.py +92 -146
  167. runbooks/remediation/universal_account_discovery.py +83 -79
  168. runbooks/remediation/workspaces_list.py +49 -44
  169. runbooks/security/__init__.py +19 -0
  170. runbooks/security/assessment_runner.py +1150 -0
  171. runbooks/security/baseline_checker.py +812 -0
  172. runbooks/security/cloudops_automation_security_validator.py +509 -535
  173. runbooks/security/compliance_automation_engine.py +17 -17
  174. runbooks/security/config/__init__.py +2 -2
  175. runbooks/security/config/compliance_config.py +50 -50
  176. runbooks/security/config_template_generator.py +63 -76
  177. runbooks/security/enterprise_security_framework.py +1 -1
  178. runbooks/security/executive_security_dashboard.py +519 -508
  179. runbooks/security/integration_test_enterprise_security.py +5 -3
  180. runbooks/security/multi_account_security_controls.py +959 -1210
  181. runbooks/security/real_time_security_monitor.py +422 -444
  182. runbooks/security/run_script.py +1 -1
  183. runbooks/security/security_baseline_tester.py +1 -1
  184. runbooks/security/security_cli.py +143 -112
  185. runbooks/security/test_2way_validation.py +439 -0
  186. runbooks/security/two_way_validation_framework.py +852 -0
  187. runbooks/sre/mcp_reliability_engine.py +6 -6
  188. runbooks/sre/production_monitoring_framework.py +167 -177
  189. runbooks/tdd/__init__.py +15 -0
  190. runbooks/tdd/cli.py +1071 -0
  191. runbooks/utils/__init__.py +14 -17
  192. runbooks/utils/logger.py +7 -2
  193. runbooks/utils/version_validator.py +51 -48
  194. runbooks/validation/__init__.py +6 -6
  195. runbooks/validation/cli.py +9 -3
  196. runbooks/validation/comprehensive_2way_validator.py +754 -708
  197. runbooks/validation/mcp_validator.py +906 -228
  198. runbooks/validation/terraform_citations_validator.py +104 -115
  199. runbooks/validation/terraform_drift_detector.py +447 -451
  200. runbooks/vpc/README.md +617 -0
  201. runbooks/vpc/__init__.py +8 -1
  202. runbooks/vpc/analyzer.py +577 -0
  203. runbooks/vpc/cleanup_wrapper.py +476 -413
  204. runbooks/vpc/cli_cloudtrail_commands.py +339 -0
  205. runbooks/vpc/cli_mcp_validation_commands.py +480 -0
  206. runbooks/vpc/cloudtrail_audit_integration.py +717 -0
  207. runbooks/vpc/config.py +92 -97
  208. runbooks/vpc/cost_engine.py +411 -148
  209. runbooks/vpc/cost_explorer_integration.py +553 -0
  210. runbooks/vpc/cross_account_session.py +101 -106
  211. runbooks/vpc/enhanced_mcp_validation.py +917 -0
  212. runbooks/vpc/eni_gate_validator.py +961 -0
  213. runbooks/vpc/heatmap_engine.py +190 -162
  214. runbooks/vpc/mcp_no_eni_validator.py +681 -640
  215. runbooks/vpc/nat_gateway_optimizer.py +358 -0
  216. runbooks/vpc/networking_wrapper.py +15 -8
  217. runbooks/vpc/pdca_remediation_planner.py +528 -0
  218. runbooks/vpc/performance_optimized_analyzer.py +219 -231
  219. runbooks/vpc/runbooks_adapter.py +1167 -241
  220. runbooks/vpc/tdd_red_phase_stubs.py +601 -0
  221. runbooks/vpc/test_data_loader.py +358 -0
  222. runbooks/vpc/tests/conftest.py +314 -4
  223. runbooks/vpc/tests/test_cleanup_framework.py +1022 -0
  224. runbooks/vpc/tests/test_cost_engine.py +0 -2
  225. runbooks/vpc/topology_generator.py +326 -0
  226. runbooks/vpc/unified_scenarios.py +1302 -1129
  227. runbooks/vpc/vpc_cleanup_integration.py +1943 -1115
  228. runbooks-1.1.5.dist-info/METADATA +328 -0
  229. {runbooks-1.1.3.dist-info → runbooks-1.1.5.dist-info}/RECORD +233 -200
  230. runbooks/finops/README.md +0 -414
  231. runbooks/finops/accuracy_cross_validator.py +0 -647
  232. runbooks/finops/business_cases.py +0 -950
  233. runbooks/finops/dashboard_router.py +0 -922
  234. runbooks/finops/ebs_optimizer.py +0 -956
  235. runbooks/finops/embedded_mcp_validator.py +0 -1629
  236. runbooks/finops/enhanced_dashboard_runner.py +0 -527
  237. runbooks/finops/finops_dashboard.py +0 -584
  238. runbooks/finops/finops_scenarios.py +0 -1218
  239. runbooks/finops/legacy_migration.py +0 -730
  240. runbooks/finops/multi_dashboard.py +0 -1519
  241. runbooks/finops/single_dashboard.py +0 -1113
  242. runbooks/finops/unlimited_scenarios.py +0 -393
  243. runbooks-1.1.3.dist-info/METADATA +0 -799
  244. {runbooks-1.1.3.dist-info → runbooks-1.1.5.dist-info}/WHEEL +0 -0
  245. {runbooks-1.1.3.dist-info → runbooks-1.1.5.dist-info}/entry_points.txt +0 -0
  246. {runbooks-1.1.3.dist-info → runbooks-1.1.5.dist-info}/licenses/LICENSE +0 -0
  247. {runbooks-1.1.3.dist-info → runbooks-1.1.5.dist-info}/top_level.txt +0 -0
@@ -46,8 +46,17 @@ from botocore.exceptions import ClientError, NoCredentialsError
46
46
 
47
47
  # Internal imports
48
48
  from runbooks.common.rich_utils import (
49
- console, print_header, print_success, print_error, print_warning, print_info,
50
- create_table, create_panel, format_cost, create_progress_bar, STATUS_INDICATORS
49
+ console,
50
+ print_header,
51
+ print_success,
52
+ print_error,
53
+ print_warning,
54
+ print_info,
55
+ create_table,
56
+ create_panel,
57
+ format_cost,
58
+ create_progress_bar,
59
+ STATUS_INDICATORS,
51
60
  )
52
61
 
53
62
  # Profile and pricing integration
@@ -55,6 +64,7 @@ try:
55
64
  from runbooks.common.profile_utils import get_profile_for_operation
56
65
  from runbooks.common.aws_pricing import get_aws_pricing_engine, calculate_annual_cost
57
66
  from runbooks.common.mcp_cost_explorer_integration import MCPCostExplorerIntegration
67
+
58
68
  INTEGRATIONS_AVAILABLE = True
59
69
  except ImportError as e:
60
70
  print_warning(f"Integration modules not fully available: {e}")
@@ -63,6 +73,7 @@ except ImportError as e:
63
73
  # Terraform drift detection integration
64
74
  try:
65
75
  from runbooks.validation.terraform_drift_detector import TerraformDriftDetector
76
+
66
77
  TERRAFORM_INTEGRATION_AVAILABLE = True
67
78
  except ImportError:
68
79
  print_warning("Terraform drift detection not available")
@@ -74,6 +85,7 @@ logger = logging.getLogger(__name__)
74
85
  @dataclass
75
86
  class CostExplorerResult:
76
87
  """Comprehensive Cost Explorer API result."""
88
+
77
89
  service_name: str
78
90
  account_id: str
79
91
  region: str
@@ -90,6 +102,7 @@ class CostExplorerResult:
90
102
  @dataclass
91
103
  class TerraformCostAlignment:
92
104
  """Terraform infrastructure cost alignment."""
105
+
93
106
  terraform_resource_id: str
94
107
  terraform_resource_type: str
95
108
  cost_explorer_attribution: Decimal
@@ -101,27 +114,28 @@ class TerraformCostAlignment:
101
114
  @dataclass
102
115
  class ComprehensiveCostAnalysis:
103
116
  """Complete cost analysis with infrastructure alignment."""
117
+
104
118
  analysis_id: str
105
119
  analysis_timestamp: datetime
106
-
120
+
107
121
  # Cost Explorer data
108
122
  cost_explorer_results: List[CostExplorerResult]
109
123
  total_monthly_cost: Decimal
110
124
  total_annual_projection: Decimal
111
-
125
+
112
126
  # MCP validation
113
127
  mcp_validation_accuracy: float
114
128
  mcp_cross_validation_results: Dict[str, Any]
115
-
129
+
116
130
  # Terraform alignment
117
131
  terraform_cost_alignment: List[TerraformCostAlignment]
118
132
  infrastructure_drift_summary: Dict[str, Any]
119
-
133
+
120
134
  # Business impact
121
135
  optimization_opportunities: List[Dict[str, Any]]
122
136
  annual_savings_potential: Decimal
123
137
  roi_projection: float
124
-
138
+
125
139
  # Compliance and governance
126
140
  compliance_status: str
127
141
  audit_trail: Dict[str, Any]
@@ -131,21 +145,23 @@ class ComprehensiveCostAnalysis:
131
145
  class ComprehensiveCostExplorerIntegration:
132
146
  """
133
147
  Comprehensive AWS Cost Explorer integration with MCP validation and terraform alignment.
134
-
148
+
135
149
  Provides enterprise-grade cost analysis with real-time API integration,
136
150
  comprehensive validation, and infrastructure governance alignment.
137
151
  """
138
-
139
- def __init__(self,
140
- billing_profile: Optional[str] = None,
141
- management_profile: Optional[str] = None,
142
- single_account_profile: Optional[str] = None,
143
- terraform_state_dir: Optional[str] = None,
144
- validation_tolerance_percent: float = 5.0,
145
- performance_target_seconds: float = 30.0):
152
+
153
+ def __init__(
154
+ self,
155
+ billing_profile: Optional[str] = None,
156
+ management_profile: Optional[str] = None,
157
+ single_account_profile: Optional[str] = None,
158
+ terraform_state_dir: Optional[str] = None,
159
+ validation_tolerance_percent: float = 5.0,
160
+ performance_target_seconds: float = 30.0,
161
+ ):
146
162
  """
147
163
  Initialize comprehensive Cost Explorer integration.
148
-
164
+
149
165
  Args:
150
166
  billing_profile: AWS profile for Cost Explorer access
151
167
  management_profile: AWS profile for Organizations access
@@ -160,33 +176,33 @@ class ComprehensiveCostExplorerIntegration:
160
176
  self.terraform_state_dir = terraform_state_dir
161
177
  self.validation_tolerance = validation_tolerance_percent
162
178
  self.performance_target = performance_target_seconds
163
-
179
+
164
180
  # Component integrations
165
181
  self.mcp_integration = None
166
182
  self.terraform_detector = None
167
183
  self.pricing_engine = None
168
-
184
+
169
185
  # Results and caching
170
186
  self.analysis_cache = {}
171
187
  self.evidence_dir = Path("validation-evidence") / "comprehensive-cost-analysis"
172
188
  self.evidence_dir.mkdir(parents=True, exist_ok=True)
173
-
189
+
174
190
  print_header("Comprehensive Cost Explorer Integration", "1.0.0")
175
191
  print_info("🏗️ Initializing enterprise cost analysis with infrastructure alignment...")
176
-
192
+
177
193
  async def initialize_integrations(self, user_profile_override: Optional[str] = None) -> Dict[str, Any]:
178
194
  """Initialize all component integrations."""
179
-
195
+
180
196
  initialization_results = {
181
- 'timestamp': datetime.now().isoformat(),
182
- 'user_profile_override': user_profile_override,
183
- 'integrations': {},
184
- 'overall_status': 'unknown'
197
+ "timestamp": datetime.now().isoformat(),
198
+ "user_profile_override": user_profile_override,
199
+ "integrations": {},
200
+ "overall_status": "unknown",
185
201
  }
186
-
202
+
187
203
  with create_progress_bar() as progress:
188
204
  task = progress.add_task("Initializing integrations...", total=100)
189
-
205
+
190
206
  # Initialize MCP Cost Explorer integration
191
207
  progress.update(task, advance=25, description="Initializing MCP integration...")
192
208
  if INTEGRATIONS_AVAILABLE:
@@ -196,126 +212,125 @@ class ComprehensiveCostExplorerIntegration:
196
212
  management_profile=self.management_profile,
197
213
  single_account_profile=self.single_account_profile,
198
214
  tolerance_percent=self.validation_tolerance,
199
- performance_target_seconds=self.performance_target
215
+ performance_target_seconds=self.performance_target,
200
216
  )
201
-
217
+
202
218
  # Initialize profiles
203
219
  mcp_results = await self.mcp_integration.initialize_profiles(user_profile_override)
204
- initialization_results['integrations']['mcp'] = {
205
- 'status': 'initialized',
206
- 'profiles_successful': len(mcp_results.get('profiles_successful', [])),
207
- 'validation_capability': 'available'
220
+ initialization_results["integrations"]["mcp"] = {
221
+ "status": "initialized",
222
+ "profiles_successful": len(mcp_results.get("profiles_successful", [])),
223
+ "validation_capability": "available",
208
224
  }
209
-
225
+
210
226
  except Exception as e:
211
- initialization_results['integrations']['mcp'] = {
212
- 'status': 'error',
213
- 'error': str(e),
214
- 'validation_capability': 'limited'
227
+ initialization_results["integrations"]["mcp"] = {
228
+ "status": "error",
229
+ "error": str(e),
230
+ "validation_capability": "limited",
215
231
  }
216
232
  else:
217
- initialization_results['integrations']['mcp'] = {
218
- 'status': 'not_available',
219
- 'reason': 'Integration modules not installed'
233
+ initialization_results["integrations"]["mcp"] = {
234
+ "status": "not_available",
235
+ "reason": "Integration modules not installed",
220
236
  }
221
-
237
+
222
238
  # Initialize pricing engine
223
239
  progress.update(task, advance=25, description="Initializing pricing engine...")
224
240
  if INTEGRATIONS_AVAILABLE:
225
241
  try:
226
- self.pricing_engine = get_aws_pricing_engine(
227
- cache_ttl_hours=24,
228
- enable_fallback=True
229
- )
230
- initialization_results['integrations']['pricing'] = {
231
- 'status': 'initialized',
232
- 'cache_ttl_hours': 24,
233
- 'fallback_enabled': True
242
+ self.pricing_engine = get_aws_pricing_engine(cache_ttl_hours=24, enable_fallback=True)
243
+ initialization_results["integrations"]["pricing"] = {
244
+ "status": "initialized",
245
+ "cache_ttl_hours": 24,
246
+ "fallback_enabled": True,
234
247
  }
235
248
  except Exception as e:
236
- initialization_results['integrations']['pricing'] = {
237
- 'status': 'error',
238
- 'error': str(e)
239
- }
240
-
249
+ initialization_results["integrations"]["pricing"] = {"status": "error", "error": str(e)}
250
+
241
251
  # Initialize terraform drift detector
242
252
  progress.update(task, advance=25, description="Initializing terraform detector...")
243
253
  if TERRAFORM_INTEGRATION_AVAILABLE:
244
254
  try:
245
- self.terraform_detector = TerraformDriftDetector(
246
- terraform_state_dir=self.terraform_state_dir
247
- )
248
- initialization_results['integrations']['terraform'] = {
249
- 'status': 'initialized',
250
- 'state_dir': self.terraform_state_dir,
251
- 'drift_detection': 'available'
255
+ self.terraform_detector = TerraformDriftDetector(terraform_state_dir=self.terraform_state_dir)
256
+ initialization_results["integrations"]["terraform"] = {
257
+ "status": "initialized",
258
+ "state_dir": self.terraform_state_dir,
259
+ "drift_detection": "available",
252
260
  }
253
261
  except Exception as e:
254
- initialization_results['integrations']['terraform'] = {
255
- 'status': 'error',
256
- 'error': str(e),
257
- 'drift_detection': 'unavailable'
262
+ initialization_results["integrations"]["terraform"] = {
263
+ "status": "error",
264
+ "error": str(e),
265
+ "drift_detection": "unavailable",
258
266
  }
259
267
  else:
260
- initialization_results['integrations']['terraform'] = {
261
- 'status': 'not_available',
262
- 'reason': 'Terraform integration module not installed'
268
+ initialization_results["integrations"]["terraform"] = {
269
+ "status": "not_available",
270
+ "reason": "Terraform integration module not installed",
263
271
  }
264
-
272
+
265
273
  progress.update(task, advance=25, description="Finalizing initialization...")
266
-
274
+
267
275
  # Determine overall status
268
- successful_integrations = sum(1 for integration in initialization_results['integrations'].values()
269
- if integration.get('status') == 'initialized')
270
- total_integrations = len(initialization_results['integrations'])
271
-
276
+ successful_integrations = sum(
277
+ 1
278
+ for integration in initialization_results["integrations"].values()
279
+ if integration.get("status") == "initialized"
280
+ )
281
+ total_integrations = len(initialization_results["integrations"])
282
+
272
283
  if successful_integrations == total_integrations:
273
- initialization_results['overall_status'] = 'fully_operational'
284
+ initialization_results["overall_status"] = "fully_operational"
274
285
  elif successful_integrations > 0:
275
- initialization_results['overall_status'] = 'partially_operational'
286
+ initialization_results["overall_status"] = "partially_operational"
276
287
  else:
277
- initialization_results['overall_status'] = 'initialization_failed'
278
-
288
+ initialization_results["overall_status"] = "initialization_failed"
289
+
279
290
  progress.update(task, completed=100)
280
-
291
+
281
292
  # Display initialization results
282
293
  self._display_initialization_results(initialization_results)
283
-
294
+
284
295
  return initialization_results
285
-
286
- async def perform_comprehensive_cost_analysis(self,
287
- account_filter: Optional[str] = None,
288
- analysis_days: int = 90,
289
- include_terraform_alignment: bool = True,
290
- runbooks_evidence_file: Optional[str] = None) -> ComprehensiveCostAnalysis:
296
+
297
+ async def perform_comprehensive_cost_analysis(
298
+ self,
299
+ account_filter: Optional[str] = None,
300
+ analysis_days: int = 90,
301
+ include_terraform_alignment: bool = True,
302
+ runbooks_evidence_file: Optional[str] = None,
303
+ ) -> ComprehensiveCostAnalysis:
291
304
  """
292
305
  Perform comprehensive cost analysis with all integrations.
293
-
306
+
294
307
  Args:
295
308
  account_filter: Specific account ID for analysis
296
309
  analysis_days: Number of days for cost analysis
297
310
  include_terraform_alignment: Include terraform drift detection
298
311
  runbooks_evidence_file: Path to runbooks evidence for terraform alignment
299
-
312
+
300
313
  Returns:
301
314
  Complete comprehensive cost analysis
302
315
  """
303
316
  analysis_start = datetime.now()
304
317
  analysis_id = f"comprehensive_cost_{analysis_start.strftime('%Y%m%d_%H%M%S')}"
305
-
318
+
306
319
  print_header("Comprehensive Cost Analysis")
307
320
  print_info(f"🎯 Analysis ID: {analysis_id}")
308
321
  print_info(f"📊 Account Filter: {account_filter or 'All accounts'}")
309
322
  print_info(f"📅 Analysis Period: {analysis_days} days")
310
-
323
+
311
324
  # Phase 1: Cost Explorer API integration
312
325
  print_info("💰 Phase 1: Cost Explorer API integration...")
313
326
  cost_explorer_results = await self._perform_cost_explorer_analysis(account_filter, analysis_days)
314
-
327
+
315
328
  # Phase 2: MCP validation
316
329
  print_info("🔍 Phase 2: MCP cross-validation...")
317
- mcp_validation_results = await self._perform_mcp_validation(cost_explorer_results, account_filter, analysis_days)
318
-
330
+ mcp_validation_results = await self._perform_mcp_validation(
331
+ cost_explorer_results, account_filter, analysis_days
332
+ )
333
+
319
334
  # Phase 3: Terraform alignment (if enabled)
320
335
  terraform_alignment = []
321
336
  infrastructure_drift = {}
@@ -326,13 +341,13 @@ class ComprehensiveCostExplorerIntegration:
326
341
  )
327
342
  else:
328
343
  print_info("⏭️ Phase 3: Skipped - terraform alignment not requested")
329
-
344
+
330
345
  # Phase 4: Business impact analysis
331
346
  print_info("💼 Phase 4: Business impact analysis...")
332
347
  optimization_opportunities, savings_potential, roi_projection = await self._analyze_business_impact(
333
348
  cost_explorer_results, terraform_alignment
334
349
  )
335
-
350
+
336
351
  # Phase 5: Generate comprehensive analysis
337
352
  print_info("📋 Phase 5: Generating comprehensive analysis...")
338
353
  comprehensive_analysis = ComprehensiveCostAnalysis(
@@ -341,381 +356,401 @@ class ComprehensiveCostExplorerIntegration:
341
356
  cost_explorer_results=cost_explorer_results,
342
357
  total_monthly_cost=sum(result.monthly_cost for result in cost_explorer_results),
343
358
  total_annual_projection=sum(result.annual_projection for result in cost_explorer_results),
344
- mcp_validation_accuracy=mcp_validation_results.get('overall_accuracy', 0.0),
359
+ mcp_validation_accuracy=mcp_validation_results.get("overall_accuracy", 0.0),
345
360
  mcp_cross_validation_results=mcp_validation_results,
346
361
  terraform_cost_alignment=terraform_alignment,
347
362
  infrastructure_drift_summary=infrastructure_drift,
348
363
  optimization_opportunities=optimization_opportunities,
349
364
  annual_savings_potential=savings_potential,
350
365
  roi_projection=roi_projection,
351
- compliance_status='compliant' if mcp_validation_results.get('overall_accuracy', 0) >= 99.5 else 'needs_review',
366
+ compliance_status="compliant"
367
+ if mcp_validation_results.get("overall_accuracy", 0) >= 99.5
368
+ else "needs_review",
352
369
  audit_trail={
353
- 'analysis_methodology': 'comprehensive_cost_explorer_with_mcp_terraform_validation',
354
- 'accuracy_standards': '≥99.5% MCP validation required',
355
- 'infrastructure_alignment': 'terraform_drift_detection_integrated',
356
- 'evidence_generation': 'complete_audit_trail'
370
+ "analysis_methodology": "comprehensive_cost_explorer_with_mcp_terraform_validation",
371
+ "accuracy_standards": "≥99.5% MCP validation required",
372
+ "infrastructure_alignment": "terraform_drift_detection_integrated",
373
+ "evidence_generation": "complete_audit_trail",
357
374
  },
358
- evidence_files=[]
375
+ evidence_files=[],
359
376
  )
360
-
377
+
361
378
  # Generate evidence files
362
379
  evidence_files = await self._generate_comprehensive_evidence(comprehensive_analysis)
363
380
  comprehensive_analysis.evidence_files = evidence_files
364
-
381
+
365
382
  # Display results
366
383
  self._display_comprehensive_results(comprehensive_analysis)
367
-
384
+
368
385
  return comprehensive_analysis
369
-
370
- async def _perform_cost_explorer_analysis(self, account_filter: Optional[str], analysis_days: int) -> List[CostExplorerResult]:
386
+
387
+ async def _perform_cost_explorer_analysis(
388
+ self, account_filter: Optional[str], analysis_days: int
389
+ ) -> List[CostExplorerResult]:
371
390
  """Perform Cost Explorer API analysis."""
372
-
391
+
373
392
  cost_explorer_results = []
374
-
393
+
375
394
  if not self.mcp_integration:
376
395
  print_warning("⚠️ MCP integration not available - using fallback pricing")
377
-
396
+
378
397
  # Fallback to pricing engine if available
379
398
  if self.pricing_engine:
380
- services = ['nat_gateway', 'elastic_ip', 'vpc_endpoint', 'ebs_gp3', 's3_standard']
399
+ services = ["nat_gateway", "elastic_ip", "vpc_endpoint", "ebs_gp3", "s3_standard"]
381
400
  for service in services:
382
- pricing_result = self.pricing_engine.get_service_pricing(service, 'us-east-1')
383
-
384
- cost_explorer_results.append(CostExplorerResult(
385
- service_name=service,
386
- account_id=account_filter or 'fallback',
387
- region='us-east-1',
388
- monthly_cost=Decimal(str(pricing_result.monthly_cost)),
389
- annual_projection=Decimal(str(pricing_result.monthly_cost * 12)),
390
- cost_trend='stable',
391
- optimization_potential=Decimal(str(pricing_result.monthly_cost * 0.3)),
392
- last_updated=pricing_result.last_updated,
393
- data_source=pricing_result.pricing_source,
394
- validation_accuracy=90.0, # Fallback accuracy
395
- confidence_level=75.0
396
- ))
397
-
401
+ pricing_result = self.pricing_engine.get_service_pricing(service, "us-east-1")
402
+
403
+ cost_explorer_results.append(
404
+ CostExplorerResult(
405
+ service_name=service,
406
+ account_id=account_filter or "fallback",
407
+ region="us-east-1",
408
+ monthly_cost=Decimal(str(pricing_result.monthly_cost)),
409
+ annual_projection=Decimal(str(pricing_result.monthly_cost * 12)),
410
+ cost_trend="stable",
411
+ optimization_potential=Decimal(str(pricing_result.monthly_cost * 0.3)),
412
+ last_updated=pricing_result.last_updated,
413
+ data_source=pricing_result.pricing_source,
414
+ validation_accuracy=90.0, # Fallback accuracy
415
+ confidence_level=75.0,
416
+ )
417
+ )
418
+
398
419
  return cost_explorer_results
399
-
420
+
400
421
  try:
401
422
  # Use MCP integration for Cost Explorer data
402
423
  cost_data = await self.mcp_integration._retrieve_cost_explorer_data(account_filter, analysis_days)
403
-
424
+
404
425
  # Process cost data into CostExplorerResult format
405
- if cost_data.get('service_breakdown'):
406
- for service_name, service_cost in cost_data['service_breakdown'].items():
426
+ if cost_data.get("service_breakdown"):
427
+ for service_name, service_cost in cost_data["service_breakdown"].items():
407
428
  annual_cost = Decimal(str(service_cost)) * 12
408
-
409
- cost_explorer_results.append(CostExplorerResult(
410
- service_name=service_name,
411
- account_id=account_filter or 'organization',
412
- region='us-east-1', # Cost Explorer aggregated
413
- monthly_cost=Decimal(str(service_cost)),
414
- annual_projection=annual_cost,
415
- cost_trend=self._determine_cost_trend(service_cost),
416
- optimization_potential=Decimal(str(service_cost * 0.25)), # 25% optimization potential
417
- last_updated=datetime.now(),
418
- data_source='cost_explorer_api',
419
- validation_accuracy=95.0, # High accuracy from API
420
- confidence_level=90.0
421
- ))
422
-
423
- elif cost_data.get('account_breakdown'):
424
- for account_id, account_cost in cost_data['account_breakdown'].items():
429
+
430
+ cost_explorer_results.append(
431
+ CostExplorerResult(
432
+ service_name=service_name,
433
+ account_id=account_filter or "organization",
434
+ region="us-east-1", # Cost Explorer aggregated
435
+ monthly_cost=Decimal(str(service_cost)),
436
+ annual_projection=annual_cost,
437
+ cost_trend=self._determine_cost_trend(service_cost),
438
+ optimization_potential=Decimal(str(service_cost * 0.25)), # 25% optimization potential
439
+ last_updated=datetime.now(),
440
+ data_source="cost_explorer_api",
441
+ validation_accuracy=95.0, # High accuracy from API
442
+ confidence_level=90.0,
443
+ )
444
+ )
445
+
446
+ elif cost_data.get("account_breakdown"):
447
+ for account_id, account_cost in cost_data["account_breakdown"].items():
425
448
  annual_cost = Decimal(str(account_cost)) * 12
426
-
427
- cost_explorer_results.append(CostExplorerResult(
428
- service_name='account_total',
429
- account_id=account_id,
430
- region='all_regions',
431
- monthly_cost=Decimal(str(account_cost)),
432
- annual_projection=annual_cost,
433
- cost_trend=self._determine_cost_trend(account_cost),
434
- optimization_potential=Decimal(str(account_cost * 0.20)), # 20% optimization potential
435
- last_updated=datetime.now(),
436
- data_source='cost_explorer_api',
437
- validation_accuracy=95.0,
438
- confidence_level=90.0
439
- ))
440
-
449
+
450
+ cost_explorer_results.append(
451
+ CostExplorerResult(
452
+ service_name="account_total",
453
+ account_id=account_id,
454
+ region="all_regions",
455
+ monthly_cost=Decimal(str(account_cost)),
456
+ annual_projection=annual_cost,
457
+ cost_trend=self._determine_cost_trend(account_cost),
458
+ optimization_potential=Decimal(str(account_cost * 0.20)), # 20% optimization potential
459
+ last_updated=datetime.now(),
460
+ data_source="cost_explorer_api",
461
+ validation_accuracy=95.0,
462
+ confidence_level=90.0,
463
+ )
464
+ )
465
+
441
466
  except Exception as e:
442
467
  print_error(f"Cost Explorer analysis error: {e}")
443
468
  logger.error(f"Cost Explorer analysis failed: {e}")
444
-
469
+
445
470
  return cost_explorer_results
446
-
447
- async def _perform_mcp_validation(self, cost_explorer_results: List[CostExplorerResult],
448
- account_filter: Optional[str], analysis_days: int) -> Dict[str, Any]:
471
+
472
+ async def _perform_mcp_validation(
473
+ self, cost_explorer_results: List[CostExplorerResult], account_filter: Optional[str], analysis_days: int
474
+ ) -> Dict[str, Any]:
449
475
  """Perform MCP cross-validation."""
450
-
476
+
451
477
  mcp_validation_results = {
452
- 'validation_timestamp': datetime.now().isoformat(),
453
- 'validation_method': 'comprehensive_mcp_cost_explorer',
454
- 'overall_accuracy': 0.0,
455
- 'validations': [],
456
- 'enterprise_compliance': False
478
+ "validation_timestamp": datetime.now().isoformat(),
479
+ "validation_method": "comprehensive_mcp_cost_explorer",
480
+ "overall_accuracy": 0.0,
481
+ "validations": [],
482
+ "enterprise_compliance": False,
457
483
  }
458
-
484
+
459
485
  if not self.mcp_integration:
460
- mcp_validation_results.update({
461
- 'status': 'mcp_integration_unavailable',
462
- 'overall_accuracy': 85.0, # Fallback accuracy
463
- 'enterprise_compliance': False,
464
- 'note': 'MCP validation requires full integration availability'
465
- })
486
+ mcp_validation_results.update(
487
+ {
488
+ "status": "mcp_integration_unavailable",
489
+ "overall_accuracy": 85.0, # Fallback accuracy
490
+ "enterprise_compliance": False,
491
+ "note": "MCP validation requires full integration availability",
492
+ }
493
+ )
466
494
  return mcp_validation_results
467
-
495
+
468
496
  try:
469
497
  # Prepare notebook-style results for cross-validation
470
498
  notebook_results = {
471
- 'cost_trends': {
472
- 'total_monthly_spend': float(sum(result.monthly_cost for result in cost_explorer_results)),
473
- 'analysis_period_days': analysis_days
499
+ "cost_trends": {
500
+ "total_monthly_spend": float(sum(result.monthly_cost for result in cost_explorer_results)),
501
+ "analysis_period_days": analysis_days,
474
502
  },
475
- 'service_breakdown': {
476
- result.service_name: float(result.monthly_cost)
477
- for result in cost_explorer_results
503
+ "service_breakdown": {
504
+ result.service_name: float(result.monthly_cost) for result in cost_explorer_results
478
505
  },
479
- 'optimization_potential': float(sum(result.optimization_potential for result in cost_explorer_results))
506
+ "optimization_potential": float(sum(result.optimization_potential for result in cost_explorer_results)),
480
507
  }
481
-
508
+
482
509
  # Perform MCP validation
483
510
  validation_results = await self.mcp_integration.validate_cost_data_with_cross_validation(
484
- notebook_results=notebook_results,
485
- account_filter=account_filter,
486
- analysis_days=analysis_days
511
+ notebook_results=notebook_results, account_filter=account_filter, analysis_days=analysis_days
487
512
  )
488
-
513
+
489
514
  # Extract validation accuracy
490
- cross_validation = validation_results.get('cross_validation', {})
491
- validations = cross_validation.get('validations', [])
492
-
515
+ cross_validation = validation_results.get("cross_validation", {})
516
+ validations = cross_validation.get("validations", [])
517
+
493
518
  if validations:
494
519
  # Calculate overall accuracy from validations
495
- validated_count = sum(1 for v in validations if v.get('status') == 'validated')
520
+ validated_count = sum(1 for v in validations if v.get("status") == "validated")
496
521
  total_count = len(validations)
497
-
522
+
498
523
  overall_accuracy = (validated_count / total_count * 100) if total_count > 0 else 0
499
-
500
- mcp_validation_results.update({
501
- 'overall_accuracy': overall_accuracy,
502
- 'validations': validations,
503
- 'enterprise_compliance': overall_accuracy >= 99.5,
504
- 'manager_priorities_assessment': validation_results.get('manager_priorities_assessment', {}),
505
- 'performance_metrics': validation_results.get('performance_metrics', {})
506
- })
524
+
525
+ mcp_validation_results.update(
526
+ {
527
+ "overall_accuracy": overall_accuracy,
528
+ "validations": validations,
529
+ "enterprise_compliance": overall_accuracy >= 99.5,
530
+ "manager_priorities_assessment": validation_results.get("manager_priorities_assessment", {}),
531
+ "performance_metrics": validation_results.get("performance_metrics", {}),
532
+ }
533
+ )
507
534
  else:
508
- mcp_validation_results.update({
509
- 'overall_accuracy': 75.0, # Default when validation fails
510
- 'enterprise_compliance': False,
511
- 'status': 'validation_incomplete'
512
- })
513
-
535
+ mcp_validation_results.update(
536
+ {
537
+ "overall_accuracy": 75.0, # Default when validation fails
538
+ "enterprise_compliance": False,
539
+ "status": "validation_incomplete",
540
+ }
541
+ )
542
+
514
543
  except Exception as e:
515
544
  print_error(f"MCP validation error: {e}")
516
- mcp_validation_results.update({
517
- 'status': 'validation_error',
518
- 'error': str(e),
519
- 'overall_accuracy': 70.0, # Conservative accuracy on error
520
- 'enterprise_compliance': False
521
- })
522
-
545
+ mcp_validation_results.update(
546
+ {
547
+ "status": "validation_error",
548
+ "error": str(e),
549
+ "overall_accuracy": 70.0, # Conservative accuracy on error
550
+ "enterprise_compliance": False,
551
+ }
552
+ )
553
+
523
554
  return mcp_validation_results
524
-
525
- async def _perform_terraform_alignment(self, cost_explorer_results: List[CostExplorerResult],
526
- runbooks_evidence_file: str) -> Tuple[List[TerraformCostAlignment], Dict[str, Any]]:
555
+
556
+ async def _perform_terraform_alignment(
557
+ self, cost_explorer_results: List[CostExplorerResult], runbooks_evidence_file: str
558
+ ) -> Tuple[List[TerraformCostAlignment], Dict[str, Any]]:
527
559
  """Perform terraform infrastructure cost alignment."""
528
-
560
+
529
561
  terraform_alignments = []
530
562
  infrastructure_drift = {}
531
-
563
+
532
564
  if not self.terraform_detector:
533
565
  print_warning("⚠️ Terraform integration not available")
534
- return terraform_alignments, {'status': 'terraform_integration_unavailable'}
535
-
566
+ return terraform_alignments, {"status": "terraform_integration_unavailable"}
567
+
536
568
  try:
537
569
  # Perform terraform drift detection
538
570
  drift_result = self.terraform_detector.detect_infrastructure_drift(
539
571
  runbooks_evidence_file=runbooks_evidence_file,
540
- resource_types=['aws_vpc', 'aws_subnet', 'aws_nat_gateway', 'aws_eip']
572
+ resource_types=["aws_vpc", "aws_subnet", "aws_nat_gateway", "aws_eip"],
541
573
  )
542
-
574
+
543
575
  # Process drift results for cost alignment
544
576
  for drift_analysis in drift_result.drift_analysis:
545
577
  # Try to correlate with cost data
546
578
  related_cost = self._correlate_cost_with_resource(
547
- drift_analysis.resource_type,
548
- drift_analysis.resource_id,
549
- cost_explorer_results
579
+ drift_analysis.resource_type, drift_analysis.resource_id, cost_explorer_results
550
580
  )
551
-
581
+
552
582
  terraform_alignment = TerraformCostAlignment(
553
583
  terraform_resource_id=drift_analysis.resource_id,
554
584
  terraform_resource_type=drift_analysis.resource_type,
555
585
  cost_explorer_attribution=related_cost,
556
586
  alignment_status=drift_analysis.drift_type,
557
587
  drift_details=drift_analysis.drift_details,
558
- remediation_recommendation=drift_analysis.remediation_recommendation
588
+ remediation_recommendation=drift_analysis.remediation_recommendation,
559
589
  )
560
-
590
+
561
591
  terraform_alignments.append(terraform_alignment)
562
-
592
+
563
593
  # Summarize infrastructure drift
564
594
  infrastructure_drift = {
565
- 'drift_detection_id': drift_result.drift_detection_id,
566
- 'total_resources_terraform': drift_result.total_resources_terraform,
567
- 'total_resources_runbooks': drift_result.total_resources_runbooks,
568
- 'drift_percentage': drift_result.drift_percentage,
569
- 'overall_risk_level': drift_result.overall_risk_level,
570
- 'compliance_impact': drift_result.compliance_impact,
571
- 'remediation_priority': drift_result.remediation_priority
595
+ "drift_detection_id": drift_result.drift_detection_id,
596
+ "total_resources_terraform": drift_result.total_resources_terraform,
597
+ "total_resources_runbooks": drift_result.total_resources_runbooks,
598
+ "drift_percentage": drift_result.drift_percentage,
599
+ "overall_risk_level": drift_result.overall_risk_level,
600
+ "compliance_impact": drift_result.compliance_impact,
601
+ "remediation_priority": drift_result.remediation_priority,
572
602
  }
573
-
603
+
574
604
  except Exception as e:
575
605
  print_error(f"Terraform alignment error: {e}")
576
- infrastructure_drift = {
577
- 'status': 'alignment_error',
578
- 'error': str(e)
579
- }
580
-
606
+ infrastructure_drift = {"status": "alignment_error", "error": str(e)}
607
+
581
608
  return terraform_alignments, infrastructure_drift
582
-
583
- async def _analyze_business_impact(self, cost_explorer_results: List[CostExplorerResult],
584
- terraform_alignments: List[TerraformCostAlignment]) -> Tuple[List[Dict[str, Any]], Decimal, float]:
609
+
610
+ async def _analyze_business_impact(
611
+ self, cost_explorer_results: List[CostExplorerResult], terraform_alignments: List[TerraformCostAlignment]
612
+ ) -> Tuple[List[Dict[str, Any]], Decimal, float]:
585
613
  """Analyze business impact and optimization opportunities."""
586
-
614
+
587
615
  optimization_opportunities = []
588
- total_savings_potential = Decimal('0')
589
-
616
+ total_savings_potential = Decimal("0")
617
+
590
618
  # Analyze cost optimization opportunities
591
619
  for result in cost_explorer_results:
592
620
  if result.optimization_potential > 0:
593
- optimization_opportunities.append({
594
- 'type': 'cost_optimization',
595
- 'service': result.service_name,
596
- 'account': result.account_id,
597
- 'current_monthly_cost': float(result.monthly_cost),
598
- 'potential_monthly_savings': float(result.optimization_potential),
599
- 'annual_savings_potential': float(result.optimization_potential * 12),
600
- 'confidence_level': result.confidence_level,
601
- 'recommendation': f"Optimize {result.service_name} configuration to reduce costs",
602
- 'implementation_effort': 'medium',
603
- 'risk_level': 'low'
604
- })
605
-
621
+ optimization_opportunities.append(
622
+ {
623
+ "type": "cost_optimization",
624
+ "service": result.service_name,
625
+ "account": result.account_id,
626
+ "current_monthly_cost": float(result.monthly_cost),
627
+ "potential_monthly_savings": float(result.optimization_potential),
628
+ "annual_savings_potential": float(result.optimization_potential * 12),
629
+ "confidence_level": result.confidence_level,
630
+ "recommendation": f"Optimize {result.service_name} configuration to reduce costs",
631
+ "implementation_effort": "medium",
632
+ "risk_level": "low",
633
+ }
634
+ )
635
+
606
636
  total_savings_potential += result.optimization_potential * 12
607
-
637
+
608
638
  # Analyze terraform alignment opportunities
609
639
  for alignment in terraform_alignments:
610
- if alignment.alignment_status in ['missing_from_terraform', 'configuration_drift']:
611
- optimization_opportunities.append({
612
- 'type': 'infrastructure_governance',
613
- 'resource_type': alignment.terraform_resource_type,
614
- 'resource_id': alignment.terraform_resource_id,
615
- 'alignment_status': alignment.alignment_status,
616
- 'cost_attribution': float(alignment.cost_explorer_attribution),
617
- 'recommendation': alignment.remediation_recommendation,
618
- 'implementation_effort': 'high' if alignment.alignment_status == 'missing_from_terraform' else 'medium',
619
- 'risk_level': 'medium',
620
- 'governance_impact': 'high'
621
- })
622
-
640
+ if alignment.alignment_status in ["missing_from_terraform", "configuration_drift"]:
641
+ optimization_opportunities.append(
642
+ {
643
+ "type": "infrastructure_governance",
644
+ "resource_type": alignment.terraform_resource_type,
645
+ "resource_id": alignment.terraform_resource_id,
646
+ "alignment_status": alignment.alignment_status,
647
+ "cost_attribution": float(alignment.cost_explorer_attribution),
648
+ "recommendation": alignment.remediation_recommendation,
649
+ "implementation_effort": "high"
650
+ if alignment.alignment_status == "missing_from_terraform"
651
+ else "medium",
652
+ "risk_level": "medium",
653
+ "governance_impact": "high",
654
+ }
655
+ )
656
+
623
657
  # Calculate ROI projection
624
658
  total_current_cost = sum(result.annual_projection for result in cost_explorer_results)
625
659
  roi_projection = float((total_savings_potential / total_current_cost) * 100) if total_current_cost > 0 else 0.0
626
-
660
+
627
661
  return optimization_opportunities, total_savings_potential, roi_projection
628
-
629
- def _correlate_cost_with_resource(self, resource_type: str, resource_id: str,
630
- cost_results: List[CostExplorerResult]) -> Decimal:
662
+
663
+ def _correlate_cost_with_resource(
664
+ self, resource_type: str, resource_id: str, cost_results: List[CostExplorerResult]
665
+ ) -> Decimal:
631
666
  """Correlate terraform resource with cost data."""
632
-
667
+
633
668
  # Simple correlation based on resource type
634
669
  service_mapping = {
635
- 'aws_vpc': 'Amazon Virtual Private Cloud',
636
- 'aws_nat_gateway': 'Amazon VPC',
637
- 'aws_subnet': 'Amazon Virtual Private Cloud',
638
- 'aws_eip': 'Amazon Elastic Compute Cloud - Compute'
670
+ "aws_vpc": "Amazon Virtual Private Cloud",
671
+ "aws_nat_gateway": "Amazon VPC",
672
+ "aws_subnet": "Amazon Virtual Private Cloud",
673
+ "aws_eip": "Amazon Elastic Compute Cloud - Compute",
639
674
  }
640
-
641
- service_name = service_mapping.get(resource_type, '')
642
-
675
+
676
+ service_name = service_mapping.get(resource_type, "")
677
+
643
678
  for result in cost_results:
644
679
  if service_name in result.service_name or result.service_name in service_name:
645
680
  # Rough attribution - could be enhanced with detailed resource tagging
646
- return result.monthly_cost * Decimal('0.1') # 10% attribution estimate
647
-
648
- return Decimal('0')
649
-
681
+ return result.monthly_cost * Decimal("0.1") # 10% attribution estimate
682
+
683
+ return Decimal("0")
684
+
650
685
  def _determine_cost_trend(self, current_cost: float) -> str:
651
686
  """Determine cost trend (simplified)."""
652
687
  # In real implementation, this would compare historical data
653
688
  if current_cost > 1000:
654
- return 'increasing'
689
+ return "increasing"
655
690
  elif current_cost < 100:
656
- return 'decreasing'
691
+ return "decreasing"
657
692
  else:
658
- return 'stable'
659
-
693
+ return "stable"
694
+
660
695
  async def _generate_comprehensive_evidence(self, analysis: ComprehensiveCostAnalysis) -> List[str]:
661
696
  """Generate comprehensive evidence files."""
662
-
697
+
663
698
  evidence_files = []
664
699
  timestamp = analysis.analysis_timestamp.strftime("%Y%m%d_%H%M%S")
665
-
700
+
666
701
  # Main analysis evidence
667
702
  main_evidence_file = self.evidence_dir / f"comprehensive_cost_analysis_{timestamp}.json"
668
-
703
+
669
704
  evidence_data = {
670
- 'comprehensive_cost_analysis': asdict(analysis),
671
- 'enterprise_metadata': {
672
- 'framework_version': '1.0.0',
673
- 'strategic_coordination': 'python-runbooks-engineer → qa-testing-specialist → cloud-architect',
674
- 'compliance_standards': ['DoD', 'Enterprise', 'FAANG SDLC'],
675
- 'validation_methodology': 'aws_cost_explorer_api + mcp_cross_validation + terraform_alignment'
705
+ "comprehensive_cost_analysis": asdict(analysis),
706
+ "enterprise_metadata": {
707
+ "framework_version": "1.0.0",
708
+ "strategic_coordination": "python-runbooks-engineer → qa-testing-specialist → cloud-architect",
709
+ "compliance_standards": ["DoD", "Enterprise", "FAANG SDLC"],
710
+ "validation_methodology": "aws_cost_explorer_api + mcp_cross_validation + terraform_alignment",
676
711
  },
677
- 'business_intelligence': {
678
- 'total_annual_cost_projection': float(analysis.total_annual_projection),
679
- 'annual_savings_potential': float(analysis.annual_savings_potential),
680
- 'roi_projection_percent': analysis.roi_projection,
681
- 'mcp_validation_accuracy': analysis.mcp_validation_accuracy,
682
- 'enterprise_compliance_status': analysis.compliance_status
712
+ "business_intelligence": {
713
+ "total_annual_cost_projection": float(analysis.total_annual_projection),
714
+ "annual_savings_potential": float(analysis.annual_savings_potential),
715
+ "roi_projection_percent": analysis.roi_projection,
716
+ "mcp_validation_accuracy": analysis.mcp_validation_accuracy,
717
+ "enterprise_compliance_status": analysis.compliance_status,
718
+ },
719
+ "executive_summary": self._generate_executive_summary(analysis),
720
+ "audit_compliance": {
721
+ "data_source": "real_aws_cost_explorer_api",
722
+ "validation_methodology": "mcp_cross_validation",
723
+ "infrastructure_alignment": "terraform_drift_detection",
724
+ "evidence_integrity": "cryptographic_hash_validation",
725
+ "audit_trail": "comprehensive",
683
726
  },
684
- 'executive_summary': self._generate_executive_summary(analysis),
685
- 'audit_compliance': {
686
- 'data_source': 'real_aws_cost_explorer_api',
687
- 'validation_methodology': 'mcp_cross_validation',
688
- 'infrastructure_alignment': 'terraform_drift_detection',
689
- 'evidence_integrity': 'cryptographic_hash_validation',
690
- 'audit_trail': 'comprehensive'
691
- }
692
727
  }
693
-
694
- with open(main_evidence_file, 'w') as f:
728
+
729
+ with open(main_evidence_file, "w") as f:
695
730
  json.dump(evidence_data, f, indent=2, default=str)
696
-
731
+
697
732
  evidence_files.append(str(main_evidence_file))
698
-
733
+
699
734
  # Executive summary file
700
735
  exec_summary_file = self.evidence_dir / f"executive_summary_{timestamp}.md"
701
736
  exec_summary = self._generate_executive_summary(analysis)
702
-
703
- with open(exec_summary_file, 'w') as f:
737
+
738
+ with open(exec_summary_file, "w") as f:
704
739
  f.write(exec_summary)
705
-
740
+
706
741
  evidence_files.append(str(exec_summary_file))
707
-
742
+
708
743
  print_success(f"📄 Evidence files generated: {len(evidence_files)} files")
709
-
744
+
710
745
  return evidence_files
711
-
746
+
712
747
  def _generate_executive_summary(self, analysis: ComprehensiveCostAnalysis) -> str:
713
748
  """Generate executive summary."""
714
-
749
+
715
750
  return f"""# Comprehensive Cost Analysis Executive Summary
716
751
 
717
752
  **Analysis ID**: {analysis.analysis_id}
718
- **Date**: {analysis.analysis_timestamp.strftime('%Y-%m-%d %H:%M:%S')}
753
+ **Date**: {analysis.analysis_timestamp.strftime("%Y-%m-%d %H:%M:%S")}
719
754
 
720
755
  ## Financial Overview
721
756
 
@@ -727,19 +762,19 @@ class ComprehensiveCostExplorerIntegration:
727
762
 
728
763
  - **MCP Validation Accuracy**: {analysis.mcp_validation_accuracy:.1f}%
729
764
  - **Enterprise Compliance**: {analysis.compliance_status.upper()}
730
- - **Infrastructure Alignment**: {'Validated' if analysis.terraform_cost_alignment else 'Not Assessed'}
765
+ - **Infrastructure Alignment**: {"Validated" if analysis.terraform_cost_alignment else "Not Assessed"}
731
766
 
732
767
  ## Key Findings
733
768
 
734
769
  - **Cost Explorer Results**: {len(analysis.cost_explorer_results)} services analyzed
735
770
  - **Optimization Opportunities**: {len(analysis.optimization_opportunities)} identified
736
- - **Infrastructure Drift**: {'Detected' if analysis.infrastructure_drift_summary.get('drift_percentage', 0) > 0 else 'None detected'}
771
+ - **Infrastructure Drift**: {"Detected" if analysis.infrastructure_drift_summary.get("drift_percentage", 0) > 0 else "None detected"}
737
772
 
738
773
  ## Recommendations
739
774
 
740
775
  1. **Cost Optimization**: Implement identified optimization opportunities for ${analysis.annual_savings_potential:,.2f} annual savings
741
- 2. **Infrastructure Governance**: {'Address infrastructure drift detected' if analysis.infrastructure_drift_summary.get('drift_percentage', 0) > 0 else 'Maintain current infrastructure alignment'}
742
- 3. **Validation Framework**: {'Continue MCP validation excellence' if analysis.mcp_validation_accuracy >= 99.5 else 'Enhance MCP validation accuracy'}
776
+ 2. **Infrastructure Governance**: {"Address infrastructure drift detected" if analysis.infrastructure_drift_summary.get("drift_percentage", 0) > 0 else "Maintain current infrastructure alignment"}
777
+ 3. **Validation Framework**: {"Continue MCP validation excellence" if analysis.mcp_validation_accuracy >= 99.5 else "Enhance MCP validation accuracy"}
743
778
 
744
779
  ## Strategic Alignment
745
780
 
@@ -749,109 +784,94 @@ class ComprehensiveCostExplorerIntegration:
749
784
 
750
785
  ---
751
786
 
752
- *Generated by Comprehensive Cost Explorer Integration v1.0.0*
787
+ *Generated by Comprehensive Cost Explorer Integration latest version*
753
788
  *Strategic Coordination: Enterprise Agile Team with systematic delegation*
754
789
  """
755
-
790
+
756
791
  def _display_initialization_results(self, results: Dict[str, Any]) -> None:
757
792
  """Display initialization results."""
758
-
793
+
759
794
  init_table = create_table(
760
795
  title="Integration Initialization Results",
761
796
  columns=[
762
797
  {"name": "Integration", "style": "bold cyan"},
763
798
  {"name": "Status", "style": "white"},
764
799
  {"name": "Capability", "style": "yellow"},
765
- {"name": "Notes", "style": "dim"}
766
- ]
800
+ {"name": "Notes", "style": "dim"},
801
+ ],
767
802
  )
768
-
769
- for integration_name, integration_data in results['integrations'].items():
770
- status = integration_data.get('status', 'unknown')
803
+
804
+ for integration_name, integration_data in results["integrations"].items():
805
+ status = integration_data.get("status", "unknown")
771
806
  status_display = {
772
- 'initialized': '✅ Operational',
773
- 'error': '❌ Error',
774
- 'not_available': '⚠️ Unavailable'
807
+ "initialized": "✅ Operational",
808
+ "error": "❌ Error",
809
+ "not_available": "⚠️ Unavailable",
775
810
  }.get(status, status)
776
-
777
- capability = 'Available' if status == 'initialized' else 'Limited'
778
- notes = integration_data.get('error', integration_data.get('reason', 'Ready'))[:50]
779
-
780
- init_table.add_row(
781
- integration_name.upper(),
782
- status_display,
783
- capability,
784
- notes
785
- )
786
-
811
+
812
+ capability = "Available" if status == "initialized" else "Limited"
813
+ notes = integration_data.get("error", integration_data.get("reason", "Ready"))[:50]
814
+
815
+ init_table.add_row(integration_name.upper(), status_display, capability, notes)
816
+
787
817
  console.print(init_table)
788
-
789
- overall_status = results['overall_status']
818
+
819
+ overall_status = results["overall_status"]
790
820
  status_panel = create_panel(
791
- f"""🏗️ Comprehensive Integration Status: {overall_status.upper().replace('_', ' ')}
821
+ f"""🏗️ Comprehensive Integration Status: {overall_status.upper().replace("_", " ")}
792
822
 
793
823
  Integration Readiness:
794
- • Real-time Cost Explorer API: {'✅ Ready' if 'mcp' in results['integrations'] and results['integrations']['mcp'].get('status') == 'initialized' else '⚠️ Limited'}
795
- • MCP Validation (≥99.5%): {'✅ Ready' if 'mcp' in results['integrations'] and results['integrations']['mcp'].get('status') == 'initialized' else '⚠️ Limited'}
796
- • Terraform Drift Detection: {'✅ Ready' if 'terraform' in results['integrations'] and results['integrations']['terraform'].get('status') == 'initialized' else '⚠️ Limited'}
797
- • Dynamic Pricing Engine: {'✅ Ready' if 'pricing' in results['integrations'] and results['integrations']['pricing'].get('status') == 'initialized' else '⚠️ Limited'}
824
+ • Real-time Cost Explorer API: {"✅ Ready" if "mcp" in results["integrations"] and results["integrations"]["mcp"].get("status") == "initialized" else "⚠️ Limited"}
825
+ • MCP Validation (≥99.5%): {"✅ Ready" if "mcp" in results["integrations"] and results["integrations"]["mcp"].get("status") == "initialized" else "⚠️ Limited"}
826
+ • Terraform Drift Detection: {"✅ Ready" if "terraform" in results["integrations"] and results["integrations"]["terraform"].get("status") == "initialized" else "⚠️ Limited"}
827
+ • Dynamic Pricing Engine: {"✅ Ready" if "pricing" in results["integrations"] and results["integrations"]["pricing"].get("status") == "initialized" else "⚠️ Limited"}
798
828
 
799
- Enterprise Compliance: {'✅ All systems operational' if overall_status == 'fully_operational' else '⚠️ Partial capability - some features may be limited'}""",
829
+ Enterprise Compliance: {"✅ All systems operational" if overall_status == "fully_operational" else "⚠️ Partial capability - some features may be limited"}""",
800
830
  title="Enterprise Integration Status",
801
- border_style="green" if overall_status == 'fully_operational' else "yellow"
831
+ border_style="green" if overall_status == "fully_operational" else "yellow",
802
832
  )
803
-
833
+
804
834
  console.print(status_panel)
805
-
835
+
806
836
  def _display_comprehensive_results(self, analysis: ComprehensiveCostAnalysis) -> None:
807
837
  """Display comprehensive analysis results."""
808
-
838
+
809
839
  print_header("Comprehensive Cost Analysis Results")
810
-
840
+
811
841
  # Financial summary
812
842
  financial_table = create_table(
813
843
  title="💰 Financial Analysis Summary",
814
844
  columns=[
815
845
  {"name": "Metric", "style": "bold cyan"},
816
846
  {"name": "Value", "style": "bright_green", "justify": "right"},
817
- {"name": "Assessment", "style": "yellow", "justify": "center"}
818
- ]
819
- )
820
-
821
- financial_table.add_row(
822
- "Current Annual Cost",
823
- f"${analysis.total_annual_projection:,.2f}",
824
- "📊"
825
- )
826
-
827
- financial_table.add_row(
828
- "Annual Savings Potential",
829
- f"${analysis.annual_savings_potential:,.2f}",
830
- "💰"
847
+ {"name": "Assessment", "style": "yellow", "justify": "center"},
848
+ ],
831
849
  )
832
-
850
+
851
+ financial_table.add_row("Current Annual Cost", f"${analysis.total_annual_projection:,.2f}", "📊")
852
+
853
+ financial_table.add_row("Annual Savings Potential", f"${analysis.annual_savings_potential:,.2f}", "💰")
854
+
833
855
  financial_table.add_row(
834
- "ROI Projection",
835
- f"{analysis.roi_projection:.1f}%",
836
- "📈" if analysis.roi_projection > 10 else "📊"
856
+ "ROI Projection", f"{analysis.roi_projection:.1f}%", "📈" if analysis.roi_projection > 10 else "📊"
837
857
  )
838
-
858
+
839
859
  financial_table.add_row(
840
860
  "MCP Validation Accuracy",
841
861
  f"{analysis.mcp_validation_accuracy:.1f}%",
842
- "✅" if analysis.mcp_validation_accuracy >= 99.5 else "⚠️"
862
+ "✅" if analysis.mcp_validation_accuracy >= 99.5 else "⚠️",
843
863
  )
844
-
864
+
845
865
  console.print(financial_table)
846
-
866
+
847
867
  # Compliance status panel
848
- compliance_color = "green" if analysis.compliance_status == 'compliant' else "yellow"
868
+ compliance_color = "green" if analysis.compliance_status == "compliant" else "yellow"
849
869
  compliance_text = f"""🏛️ Enterprise Compliance Assessment
850
870
 
851
871
  Compliance Status: {analysis.compliance_status.upper()}
852
- MCP Validation: {analysis.mcp_validation_accuracy:.1f}% ({'✅ EXCEEDS' if analysis.mcp_validation_accuracy >= 99.5 else '⚠️ BELOW'} 99.5% requirement)
853
- Infrastructure Alignment: {'✅ Terraform validated' if analysis.terraform_cost_alignment else '📊 Assessment available'}
854
- Audit Trail: {'✅ Complete' if analysis.evidence_files else '⚠️ Generating'}
872
+ MCP Validation: {analysis.mcp_validation_accuracy:.1f}% ({"✅ EXCEEDS" if analysis.mcp_validation_accuracy >= 99.5 else "⚠️ BELOW"} 99.5% requirement)
873
+ Infrastructure Alignment: {"✅ Terraform validated" if analysis.terraform_cost_alignment else "📊 Assessment available"}
874
+ Audit Trail: {"✅ Complete" if analysis.evidence_files else "⚠️ Generating"}
855
875
 
856
876
  🎯 Strategic Objectives:
857
877
  • runbooks package: ✅ Enhanced with real-time Cost Explorer API
@@ -865,19 +885,17 @@ Audit Trail: {'✅ Complete' if analysis.evidence_files else '⚠️ Generating'
865
885
  • Executive-ready reporting with quantified ROI"""
866
886
 
867
887
  compliance_panel = create_panel(
868
- compliance_text,
869
- title="Enterprise Compliance & Strategic Alignment",
870
- border_style=compliance_color
888
+ compliance_text, title="Enterprise Compliance & Strategic Alignment", border_style=compliance_color
871
889
  )
872
-
890
+
873
891
  console.print(compliance_panel)
874
-
892
+
875
893
  # Optimization opportunities summary
876
894
  if analysis.optimization_opportunities:
877
895
  print_info(f"🔧 {len(analysis.optimization_opportunities)} optimization opportunities identified")
878
896
  print_info(f"💰 Total annual savings potential: ${analysis.annual_savings_potential:,.2f}")
879
897
  print_info(f"📈 ROI projection: {analysis.roi_projection:.1f}%")
880
-
898
+
881
899
  # Evidence files
882
900
  if analysis.evidence_files:
883
901
  print_success(f"📄 Evidence files generated: {len(analysis.evidence_files)} files")
@@ -889,91 +907,65 @@ Audit Trail: {'✅ Complete' if analysis.evidence_files else '⚠️ Generating'
889
907
  async def main():
890
908
  """Main CLI interface for comprehensive cost analysis."""
891
909
  import argparse
892
-
910
+
893
911
  parser = argparse.ArgumentParser(
894
912
  description="Comprehensive AWS Cost Explorer Integration with MCP Validation and Terraform Alignment"
895
913
  )
914
+ parser.add_argument("--account-filter", help="Specific AWS account ID to analyze")
915
+ parser.add_argument("--analysis-days", type=int, default=90, help="Number of days for cost analysis (default: 90)")
916
+ parser.add_argument("--billing-profile", help="AWS profile for Cost Explorer access")
917
+ parser.add_argument("--management-profile", help="AWS profile for Organizations access")
918
+ parser.add_argument("--single-account-profile", help="AWS profile for single account operations")
919
+ parser.add_argument("--terraform-state-dir", help="Directory containing terraform state files")
920
+ parser.add_argument("--runbooks-evidence", help="Path to runbooks evidence file for terraform alignment")
921
+ parser.add_argument("--skip-terraform", action="store_true", help="Skip terraform alignment validation")
896
922
  parser.add_argument(
897
- "--account-filter",
898
- help="Specific AWS account ID to analyze"
923
+ "--validation-tolerance", type=float, default=5.0, help="MCP validation tolerance percentage (default: 5.0)"
899
924
  )
900
- parser.add_argument(
901
- "--analysis-days",
902
- type=int,
903
- default=90,
904
- help="Number of days for cost analysis (default: 90)"
905
- )
906
- parser.add_argument(
907
- "--billing-profile",
908
- help="AWS profile for Cost Explorer access"
909
- )
910
- parser.add_argument(
911
- "--management-profile",
912
- help="AWS profile for Organizations access"
913
- )
914
- parser.add_argument(
915
- "--single-account-profile",
916
- help="AWS profile for single account operations"
917
- )
918
- parser.add_argument(
919
- "--terraform-state-dir",
920
- help="Directory containing terraform state files"
921
- )
922
- parser.add_argument(
923
- "--runbooks-evidence",
924
- help="Path to runbooks evidence file for terraform alignment"
925
- )
926
- parser.add_argument(
927
- "--skip-terraform",
928
- action="store_true",
929
- help="Skip terraform alignment validation"
930
- )
931
- parser.add_argument(
932
- "--validation-tolerance",
933
- type=float,
934
- default=5.0,
935
- help="MCP validation tolerance percentage (default: 5.0)"
936
- )
937
-
925
+
938
926
  args = parser.parse_args()
939
-
927
+
940
928
  # Initialize comprehensive integration
941
929
  integration = ComprehensiveCostExplorerIntegration(
942
930
  billing_profile=args.billing_profile,
943
931
  management_profile=args.management_profile,
944
932
  single_account_profile=args.single_account_profile,
945
933
  terraform_state_dir=args.terraform_state_dir,
946
- validation_tolerance_percent=args.validation_tolerance
934
+ validation_tolerance_percent=args.validation_tolerance,
947
935
  )
948
-
936
+
949
937
  try:
950
938
  # Initialize all integrations
951
939
  init_results = await integration.initialize_integrations()
952
-
953
- if init_results['overall_status'] == 'initialization_failed':
940
+
941
+ if init_results["overall_status"] == "initialization_failed":
954
942
  print_error("❌ Integration initialization failed - limited functionality available")
955
-
943
+
956
944
  # Perform comprehensive cost analysis
957
945
  analysis = await integration.perform_comprehensive_cost_analysis(
958
946
  account_filter=args.account_filter,
959
947
  analysis_days=args.analysis_days,
960
948
  include_terraform_alignment=not args.skip_terraform and bool(args.runbooks_evidence),
961
- runbooks_evidence_file=args.runbooks_evidence
949
+ runbooks_evidence_file=args.runbooks_evidence,
962
950
  )
963
-
951
+
964
952
  # Final summary
965
- if analysis.compliance_status == 'compliant':
966
- print_success("✅ ENTERPRISE COMPLIANCE ACHIEVED: ≥99.5% MCP validation with complete infrastructure alignment")
953
+ if analysis.compliance_status == "compliant":
954
+ print_success(
955
+ "✅ ENTERPRISE COMPLIANCE ACHIEVED: ≥99.5% MCP validation with complete infrastructure alignment"
956
+ )
967
957
  else:
968
958
  print_warning("⚠️ COMPLIANCE REVIEW REQUIRED: Enhance MCP validation accuracy to meet enterprise standards")
969
-
970
- print_info(f"💰 Annual savings potential: ${analysis.annual_savings_potential:,.2f} ({analysis.roi_projection:.1f}% ROI)")
959
+
960
+ print_info(
961
+ f"💰 Annual savings potential: ${analysis.annual_savings_potential:,.2f} ({analysis.roi_projection:.1f}% ROI)"
962
+ )
971
963
  print_info(f"📊 Analysis evidence: {len(analysis.evidence_files)} files generated")
972
-
964
+
973
965
  except Exception as e:
974
966
  print_error(f"❌ Comprehensive cost analysis failed: {str(e)}")
975
967
  raise
976
968
 
977
969
 
978
970
  if __name__ == "__main__":
979
- asyncio.run(main())
971
+ asyncio.run(main())