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
@@ -13,22 +13,31 @@ from dataclasses import dataclass, field
13
13
  from enum import Enum
14
14
 
15
15
  from .rich_utils import (
16
- create_table, console, print_header, print_success, print_info,
17
- print_warning, format_cost, create_panel, create_progress_bar
16
+ create_table,
17
+ console,
18
+ print_header,
19
+ print_success,
20
+ print_info,
21
+ print_warning,
22
+ format_cost,
23
+ create_panel,
24
+ create_progress_bar,
18
25
  )
19
26
  from .profile_utils import get_profile_for_operation
20
27
 
21
28
 
22
29
  class BusinessImpactLevel(Enum):
23
30
  """Business impact classification for operations and optimizations."""
31
+
24
32
  CRITICAL = "CRITICAL" # >$100K annual impact
25
- HIGH = "HIGH" # $20K-100K annual impact
26
- MEDIUM = "MEDIUM" # $5K-20K annual impact
27
- LOW = "LOW" # <$5K annual impact
33
+ HIGH = "HIGH" # measurable range annual impact
34
+ MEDIUM = "MEDIUM" # measurable range annual impact
35
+ LOW = "LOW" # <$5K annual impact
28
36
 
29
37
 
30
38
  class OptimizationType(Enum):
31
39
  """Types of optimization operations supported."""
40
+
32
41
  COST_REDUCTION = "COST_REDUCTION"
33
42
  RESOURCE_EFFICIENCY = "RESOURCE_EFFICIENCY"
34
43
  SECURITY_COMPLIANCE = "SECURITY_COMPLIANCE"
@@ -39,6 +48,7 @@ class OptimizationType(Enum):
39
48
  @dataclass
40
49
  class BusinessMetrics:
41
50
  """Universal business metrics for operations and optimizations."""
51
+
42
52
  annual_savings: float = 0.0
43
53
  monthly_cost_current: float = 0.0
44
54
  monthly_cost_optimized: float = 0.0
@@ -70,6 +80,7 @@ class BusinessMetrics:
70
80
  @dataclass
71
81
  class OptimizationResult:
72
82
  """Universal optimization result structure."""
83
+
73
84
  resource_type: str
74
85
  operation_type: OptimizationType
75
86
  business_metrics: BusinessMetrics
@@ -101,8 +112,9 @@ class UniversalBusinessLogic:
101
112
  self.module_name = module_name
102
113
  self.session_metrics = []
103
114
 
104
- def create_cost_analysis_table(self, cost_data: Dict[str, Any], title: str,
105
- include_quarterly: bool = False) -> None:
115
+ def create_cost_analysis_table(
116
+ self, cost_data: Dict[str, Any], title: str, include_quarterly: bool = False
117
+ ) -> None:
106
118
  """
107
119
  Standardized cost analysis table creation following FinOps patterns.
108
120
 
@@ -111,10 +123,7 @@ class UniversalBusinessLogic:
111
123
  title: Table title for display
112
124
  include_quarterly: Include quarterly intelligence columns
113
125
  """
114
- table = create_table(
115
- title=title,
116
- caption="Enterprise cost analysis with MCP validation"
117
- )
126
+ table = create_table(title=title, caption="Enterprise cost analysis with MCP validation")
118
127
 
119
128
  # Standard columns based on successful FinOps patterns
120
129
  table.add_column("Resource", style="cyan", no_wrap=True)
@@ -129,21 +138,16 @@ class UniversalBusinessLogic:
129
138
  # Add rows with consistent formatting
130
139
  total_savings = 0.0
131
140
  for resource, data in cost_data.items():
132
- current_cost = data.get('current', 0.0)
133
- optimization_pct = data.get('optimization_percentage', 0.0)
134
- annual_savings = data.get('annual_savings', 0.0)
141
+ current_cost = data.get("current", 0.0)
142
+ optimization_pct = data.get("optimization_percentage", 0.0)
143
+ annual_savings = data.get("annual_savings", 0.0)
135
144
  total_savings += annual_savings
