cdk-factory 0.15.10__py3-none-any.whl → 0.18.9__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.

Potentially problematic release.


This version of cdk-factory might be problematic. Click here for more details.

Files changed (63) hide show
  1. cdk_factory/configurations/base_config.py +23 -24
  2. cdk_factory/configurations/cdk_config.py +6 -4
  3. cdk_factory/configurations/deployment.py +12 -0
  4. cdk_factory/configurations/devops.py +1 -1
  5. cdk_factory/configurations/pipeline_stage.py +29 -5
  6. cdk_factory/configurations/resources/acm.py +85 -0
  7. cdk_factory/configurations/resources/auto_scaling.py +7 -5
  8. cdk_factory/configurations/resources/cloudfront.py +7 -2
  9. cdk_factory/configurations/resources/ecr.py +1 -1
  10. cdk_factory/configurations/resources/ecs_cluster.py +108 -0
  11. cdk_factory/configurations/resources/ecs_service.py +17 -2
  12. cdk_factory/configurations/resources/load_balancer.py +17 -4
  13. cdk_factory/configurations/resources/monitoring.py +8 -3
  14. cdk_factory/configurations/resources/rds.py +305 -19
  15. cdk_factory/configurations/resources/rum.py +7 -2
  16. cdk_factory/configurations/resources/s3.py +1 -1
  17. cdk_factory/configurations/resources/security_group_full_stack.py +7 -8
  18. cdk_factory/configurations/resources/vpc.py +19 -0
  19. cdk_factory/configurations/workload.py +32 -2
  20. cdk_factory/constructs/ecr/ecr_construct.py +9 -2
  21. cdk_factory/constructs/lambdas/policies/policy_docs.py +4 -4
  22. cdk_factory/interfaces/istack.py +6 -3
  23. cdk_factory/interfaces/networked_stack_mixin.py +75 -0
  24. cdk_factory/interfaces/standardized_ssm_mixin.py +657 -0
  25. cdk_factory/interfaces/vpc_provider_mixin.py +210 -0
  26. cdk_factory/lambdas/edge/ip_gate/handler.py +42 -40
  27. cdk_factory/pipeline/pipeline_factory.py +222 -27
  28. cdk_factory/stack/stack_factory.py +34 -0
  29. cdk_factory/stack_library/__init__.py +3 -2
  30. cdk_factory/stack_library/acm/__init__.py +6 -0
  31. cdk_factory/stack_library/acm/acm_stack.py +169 -0
  32. cdk_factory/stack_library/api_gateway/api_gateway_stack.py +84 -59
  33. cdk_factory/stack_library/auto_scaling/auto_scaling_stack.py +366 -408
  34. cdk_factory/stack_library/code_artifact/code_artifact_stack.py +2 -2
  35. cdk_factory/stack_library/cognito/cognito_stack.py +152 -92
  36. cdk_factory/stack_library/dynamodb/dynamodb_stack.py +19 -15
  37. cdk_factory/stack_library/ecr/ecr_stack.py +2 -2
  38. cdk_factory/stack_library/ecs/__init__.py +12 -0
  39. cdk_factory/stack_library/ecs/ecs_cluster_stack.py +316 -0
  40. cdk_factory/stack_library/ecs/ecs_service_stack.py +20 -39
  41. cdk_factory/stack_library/lambda_edge/lambda_edge_stack.py +2 -2
  42. cdk_factory/stack_library/load_balancer/load_balancer_stack.py +151 -118
  43. cdk_factory/stack_library/rds/rds_stack.py +85 -74
  44. cdk_factory/stack_library/route53/route53_stack.py +8 -3
  45. cdk_factory/stack_library/rum/rum_stack.py +108 -91
  46. cdk_factory/stack_library/security_group/security_group_full_stack.py +9 -22
  47. cdk_factory/stack_library/security_group/security_group_stack.py +11 -11
  48. cdk_factory/stack_library/stack_base.py +5 -0
  49. cdk_factory/stack_library/vpc/vpc_stack.py +272 -124
  50. cdk_factory/stack_library/websites/static_website_stack.py +1 -1
  51. cdk_factory/utilities/api_gateway_integration_utility.py +24 -16
  52. cdk_factory/utilities/environment_services.py +5 -5
  53. cdk_factory/utilities/json_loading_utility.py +12 -3
  54. cdk_factory/validation/config_validator.py +483 -0
  55. cdk_factory/version.py +1 -1
  56. cdk_factory/workload/workload_factory.py +1 -0
  57. {cdk_factory-0.15.10.dist-info → cdk_factory-0.18.9.dist-info}/METADATA +1 -1
  58. {cdk_factory-0.15.10.dist-info → cdk_factory-0.18.9.dist-info}/RECORD +61 -54
  59. cdk_factory/interfaces/enhanced_ssm_parameter_mixin.py +0 -321
  60. cdk_factory/interfaces/ssm_parameter_mixin.py +0 -329
  61. {cdk_factory-0.15.10.dist-info → cdk_factory-0.18.9.dist-info}/WHEEL +0 -0
  62. {cdk_factory-0.15.10.dist-info → cdk_factory-0.18.9.dist-info}/entry_points.txt +0 -0
  63. {cdk_factory-0.15.10.dist-info → cdk_factory-0.18.9.dist-info}/licenses/LICENSE +0 -0