136
145
 
137
- row_data = [
138
- resource,
139
- format_cost(current_cost),
140
- f"{optimization_pct:.1f}%",
141
- format_cost(annual_savings)
142
- ]
146
+ row_data = [resource, format_cost(current_cost), f"{optimization_pct:.1f}%", format_cost(annual_savings)]
143
147
 
144
148
  if include_quarterly:
145
- quarterly_trend = data.get('quarterly_trend', 'Stable')
146
- strategic_context = data.get('strategic_context', 'Monitor')
149
+ quarterly_trend = data.get("quarterly_trend", "Stable")
150
+ strategic_context = data.get("strategic_context", "Monitor")
147
151
  row_data.extend([quarterly_trend, strategic_context])
148
152
 
149
153
  table.add_row(*row_data)
@@ -163,17 +167,14 @@ class UniversalBusinessLogic:
163
167
  [bold bright_green]Total Annual Savings: {format_cost(total_savings)}[/]
164
168
  [yellow]Business Impact: {impact_level.value}[/]
165
169
  [cyan]Resources Analyzed: {len(cost_data)}[/]
166
- [dim]Analysis Timestamp: {datetime.now().strftime('%Y-%m-%d %H:%M:%S')}[/]
170
+ [dim]Analysis Timestamp: {datetime.now().strftime("%Y-%m-%d %H:%M:%S")}[/]
167
171
  """
168
- summary_panel = create_panel(
169
- summary_text.strip(),
170
- title="💰 Executive Summary",
171
- border_style="green"
172
- )
172
+ summary_panel = create_panel(summary_text.strip(), title="💰 Executive Summary", border_style="green")
173
173
  console.print(summary_panel)
174
174
 
175
- def standardize_resource_operations(self, resource_type: str, operation: str,
176
- profile: Optional[str] = None, **kwargs) -> Dict[str, Any]:
175
+ def standardize_resource_operations(
176
+ self, resource_type: str, operation: str, profile: Optional[str] = None, **kwargs
177
+ ) -> Dict[str, Any]:
177
178
  """
178
179
  Standardized resource operation pattern following proven CLI patterns.
179
180
 
@@ -189,7 +190,7 @@ class UniversalBusinessLogic:
189
190
  # Apply proven profile management patterns
190
191
  selected_profile = get_profile_for_operation("operational", profile)
191
192
 
192
- print_header(f"{resource_type.title()} {operation.title()}", f"v1.1.2 - {self.module_name}")
193
+ print_header(f"{resource_type.title()} {operation.title()}", f"latest version - {self.module_name}")
193
194
  print_info(f"Using profile: {selected_profile}")
194
195
 
195
196
  # Standard operation tracking
@@ -197,19 +198,16 @@ class UniversalBusinessLogic:
197
198
 
198
199
  # Standard result format following successful patterns
199
200
  result = {
200
- 'module': self.module_name,
201
- 'resource_type': resource_type,
202
- 'operation': operation,
203
- 'profile_used': selected_profile,
204
- 'timestamp': operation_start.isoformat(),
205
- 'success': True,
206
- 'results': {},
207
- 'business_metrics': BusinessMetrics(),
208
- 'recommendations': [],
209
- 'performance_data': {
210
- 'start_time': operation_start.isoformat(),
211
- 'execution_time_seconds': 0.0
212
- }
201
+ "module": self.module_name,
202
+ "resource_type": resource_type,
203
+ "operation": operation,
204
+ "profile_used": selected_profile,
205
+ "timestamp": operation_start.isoformat(),
206
+ "success": True,
207
+ "results": {},
208
+ "business_metrics": BusinessMetrics(),
209
+ "recommendations": [],
210
+ "performance_data": {"start_time": operation_start.isoformat(), "execution_time_seconds": 0.0},
213
211
  }
214
212
 
215
213
  return result
@@ -230,30 +228,38 @@ class UniversalBusinessLogic:
230
228
 
231
229
  # Impact-based recommendations
232
230
  if impact == BusinessImpactLevel.CRITICAL:
233
- recommendations.extend([
234
- f"🚨 CRITICAL: Immediate action required - ${metrics.annual_savings:,.0f} annual savings opportunity",
235
- "📋 Executive approval recommended for implementation",
236
- " Target implementation: Within 30 days",
237
- "📊 Monthly progress tracking recommended"
238
- ])
231
+ recommendations.extend(
232
+ [
233
+ f"🚨 CRITICAL: Immediate action required - ${metrics.annual_savings:,.0f} annual savings opportunity",
234
+ "📋 Executive approval recommended for implementation",
235
+ " Target implementation: Within 30 days",
236
+ "📊 Monthly progress tracking recommended",
237
+ ]
238
+ )
239
239
  elif impact == BusinessImpactLevel.HIGH:
240
- recommendations.extend([
241
- f"🔴 HIGH PRIORITY: ${metrics.annual_savings:,.0f} annual savings available",
242
- "📋 Business case development recommended",
243
- " Target implementation: Within 90 days",
244
- "📊 Quarterly progress review recommended"
245
- ])
240
+ recommendations.extend(
241
+ [
242
+ f"🔴 HIGH PRIORITY: ${metrics.annual_savings:,.0f} annual savings available",
243
+ "📋 Business case development recommended",
244
+ " Target implementation: Within 90 days",
245
+ "📊 Quarterly progress review recommended",
246
+ ]
247
+ )
246
248
  elif impact == BusinessImpactLevel.MEDIUM:
247
- recommendations.extend([
248
- f"🟡 MEDIUM PRIORITY: ${metrics.annual_savings:,.0f} annual savings potential",
249
- "📋 Consider in next planning cycle",
250
- " Target implementation: Within 6 months"
251
- ])
249
+ recommendations.extend(
250
+ [
251
+ f"🟡 MEDIUM PRIORITY: ${metrics.annual_savings:,.0f} annual savings potential",
252
+ "📋 Consider in next planning cycle",
253
+ "⏰ Target implementation: Within 6 months",
254
+ ]
255
+ )
252
256
  else:
253
- recommendations.extend([
254
- f"🟢 LOW PRIORITY: ${metrics.annual_savings:,.0f} annual savings",
255
- "📋 Include in routine optimization reviews"
256
- ])
257
+ recommendations.extend(
258
+ [
259
+ f"🟢 LOW PRIORITY: ${metrics.annual_savings:,.0f} annual savings",
260
+ "📋 Include in routine optimization reviews",
261
+ ]
262
+ )
257
263
 
258
264
  # ROI-based recommendations
259
265
  if metrics.roi_percentage > 200:
@@ -271,8 +277,9 @@ class UniversalBusinessLogic:
271
277
 
272
278
  return recommendations
273
279
 