@@ -1,329 +0,0 @@
1
- """
2
- Geek Cafe, LLC
3
- Maintainers: Eric Wilson
4
- MIT License. See Project Root for the license information.
5
- """
6
-
7
- from typing import Dict, Any, Optional
8
- from aws_cdk import aws_ssm as ssm
9
- from constructs import Construct
10
- from aws_lambda_powertools import Logger
11
-
12
- logger = Logger(__name__)
13
-
14
-
15
- class SsmParameterMixin:
16
- """
17
- A mixin class that provides SSM parameter export and import functionality
18
- for CDK stacks.
19
-
20
- This mixin should be used by stack classes to standardize how SSM parameters
21
- are exported and imported across the project.
22
- """
23
-
24
- @staticmethod
25
- def normalize_resource_name(name: str, for_export: bool = False) -> str:
26
- """
27
- Normalize resource names for consistent naming across CDK stacks.
28
-
29
- Args:
30
- name: The resource name to normalize
31
- for_export: If True, keeps hyphens for CloudFormation export compatibility
32
-
33
- Returns:
34
- Normalized name with consistent convention
35
-
36
- Examples:
37
- "web-servers" -> "web_servers" (for SSM parameters)
38
- "web-servers" -> "web-servers" (for CloudFormation exports, for_export=True)
39
- "API-Gateway" -> "api_gateway" or "api-gateway"
40
- """
41
- if for_export:
42
- # CloudFormation exports only allow alphanumeric, colons, hyphens
43
- return name.lower()
44
- else:
45
- # SSM parameters use underscores for consistency
46
- return name.replace("-", "_").lower()
47
-
48
- def export_ssm_parameter(
49
- self,
50
- scope: Construct,
51
- id: str,
52
- value: str,
53
- parameter_name: str,
54
- description: str = None,
55
- string_list_value: bool = False,
56
- ) -> ssm.StringParameter:
57
- """
58
- Export a value to SSM Parameter Store.
59
-
60
- Args:
61
- scope: The CDK construct scope
62
- id: The construct ID for the SSM parameter
63
- value: The value to store in the parameter
64
- parameter_name: The name of the parameter in SSM
65
- description: Optional description for the parameter
66
- string_list_value: Whether the parameter is a comma-delimited list
67
-
68
- Returns:
69
- The created SSM parameter
70
- """
71
- if not parameter_name:
72
- logger.warning(f"No SSM parameter name provided for {id}, skipping export")
73
- return None
74
-
75
- # Ensure parameter name starts with a slash
76
- if not parameter_name.startswith("/"):
77
- parameter_name = f"/{parameter_name}"
78
-
79
- logger.info(f"Exporting SSM parameter: {parameter_name}")
80
-
81
- return ssm.StringParameter(
82
- scope=scope,
83
- id=id,
84
- string_value=value,
85
- parameter_name=parameter_name,
86
- description=description,
87
- )
88
-
89
- def import_ssm_parameter(
90
- self,
91
- scope: Construct,
92
- id: str,
93
- parameter_name: str,
94
- version: Optional[int] = None,
95
- ) -> str:
96
- """
97
- Import a value from SSM Parameter Store.
98
-
99
- Args:
100
- scope: The CDK construct scope
101
- id: The construct ID for the SSM parameter reference
102
- parameter_name: The name of the parameter in SSM
103
- version: Optional specific version to retrieve
104
-
105
- Returns:
106
- The parameter value as a string
107
- """
108
- if not parameter_name:
109
- logger.warning(f"No SSM parameter name provided for {id}, cannot import")
110
- return None
111
-
112
- # Ensure parameter name starts with a slash
113
- if not parameter_name.startswith("/"):
114
- parameter_name = f"/{parameter_name}"
115
-
116
- logger.info(f"Importing SSM parameter: {parameter_name}")
117
-
118
- if version:
119
- return ssm.StringParameter.from_string_parameter_attributes(
120
- scope,
121
- id,
122
- parameter_name=parameter_name,
123
- version=version,
124
- ).string_value
125
- else:
126
- return ssm.StringParameter.from_string_parameter_name(
127
- scope,
128
- id,
129
- parameter_name,
130
- ).string_value
131
-
132
- def export_ssm_parameters_from_config(
133
- self,
134
- scope: Construct,
135
- config_dict: Dict[str, Any],
136
- ssm_config: Dict[str, str],
137
- resource: str = "",
138
- ) -> Dict[str, ssm.StringParameter]:
139
- """
140
- Export multiple SSM parameters based on a configuration dictionary and SSM path mapping.
141
-
142
- Args:
143
- scope: The CDK construct scope
144
- config_dict: Dictionary containing values to export
145
- ssm_config: Dictionary mapping keys to SSM parameter paths
146
- resource: Optional resource name for the parameter IDs
147
-
148
- Returns:
149
- Dictionary of created SSM parameters
150
- """
151
- parameters = {}
152
- missing_keys = []
153
- for key, path in ssm_config.items():
154
- if key not in config_dict:
155
- # missing or misspelled key
156
- missing_keys.append(key)
157
- continue
158
-
159
- if not path:
160
- # nothing configured for this key which is acceptable
161
- continue
162
-
163
- value = str(config_dict[key])
164
- id_name = f"{resource}{key.replace('_', '-')}-param"
165
-
166
- param = self.export_ssm_parameter(
167
- scope=scope,
168
- id=id_name,
169
- value=value,
170
- parameter_name=path,
171
- description=f"Exported {key} from {resource}",
172
- )
173
-
174
- if param:
175
- parameters[key] = param
176
-
177
- if missing_keys:
178
- logger.warning(f"Missing keys: {missing_keys}")
179
- # TODO : throw an exception here?
180
- message = (
181
- "🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨"
182
- f"\nThe following keys are missing from the config dictionary: {missing_keys}."
183
- f"\nThe accepted keys are: {list(config_dict.keys())}."
184
- "\nPlease check your configuration. Some keys may be misspelled."
185
- "\n🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨🚨"
186
- )
187
- print(message)
188
- logger.error(message.replace("\n", ""))
189
- exit(1)
190
-
191
- return parameters
192
-
193
- def export_resource_to_ssm(
194
- self,
195
- scope: Construct,
196
- resource_values: Dict[str, Any],
197
- config: Any, # Should be a BaseConfig subclass
198
- resource_name: str,
199
- resource_type: str = None,
200
- context: Dict[str, Any] = None,
201
- ) -> Dict[str, ssm.StringParameter]:
202
- """
203
- Export resource attributes to SSM Parameter Store based on configuration.
204
-
205
- This is a higher-level method that makes it clear we're exporting values.
206
- It first tries to use the ssm_exports property, then falls back to ssm_parameters.
207
-
208
- Args:
209
- scope: The CDK construct scope
210
- resource_values: Dictionary of resource values to export
211
- config: Configuration object with ssm_exports or ssm_parameters
212
- resource_name: Name of the resource (used as prefix for parameter IDs)
213
- resource_type: Type of the resource (e.g., 'vpc', 'security-group')
214
- context: Additional context variables for template formatting
215
-
216
- Returns:
217
- Dictionary of created SSM parameters
218
- """
219
- # First try the new ssm_exports property
220
- ssm_config = getattr(config, "ssm_exports", {})
221
-
222
- # If empty, fall back to the legacy ssm_parameters for backward compatibility
223
- if not ssm_config:
224
- ssm_config = getattr(config, "ssm_parameters", {})
225
-
226
- # Export all resources to SSM if paths are configured
227
- if ssm_config:
228
- logger.info(f"Exporting resources to SSM: {list(ssm_config.keys())}")
229
-
230
- # Format the SSM paths using the template if available
231
- formatted_ssm_config = {}
232
- for key, path in ssm_config.items():
233
- # Extract the attribute name from the key (remove _path suffix)
234
- attr_name = key[:-5] if key.endswith("_path") else key
235
-
236
- # If config has format_ssm_path method, use it to format the path
237
- if hasattr(config, "format_ssm_path") and resource_type:
238
- formatted_path = config.format_ssm_path(
239
- path=path,
240
- resource_type=resource_type,
241
- resource_name=resource_name,
242
- attribute=attr_name,
243
- context=context,
244
- )
245
- formatted_ssm_config[key] = formatted_path
246
- else:
247
- formatted_ssm_config[key] = path
248
-
249
- return self.export_ssm_parameters_from_config(
250
- scope=scope,
251
- config_dict=resource_values,
252
- ssm_config=formatted_ssm_config,
253
- resource=f"{resource_name}-",
254
- )
255
- else:
256
- logger.info(f"No SSM export paths configured for {resource_name} resources")
257
- logger.info("The following SSM exports are available for this resource: ")
258
- for key, item in resource_values.items():
259
- logger.info(f"{key}: {item}")
260
- return {}
261
-
262
- def import_resources_from_ssm(
263
- self,
264
- scope: Construct,
265
- config: Any, # Should be a BaseConfig subclass
266
- resource_name: str,
267
- resource_type: str = None,
268
- context: Dict[str, Any] = None,
269
- ) -> Dict[str, str]:
270
- """
271
- Import resource attributes from SSM Parameter Store based on configuration.
272
-
273
- This is a higher-level method that makes it clear we're importing values.
274
- It first tries to use the ssm_imports property, then falls back to ssm_parameters.
275
-
276
- Args:
277
- scope: The CDK construct scope
278
- config: Configuration object with ssm_imports or ssm_parameters
279
- resource_name: Name of the resource (used as prefix for parameter IDs)
280
- resource_type: Type of the resource (e.g., 'vpc', 'security-group')
281
- context: Additional context variables for template formatting
282
-
283
- Returns:
284
- Dictionary of imported SSM parameter values
285
- """
286
- # First try the new ssm_imports property
287
- ssm_config = getattr(config, "ssm_imports", {})
288
-
289
- # If empty, fall back to the legacy ssm_parameters for backward compatibility
290
- if not ssm_config:
291
- ssm_config = getattr(config, "ssm_parameters", {})
292
-
293
- imported_values = {}
294
-
295
- if ssm_config:
296
- logger.info(f"Importing resources from SSM: {list(ssm_config.keys())}")
297
- for key, path in ssm_config.items():
298
- if not path:
299
- continue
300
-
301
- # Extract the attribute name from the key (remove _path suffix)
302
- attr_name = key[:-5] if key.endswith("_path") else key
303
-
304
- # Format the SSM path using the template if available
305
- if hasattr(config, "format_ssm_path") and resource_type:
306
- formatted_path = config.format_ssm_path(
307
- path=path,
308
- resource_type=resource_type,
309
- resource_name=resource_name,
310
- attribute=attr_name,
311
- context=context,
312
- )
313
- else:
314
- formatted_path = path
315
-
316
- id_name = f"{resource_name}-{key.replace('_', '')}-Import"
317
- value = self.import_ssm_parameter(
318
- scope=scope, id=id_name, parameter_name=formatted_path
319
- )
320
-
321
- if value:
322
- # Remove _path suffix if present
323
- if key.endswith("_path"):
324
- key = key[:-5] # Remove _path suffix
325
- imported_values[key] = value
326
- else:
327
- logger.info(f"No SSM import paths configured for {resource_name} resources")
328
-
329
- return imported_values