274
- def create_executive_dashboard(self, results: List[OptimizationResult],
275
- dashboard_title: str = "Executive Dashboard") -> None:
280
+ def create_executive_dashboard(
281
+ self, results: List[OptimizationResult], dashboard_title: str = "Executive Dashboard"
282
+ ) -> None:
276
283
  """
277
284
  Create executive dashboard following successful FinOps patterns.
278
285
 
@@ -288,7 +295,14 @@ class UniversalBusinessLogic:
288
295
 
289
296
  # Summary metrics
290
297
  total_savings = sum(r.business_metrics.annual_savings for r in results)
291
- high_impact_count = len([r for r in results if r.business_metrics.determine_impact_level() in [BusinessImpactLevel.CRITICAL, BusinessImpactLevel.HIGH]])
298
+ high_impact_count = len(
299
+ [
300
+ r
301
+ for r in results
302
+ if r.business_metrics.determine_impact_level()
303
+ in [BusinessImpactLevel.CRITICAL, BusinessImpactLevel.HIGH]
304
+ ]
305
+ )
292
306
 
293
307
  # Executive summary table
294
308
  summary_table = create_table(
@@ -296,13 +310,17 @@ class UniversalBusinessLogic:
296
310
  columns=[
297
311
  {"name": "Metric", "style": "cyan", "justify": "left"},
298
312
  {"name": "Value", "style": "bright_green", "justify": "right"},
299
- {"name": "Impact", "style": "yellow", "justify": "left"}
300
- ]
313
+ {"name": "Impact", "style": "yellow", "justify": "left"},
314
+ ],
301
315
  )
302
316
 
303
317
  summary_table.add_row("Total Annual Savings", format_cost(total_savings), f"{len(results)} opportunities")
304
318
  summary_table.add_row("High Priority Items", str(high_impact_count), "Immediate attention required")
305
- summary_table.add_row("Average Confidence", f"{sum(r.business_metrics.confidence_level for r in results) / len(results):.1f}%", "Validation accuracy")
319
+ summary_table.add_row(
320
+ "Average Confidence",
321
+ f"{sum(r.business_metrics.confidence_level for r in results) / len(results):.1f}%",
322
+ "Validation accuracy",
323
+ )
306
324
 
307
325
  console.print(summary_table)
308
326
 
@@ -318,8 +336,8 @@ class UniversalBusinessLogic:
318
336
  {"name": "Annual Savings", "style": "bright_green", "justify": "right"},
319
337
  {"name": "Impact", "style": "yellow", "justify": "center"},
320
338
  {"name": "Confidence", "style": "blue", "justify": "right"},
321
- {"name": "Next Action", "style": "white", "justify": "left"}
322
- ]
339
+ {"name": "Next Action", "style": "white", "justify": "left"},
340
+ ],
323
341
  )
324
342
 
325
343
  for result in top_results:
@@ -331,7 +349,7 @@ class UniversalBusinessLogic:
331
349
  format_cost(result.business_metrics.annual_savings),
332
350
  impact.value,
333
351
  f"{result.business_metrics.confidence_level:.1f}%",
334
- next_action
352
+ next_action,
335
353
  )
336
354
 
337
355
  console.print(opportunities_table)
@@ -350,8 +368,8 @@ class UniversalBusinessLogic:
350
368
  metrics = BusinessMetrics()
351
369
 
352
370
  # Extract costs
353
- current_monthly = usage_data.get('monthly_cost_current', 0.0)
354
- optimized_monthly = usage_data.get('monthly_cost_optimized', current_monthly * 0.7) # Default 30% optimization
371
+ current_monthly = usage_data.get("monthly_cost_current", 0.0)
372
+ optimized_monthly = usage_data.get("monthly_cost_optimized", current_monthly * 0.7) # Default 30% optimization
355
373
 
356
374
  metrics.monthly_cost_current = current_monthly
357
375
  metrics.monthly_cost_optimized = optimized_monthly
@@ -362,12 +380,12 @@ class UniversalBusinessLogic:
362
380
 
363
381
  # Set confidence based on resource type (following successful patterns)
364
382
  confidence_levels = {
365
- 'NAT Gateway': 95.0, # High confidence from proven results
366
- 'Elastic IP': 90.0,
367
- 'EBS Volume': 85.0,
368
- 'EC2 Instance': 80.0,
369
- 'RDS Instance': 75.0,
370
- 'Generic': 70.0
383
+ "NAT Gateway": 95.0, # High confidence from proven results
384
+ "Elastic IP": 90.0,
385
+ "EBS Volume": 85.0,
386
+ "EC2 Instance": 80.0,
387
+ "RDS Instance": 75.0,
388
+ "Generic": 70.0,
371
389
  }
372
390
  metrics.confidence_level = confidence_levels.get(resource_type, 70.0)
373
391
 
@@ -384,8 +402,9 @@ class UniversalBusinessLogic:
384
402
 
385
403
  return metrics
386
404
 
387
- def export_business_results(self, results: List[OptimizationResult],
388
- export_formats: List[str] = None) -> Dict[str, str]:
405
+ def export_business_results(
406
+ self, results: List[OptimizationResult], export_formats: List[str] = None
407
+ ) -> Dict[str, str]:
389
408
  """
390
409
  Export business results in multiple formats following successful patterns.
391
410
 
@@ -397,9 +416,9 @@ class UniversalBusinessLogic:
397
416
  Dictionary with export file paths
398
417
  """
399
418
  if export_formats is None:
400
- export_formats = ['csv', 'json', 'markdown']
419
+ export_formats = ["csv", "json", "markdown"]
401
420
 
402
- timestamp = datetime.now().strftime('%Y%m%d_%H%M%S')
421
+ timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
403
422
  base_filename = f"{self.module_name}_optimization_results_{timestamp}"
404
423
 
405
424
  exported_files = {}
@@ -409,41 +428,44 @@ class UniversalBusinessLogic:
409
428
  for fmt in export_formats:
410
429
  filename = f"./awso_evidence/{base_filename}.{fmt}"
411
430
 
412
- if fmt == 'csv':
431
+ if fmt == "csv":
413
432
  # CSV export for analysis
414
433
  csv_content = "Resource,Annual_Savings,Impact_Level,Confidence,ROI_Percentage\n"
415
434
  for result in results:
416
435
  csv_content += f"{result.resource_type},{result.business_metrics.annual_savings},"
417
436
  csv_content += f"{result.business_metrics.determine_impact_level().value},"
418
- csv_content += f"{result.business_metrics.confidence_level},{result.business_metrics.roi_percentage}\n"
437
+ csv_content += (
438
+ f"{result.business_metrics.confidence_level},{result.business_metrics.roi_percentage}\n"
439
+ )
419
440
 
420
- with open(filename, 'w') as f:
441
+ with open(filename, "w") as f:
421
442
  f.write(csv_content)
422
443
 
423
- elif fmt == 'json':
444
+ elif fmt == "json":
424
445
  # JSON export for systems integration
425
446
  import json
447
+
426
448
  json_data = {
427
- 'module': self.module_name,
428
- 'timestamp': timestamp,
429
- 'total_results': len(results),
430
- 'total_annual_savings': sum(r.business_metrics.annual_savings for r in results),
431
- 'results': [
449
+ "module": self.module_name,
450
+ "timestamp": timestamp,
451
+ "total_results": len(results),
452
+ "total_annual_savings": sum(r.business_metrics.annual_savings for r in results),
453
+ "results": [
432
454
  {
433
- 'resource_type': r.resource_type,
434
- 'annual_savings': r.business_metrics.annual_savings,
435
- 'impact_level': r.business_metrics.determine_impact_level().value,
436
- 'confidence_level': r.business_metrics.confidence_level,
437
- 'executive_summary': r.get_executive_summary()
455
+ "resource_type": r.resource_type,
456
+ "annual_savings": r.business_metrics.annual_savings,
457
+ "impact_level": r.business_metrics.determine_impact_level().value,
458
+ "confidence_level": r.business_metrics.confidence_level,
459
+ "executive_summary": r.get_executive_summary(),
438
460
  }
439
461
  for r in results
440
- ]
462
+ ],
441
463
  }
442
464
 
443
- with open(filename, 'w') as f:
465
+ with open(filename, "w") as f:
444
466
  json.dump(json_data, f, indent=2)
445
467
 
446
- elif fmt == 'markdown':
468
+ elif fmt == "markdown":
447
469
  # Markdown export for documentation and reports
448
470
  md_content = f"# {self.module_name.title()} Optimization Results\n\n"
449
471
  md_content += f"**Generated**: {datetime.now().strftime('%Y-%m-%d %H:%M:%S')}\n\n"
@@ -462,7 +484,7 @@ class UniversalBusinessLogic:
462
484
  md_content += f"- **Confidence**: {result.business_metrics.confidence_level:.1f}%\n"
463
485
  md_content += f"- **ROI**: {result.business_metrics.roi_percentage:.1f}%\n\n"
464
486
 
465
- with open(filename, 'w') as f:
487
+ with open(filename, "w") as f:
466
488
  f.write(md_content)
467
489
 
468
490
  exported_files[fmt] = filename
@@ -482,4 +504,4 @@ def create_business_logic_handler(module_name: str) -> UniversalBusinessLogic:
482
504
  Returns:
483
505
  UniversalBusinessLogic instance configured for the module
484
506
  """
485
- return UniversalBusinessLogic(module_name)
507
+ return UniversalBusinessLogic(module_name)
@@ -27,26 +27,19 @@ def common_aws_options(f: Callable) -> Callable:
27
27
  def my_command(profile, region, dry_run, **kwargs):
28
28
  # Your command logic here
29
29
  """
30
+
31
+ @click.option("--profile", help="AWS profile override (highest priority over environment variables)", type=str)
32
+ @click.option("--region", help="AWS region override (default: us-east-1)", type=str, default="us-east-1")
30
33
  @click.option(
31
- '--profile',
32
- help='AWS profile override (highest priority over environment variables)',
33
- type=str
34
- )
35
- @click.option(
36
- '--region',
37
- help='AWS region override (default: us-east-1)',
38
- type=str,
39
- default='us-east-1'
40
- )
41
- @click.option(
42
- '--dry-run',
34
+ "--dry-run",
43
35
  is_flag=True,
44
36
  default=True,
45
- help='Safe analysis mode - no resource modifications (enterprise default)'
37
+ help="Safe analysis mode - no resource modifications (enterprise default)",
46
38
  )
47
39
  @wraps(f)
48
40
  def wrapper(*args, **kwargs):
49
41
  return f(*args, **kwargs)
42
+
50
43
  return wrapper
51
44
 
52
45
 
@@ -65,26 +58,24 @@ def common_output_options(f: Callable) -> Callable:
65
58
  def my_command(output_format, output_dir, export, **kwargs):
66
59
  # Your command logic here
67
60
  """
61
+
68
62
  @click.option(
69
- '--output-format',
70
- type=click.Choice(['json', 'csv', 'table', 'pdf', 'markdown'], case_sensitive=False),
71
- default='table',
72
- help='Output format for results display'
73
- )
74
- @click.option(
75
- '--output-dir',
76
- default='./awso_evidence',
77
- help='Directory for generated files and evidence packages',
78
- type=click.Path()
63
+ "--output-format",
64
+ type=click.Choice(["json", "csv", "table", "pdf", "markdown"], case_sensitive=False),
65
+ default="table",
66
+ help="Output format for results display",
79
67
  )
80
68
  @click.option(
81
- '--export',
82
- is_flag=True,
83
- help='Enable multi-format export (CSV, JSON, PDF, HTML)'
69
+ "--output-dir",
70
+ default="./awso_evidence",
71
+ help="Directory for generated files and evidence packages",
72
+ type=click.Path(),
84
73
  )
74
+ @click.option("--export", is_flag=True, help="Enable multi-format export (CSV, JSON, PDF, HTML)")
85
75
  @wraps(f)
86
76
  def wrapper(*args, **kwargs):
87
77
  return f(*args, **kwargs)
78
+
88
79
  return wrapper
89
80
 
90
81
 
@@ -102,20 +93,18 @@ def mcp_validation_option(f: Callable) -> Callable:
102
93
  def my_command(validate, confidence_threshold, **kwargs):
103
94
  # Your command logic with MCP validation
104
95
  """
96
+
97
+ @click.option("--validate", is_flag=True, help="Enable MCP validation for enhanced accuracy (≥99.5% target)")
105
98
  @click.option(
106
- '--validate',
107
- is_flag=True,
108
- help='Enable MCP validation for enhanced accuracy (≥99.5% target)'
109
- )
110
- @click.option(
111
- '--confidence-threshold',
99
+ "--confidence-threshold",
112
100
  type=float,
113
101
  default=99.5,
114
- help='Minimum confidence threshold for validation (default: 99.5%%)'
102
+ help="Minimum confidence threshold for validation (default: 99.5%%)",
115
103
  )
116
104
  @wraps(f)
117
105
  def wrapper(*args, **kwargs):
118
106
  return f(*args, **kwargs)
107
+
119
108
  return wrapper
120
109
 
121
110
 
@@ -134,26 +123,21 @@ def enterprise_options(f: Callable) -> Callable:
134
123
  def my_command(all_profiles, combine, approval_required, **kwargs):
135
124
  # Your enterprise command logic
136
125
  """
126
+
137
127
  @click.option(
138
- '--all',
139
- 'all_profiles',
140
- is_flag=True,
141
- help='Use all available AWS profiles for multi-account operations'
142
- )
143
- @click.option(
144
- '--combine',
145
- is_flag=True,
146
- help='Combine profiles from the same AWS account for unified reporting'
128
+ "--all", "all_profiles", is_flag=True, help="Use all available AWS profiles for multi-account operations"
147
129
  )
130
+ @click.option("--combine", is_flag=True, help="Combine profiles from the same AWS account for unified reporting")
148
131
  @click.option(
149
- '--approval-required',
132
+ "--approval-required",
150
133
  is_flag=True,
151
134
  default=True,
152
- help='Require human approval for state-changing operations (enterprise default)'
135
+ help="Require human approval for state-changing operations (enterprise default)",
153
136
  )
154
137
  @wraps(f)
155
138
  def wrapper(*args, **kwargs):
156
139
  return f(*args, **kwargs)
140
+
157
141
  return wrapper
158
142
 
159
143
 
@@ -172,26 +156,16 @@ def performance_options(f: Callable) -> Callable:
172
156
  def my_command(performance_target, timeout, parallel, **kwargs):
173
157
  # Your performance-monitored command
174
158
  """
159
+
175
160
  @click.option(
176
- '--performance-target',
177
- type=int,
178
- default=30,
179
- help='Target execution time in seconds (enterprise default: 30s)'
180
- )
181
- @click.option(
182
- '--timeout',
183
- type=int,
184
- default=300,
185
- help='Maximum execution timeout in seconds (default: 5 minutes)'
186
- )
187
- @click.option(
188
- '--parallel',
189
- is_flag=True,
190
- help='Enable parallel processing for multi-resource operations'
161
+ "--performance-target", type=int, default=30, help="Target execution time in seconds (enterprise default: 30s)"
191
162
  )
163
+ @click.option("--timeout", type=int, default=300, help="Maximum execution timeout in seconds (default: 5 minutes)")
164
+ @click.option("--parallel", is_flag=True, help="Enable parallel processing for multi-resource operations")
192
165
  @wraps(f)
193
166
  def wrapper(*args, **kwargs):
194
167
  return f(*args, **kwargs)
168
+
195
169
  return wrapper
196
170
 
197
171
 
@@ -208,6 +182,7 @@ def all_standard_options(f: Callable) -> Callable:
208
182
  def comprehensive_command(**kwargs):
209
183
  # Command with all standard options available
210
184
  """
185
+
211
186
  @performance_options
212
187
  @enterprise_options
213
188
  @mcp_validation_option
@@ -216,4 +191,5 @@ def all_standard_options(f: Callable) -> Callable:
216
191
  @wraps(f)
217
192
  def wrapper(*args, **kwargs):
218
193
  return f(*args, **kwargs)
219
- return wrapper
194
+
195
+ return wrapper