cdk-cost-analyzer 0.1.1

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 (228) hide show
  1. package/.cdk-cost-analyzer-cache/metadata.json +12 -0
  2. package/.gitlab-ci.yml +214 -0
  3. package/.husky/pre-commit +12 -0
  4. package/.kiro/hooks/accessibility-audit.kiro.hook +18 -0
  5. package/.kiro/hooks/api-schema-validation.kiro.hook +21 -0
  6. package/.kiro/hooks/auto-test-on-save.kiro.hook +19 -0
  7. package/.kiro/hooks/cdk-synth-on-change.kiro.hook +20 -0
  8. package/.kiro/hooks/code-coverage-check.kiro.hook +14 -0
  9. package/.kiro/hooks/commit-message-helper.kiro.hook +14 -0
  10. package/.kiro/hooks/dependency-update-check.kiro.hook +14 -0
  11. package/.kiro/hooks/env-file-validation.kiro.hook +18 -0
  12. package/.kiro/hooks/lint-and-format-on-save.kiro.hook +21 -0
  13. package/.kiro/hooks/mcp-config-validation.kiro.hook +17 -0
  14. package/.kiro/hooks/mcp-server-test.kiro.hook +14 -0
  15. package/.kiro/hooks/performance-analysis.kiro.hook +14 -0
  16. package/.kiro/hooks/readme-spell-check.kiro.hook +14 -0
  17. package/.kiro/hooks/security-scan-on-dependency-change.kiro.hook +21 -0
  18. package/.kiro/hooks/translation-update.kiro.hook +18 -0
  19. package/.kiro/hooks/update-documentation.kiro.hook +18 -0
  20. package/.kiro/settings/mcp.json +20 -0
  21. package/.kiro/specs/cdk-cost-analyzer/design.md +620 -0
  22. package/.kiro/specs/cdk-cost-analyzer/requirements.md +183 -0
  23. package/.kiro/specs/cdk-cost-analyzer/tasks.md +357 -0
  24. package/.kiro/specs/github-actions-ci/design.md +281 -0
  25. package/.kiro/specs/github-actions-ci/requirements.md +86 -0
  26. package/.kiro/specs/github-actions-ci/tasks.md +115 -0
  27. package/.kiro/specs/nlb-calculator-test-coverage/design.md +190 -0
  28. package/.kiro/specs/nlb-calculator-test-coverage/requirements.md +84 -0
  29. package/.kiro/specs/nlb-calculator-test-coverage/tasks.md +150 -0
  30. package/.kiro/specs/production-readiness/design.md +1213 -0
  31. package/.kiro/specs/production-readiness/requirements.md +312 -0
  32. package/.kiro/specs/production-readiness/tasks.md +269 -0
  33. package/.kiro/specs/repository-cleanup/design.md +283 -0
  34. package/.kiro/specs/repository-cleanup/requirements.md +74 -0
  35. package/.kiro/specs/repository-cleanup/tasks.md +64 -0
  36. package/.kiro/steering/aws-cli-best-practices.md +41 -0
  37. package/.kiro/steering/cdk-best-practices.md +49 -0
  38. package/.kiro/steering/development-standards.md +54 -0
  39. package/.kiro/steering/docker-best-practices.md +34 -0
  40. package/.kiro/steering/documentation-style.md +151 -0
  41. package/.kiro/steering/git-best-practices.md +37 -0
  42. package/.kiro/steering/mcp-best-practices.md +95 -0
  43. package/.kiro/steering/python-best-practices.md +48 -0
  44. package/.kiro/steering/react-best-practices.md +44 -0
  45. package/.kiro/steering/security-best-practices.md +41 -0
  46. package/.kiro/steering/testing-best-practices.md +59 -0
  47. package/.kiro/steering/typescript-best-practices.md +40 -0
  48. package/CHANGELOG.md +49 -0
  49. package/CONTRIBUTING.md +258 -0
  50. package/LICENSE +19 -0
  51. package/README.md +480 -0
  52. package/SECURITY.md +117 -0
  53. package/dist/api/index.d.ts +11 -0
  54. package/dist/api/index.js +65 -0
  55. package/dist/api/types.d.ts +15 -0
  56. package/dist/api/types.js +3 -0
  57. package/dist/cli/index.d.ts +2 -0
  58. package/dist/cli/index.js +262 -0
  59. package/dist/config/ConfigManager.d.ts +40 -0
  60. package/dist/config/ConfigManager.js +238 -0
  61. package/dist/config/index.d.ts +2 -0
  62. package/dist/config/index.js +19 -0
  63. package/dist/config/types.d.ts +72 -0
  64. package/dist/config/types.js +15 -0
  65. package/dist/diff/DiffEngine.d.ts +7 -0
  66. package/dist/diff/DiffEngine.js +73 -0
  67. package/dist/diff/index.d.ts +2 -0
  68. package/dist/diff/index.js +21 -0
  69. package/dist/diff/types.d.ts +20 -0
  70. package/dist/diff/types.js +3 -0
  71. package/dist/integrations/GitLabIntegration.d.ts +7 -0
  72. package/dist/integrations/GitLabIntegration.js +45 -0
  73. package/dist/integrations/index.d.ts +2 -0
  74. package/dist/integrations/index.js +21 -0
  75. package/dist/integrations/types.d.ts +11 -0
  76. package/dist/integrations/types.js +13 -0
  77. package/dist/parser/TemplateParser.d.ts +8 -0
  78. package/dist/parser/TemplateParser.js +75 -0
  79. package/dist/parser/index.d.ts +2 -0
  80. package/dist/parser/index.js +22 -0
  81. package/dist/parser/types.d.ts +30 -0
  82. package/dist/parser/types.js +3 -0
  83. package/dist/pipeline/PipelineOrchestrator.d.ts +23 -0
  84. package/dist/pipeline/PipelineOrchestrator.js +191 -0
  85. package/dist/pipeline/index.d.ts +2 -0
  86. package/dist/pipeline/index.js +19 -0
  87. package/dist/pipeline/types.d.ts +41 -0
  88. package/dist/pipeline/types.js +13 -0
  89. package/dist/pricing/CacheManager.d.ts +75 -0
  90. package/dist/pricing/CacheManager.js +195 -0
  91. package/dist/pricing/PricingClient.d.ts +17 -0
  92. package/dist/pricing/PricingClient.js +122 -0
  93. package/dist/pricing/PricingService.d.ts +16 -0
  94. package/dist/pricing/PricingService.js +149 -0
  95. package/dist/pricing/calculators/ALBCalculator.d.ts +16 -0
  96. package/dist/pricing/calculators/ALBCalculator.js +163 -0
  97. package/dist/pricing/calculators/APIGatewayCalculator.d.ts +10 -0
  98. package/dist/pricing/calculators/APIGatewayCalculator.js +177 -0
  99. package/dist/pricing/calculators/CloudFrontCalculator.d.ts +59 -0
  100. package/dist/pricing/calculators/CloudFrontCalculator.js +151 -0
  101. package/dist/pricing/calculators/DynamoDBCalculator.d.ts +9 -0
  102. package/dist/pricing/calculators/DynamoDBCalculator.js +146 -0
  103. package/dist/pricing/calculators/EC2Calculator.d.ts +7 -0
  104. package/dist/pricing/calculators/EC2Calculator.js +80 -0
  105. package/dist/pricing/calculators/ECSCalculator.d.ts +9 -0
  106. package/dist/pricing/calculators/ECSCalculator.js +116 -0
  107. package/dist/pricing/calculators/ElastiCacheCalculator.d.ts +8 -0
  108. package/dist/pricing/calculators/ElastiCacheCalculator.js +106 -0
  109. package/dist/pricing/calculators/LambdaCalculator.d.ts +13 -0
  110. package/dist/pricing/calculators/LambdaCalculator.js +111 -0
  111. package/dist/pricing/calculators/NLBCalculator.d.ts +16 -0
  112. package/dist/pricing/calculators/NLBCalculator.js +138 -0
  113. package/dist/pricing/calculators/NatGatewayCalculator.d.ts +12 -0
  114. package/dist/pricing/calculators/NatGatewayCalculator.js +116 -0
  115. package/dist/pricing/calculators/RDSCalculator.d.ts +9 -0
  116. package/dist/pricing/calculators/RDSCalculator.js +103 -0
  117. package/dist/pricing/calculators/S3Calculator.d.ts +8 -0
  118. package/dist/pricing/calculators/S3Calculator.js +68 -0
  119. package/dist/pricing/calculators/VPCEndpointCalculator.d.ts +12 -0
  120. package/dist/pricing/calculators/VPCEndpointCalculator.js +129 -0
  121. package/dist/pricing/index.d.ts +10 -0
  122. package/dist/pricing/index.js +37 -0
  123. package/dist/pricing/types.d.ts +53 -0
  124. package/dist/pricing/types.js +22 -0
  125. package/dist/releasetag.txt +1 -0
  126. package/dist/reporter/Reporter.d.ts +18 -0
  127. package/dist/reporter/Reporter.js +412 -0
  128. package/dist/reporter/index.d.ts +2 -0
  129. package/dist/reporter/index.js +21 -0
  130. package/dist/reporter/types.d.ts +72 -0
  131. package/dist/reporter/types.js +3 -0
  132. package/dist/synthesis/SynthesisOrchestrator.d.ts +26 -0
  133. package/dist/synthesis/SynthesisOrchestrator.js +243 -0
  134. package/dist/synthesis/index.d.ts +2 -0
  135. package/dist/synthesis/index.js +19 -0
  136. package/dist/synthesis/types.d.ts +17 -0
  137. package/dist/synthesis/types.js +13 -0
  138. package/dist/threshold/ThresholdEnforcer.d.ts +29 -0
  139. package/dist/threshold/ThresholdEnforcer.js +143 -0
  140. package/dist/threshold/index.d.ts +2 -0
  141. package/dist/threshold/index.js +19 -0
  142. package/dist/threshold/types.d.ts +15 -0
  143. package/dist/threshold/types.js +17 -0
  144. package/docs/CALCULATORS.md +820 -0
  145. package/docs/CI_CD.md +608 -0
  146. package/docs/CONFIGURATION.md +407 -0
  147. package/docs/DEVELOPMENT.md +387 -0
  148. package/docs/RELEASE.md +223 -0
  149. package/docs/TROUBLESHOOTING.md +847 -0
  150. package/examples/.cdk-cost-analyzer.yml +85 -0
  151. package/examples/.gitlab-ci.yml +125 -0
  152. package/examples/api-usage.js +26 -0
  153. package/examples/complex/base.json +16 -0
  154. package/examples/complex/target.json +29 -0
  155. package/examples/monorepo/.gitlab-ci.yml +251 -0
  156. package/examples/monorepo/README.md +341 -0
  157. package/examples/monorepo/package.json +27 -0
  158. package/examples/monorepo/packages/backend-infra/.cdk-cost-analyzer.yml +34 -0
  159. package/examples/monorepo/packages/backend-infra/bin/app.ts +16 -0
  160. package/examples/monorepo/packages/backend-infra/cdk.json +7 -0
  161. package/examples/monorepo/packages/backend-infra/lib/backend-stack.ts +128 -0
  162. package/examples/monorepo/packages/backend-infra/package.json +30 -0
  163. package/examples/monorepo/packages/backend-infra/tsconfig.json +11 -0
  164. package/examples/monorepo/packages/data-infra/.cdk-cost-analyzer.yml +38 -0
  165. package/examples/monorepo/packages/data-infra/bin/app.ts +16 -0
  166. package/examples/monorepo/packages/data-infra/cdk.json +7 -0
  167. package/examples/monorepo/packages/data-infra/lib/data-stack.ts +121 -0
  168. package/examples/monorepo/packages/data-infra/package.json +30 -0
  169. package/examples/monorepo/packages/data-infra/tsconfig.json +11 -0
  170. package/examples/monorepo/packages/frontend-infra/.cdk-cost-analyzer.yml +31 -0
  171. package/examples/monorepo/packages/frontend-infra/bin/app.ts +16 -0
  172. package/examples/monorepo/packages/frontend-infra/cdk.json +7 -0
  173. package/examples/monorepo/packages/frontend-infra/lib/frontend-stack.ts +60 -0
  174. package/examples/monorepo/packages/frontend-infra/package.json +30 -0
  175. package/examples/monorepo/packages/frontend-infra/tsconfig.json +11 -0
  176. package/examples/monorepo/tsconfig.json +35 -0
  177. package/examples/multi-stack/.cdk-cost-analyzer.yml +72 -0
  178. package/examples/multi-stack/.gitlab-ci.yml +184 -0
  179. package/examples/multi-stack/README.md +279 -0
  180. package/examples/multi-stack/bin/app.ts +36 -0
  181. package/examples/multi-stack/cdk.json +72 -0
  182. package/examples/multi-stack/lib/compute-stack.ts +128 -0
  183. package/examples/multi-stack/lib/networking-stack.ts +69 -0
  184. package/examples/multi-stack/lib/storage-stack.ts +141 -0
  185. package/examples/multi-stack/package-lock.json +4437 -0
  186. package/examples/multi-stack/package.json +42 -0
  187. package/examples/multi-stack/tsconfig.json +34 -0
  188. package/examples/simple/base.json +8 -0
  189. package/examples/simple/target.json +14 -0
  190. package/examples/single-stack/.NVP +0 -0
  191. package/examples/single-stack/.cdk-cost-analyzer.yml +52 -0
  192. package/examples/single-stack/.gitlab-ci.yml +126 -0
  193. package/examples/single-stack/README.md +184 -0
  194. package/examples/single-stack/UeK +0 -0
  195. package/examples/single-stack/bin/app.ts +16 -0
  196. package/examples/single-stack/cdk.json +72 -0
  197. package/examples/single-stack/lib/infrastructure-stack.ts +119 -0
  198. package/examples/single-stack/package-lock.json +4443 -0
  199. package/examples/single-stack/package.json +38 -0
  200. package/examples/single-stack/tsconfig.json +34 -0
  201. package/package.json +139 -0
  202. package/test-cdk-project/README-COMPUTE.md +141 -0
  203. package/test-cdk-project/README.md +95 -0
  204. package/test-cdk-project/app-with-compute.js +102 -0
  205. package/test-cdk-project/app.js +81 -0
  206. package/test-cdk-project/cdk-compute.json +3 -0
  207. package/test-cdk-project/cdk.context.json +7 -0
  208. package/test-cdk-project/cdk.json +3 -0
  209. package/test-cdk-project/cdk.out/TestStack.assets.json +21 -0
  210. package/test-cdk-project/cdk.out/TestStack.template.json +115 -0
  211. package/test-cdk-project/cdk.out/cdk.out +1 -0
  212. package/test-cdk-project/cdk.out/manifest.json +503 -0
  213. package/test-cdk-project/cdk.out/tree.json +1 -0
  214. package/test-cdk-project/cdk.out.base/TestStack.assets.json +21 -0
  215. package/test-cdk-project/cdk.out.base/TestStack.template.json +115 -0
  216. package/test-cdk-project/cdk.out.base/cdk.out +1 -0
  217. package/test-cdk-project/cdk.out.base/manifest.json +503 -0
  218. package/test-cdk-project/cdk.out.base/tree.json +1 -0
  219. package/test-cdk-project/cdk.out.target/TestStack.assets.json +21 -0
  220. package/test-cdk-project/cdk.out.target/TestStack.template.json +183 -0
  221. package/test-cdk-project/cdk.out.target/cdk.out +1 -0
  222. package/test-cdk-project/cdk.out.target/manifest.json +521 -0
  223. package/test-cdk-project/cdk.out.target/tree.json +1 -0
  224. package/test-cdk-project/package-lock.json +422 -0
  225. package/test-cdk-project/package.json +17 -0
  226. package/tools/workflows/README.md +102 -0
  227. package/tools/workflows/validate-workflows.js +109 -0
  228. package/tools/workflows/workflow-utils.ts +181 -0
@@ -0,0 +1,341 @@
1
+ # Monorepo CDK Cost Analyzer Example
2
+
3
+ This example demonstrates how to integrate CDK Cost Analyzer into a monorepo structure with multiple independent CDK applications.
4
+
5
+ ## Project Structure
6
+
7
+ ```
8
+ monorepo/
9
+ ├── packages/
10
+ │ ├── frontend-infra/ # Frontend infrastructure (S3, CloudFront)
11
+ │ │ ├── bin/
12
+ │ │ ├── lib/
13
+ │ │ ├── .cdk-cost-analyzer.yml
14
+ │ │ ├── cdk.json
15
+ │ │ └── package.json
16
+ │ ├── backend-infra/ # Backend infrastructure (Lambda, API Gateway)
17
+ │ │ ├── bin/
18
+ │ │ ├── lib/
19
+ │ │ ├── .cdk-cost-analyzer.yml
20
+ │ │ ├── cdk.json
21
+ │ │ └── package.json
22
+ │ └── data-infra/ # Data infrastructure (RDS, DynamoDB)
23
+ │ ├── bin/
24
+ │ ├── lib/
25
+ │ ├── .cdk-cost-analyzer.yml
26
+ │ ├── cdk.json
27
+ │ └── package.json
28
+ ├── .gitlab-ci.yml # GitLab CI pipeline with parallel analysis
29
+ ├── package.json # Root package.json for workspace
30
+ └── README.md # This file
31
+ ```
32
+
33
+ ## Architecture Overview
34
+
35
+ This monorepo contains three independent CDK applications:
36
+
37
+ ### Frontend Infrastructure
38
+ - **Amazon S3**: Static website hosting
39
+ - **Amazon CloudFront**: Content delivery network
40
+ - **AWS Certificate Manager**: SSL/TLS certificates
41
+
42
+ ### Backend Infrastructure
43
+ - **AWS Lambda**: Serverless API functions
44
+ - **Amazon API Gateway**: REST API endpoints
45
+ - **Amazon DynamoDB**: NoSQL database
46
+
47
+ ### Data Infrastructure
48
+ - **Amazon RDS**: PostgreSQL database
49
+ - **Amazon ElastiCache**: Redis cache
50
+ - **AWS Backup**: Automated backup solution
51
+
52
+ ## Why Monorepo?
53
+
54
+ Monorepo architectures provide several benefits:
55
+
56
+ - **Code Sharing**: Share common constructs and utilities across applications
57
+ - **Atomic Changes**: Update multiple applications in a single commit
58
+ - **Consistent Tooling**: Unified build and deployment processes
59
+ - **Independent Deployment**: Each application can be deployed separately
60
+ - **Team Autonomy**: Different teams can own different applications
61
+
62
+ ## Prerequisites
63
+
64
+ - Node.js 18 or later
65
+ - AWS CDK CLI: `npm install -g aws-cdk`
66
+ - AWS account with appropriate credentials
67
+ - GitLab repository with CI/CD enabled
68
+
69
+ ## Setup Instructions
70
+
71
+ ### 1. Install Dependencies
72
+
73
+ ```bash
74
+ cd examples/monorepo
75
+ npm install
76
+ ```
77
+
78
+ This installs dependencies for all packages in the workspace.
79
+
80
+ ### 2. Configure AWS Credentials
81
+
82
+ For local development:
83
+
84
+ ```bash
85
+ export AWS_ACCESS_KEY_ID=your-access-key
86
+ export AWS_SECRET_ACCESS_KEY=your-secret-key
87
+ export AWS_REGION=us-east-1
88
+ ```
89
+
90
+ For GitLab CI, configure these as CI/CD variables in your GitLab project settings.
91
+
92
+ ### 3. Bootstrap CDK (First Time Only)
93
+
94
+ ```bash
95
+ cdk bootstrap aws://ACCOUNT-ID/REGION
96
+ ```
97
+
98
+ ### 4. Review Configuration
99
+
100
+ Each package has its own `.cdk-cost-analyzer.yml` with application-specific thresholds and assumptions.
101
+
102
+ ## Local Development
103
+
104
+ ### Work with Specific Application
105
+
106
+ ```bash
107
+ # Frontend infrastructure
108
+ cd packages/frontend-infra
109
+ cdk synth
110
+ cdk deploy
111
+
112
+ # Backend infrastructure
113
+ cd packages/backend-infra
114
+ cdk synth
115
+ cdk deploy
116
+
117
+ # Data infrastructure
118
+ cd packages/data-infra
119
+ cdk synth
120
+ cdk deploy
121
+ ```
122
+
123
+ ### Run Cost Analysis for Specific Application
124
+
125
+ ```bash
126
+ # Install cost analyzer
127
+ npm install -g cdk-cost-analyzer
128
+
129
+ # Analyze frontend infrastructure
130
+ cd packages/frontend-infra
131
+ cdk-cost-analyzer pipeline \
132
+ --base-branch main \
133
+ --target-branch feature/my-changes \
134
+ --region us-east-1
135
+
136
+ # Analyze backend infrastructure
137
+ cd packages/backend-infra
138
+ cdk-cost-analyzer pipeline \
139
+ --base-branch main \
140
+ --target-branch feature/my-changes \
141
+ --region us-east-1
142
+ ```
143
+
144
+ ## GitLab CI/CD Integration
145
+
146
+ The `.gitlab-ci.yml` file configures parallel cost analysis for all applications in the monorepo.
147
+
148
+ ### Pipeline Stages
149
+
150
+ 1. **Build**: Install dependencies for all packages
151
+ 2. **Test**: Run tests for all packages in parallel
152
+ 3. **Cost Analysis**: Analyze cost changes for each application in parallel
153
+ 4. **Deploy**: Deploy applications to AWS
154
+
155
+ ### Parallel Cost Analysis
156
+
157
+ The pipeline runs cost analysis for each application independently and in parallel:
158
+
159
+ ```yaml
160
+ cost-analysis:frontend:
161
+ # Analyzes frontend infrastructure changes
162
+
163
+ cost-analysis:backend:
164
+ # Analyzes backend infrastructure changes
165
+
166
+ cost-analysis:data:
167
+ # Analyzes data infrastructure changes
168
+ ```
169
+
170
+ Each analysis job:
171
+ - Has its own cost thresholds
172
+ - Posts separate comments to merge requests
173
+ - Can fail independently without blocking other analyses
174
+
175
+ ### Viewing Cost Reports
176
+
177
+ Each application posts its own cost analysis comment to merge requests:
178
+
179
+ ```
180
+ Frontend Infrastructure Cost Analysis
181
+ ======================================
182
+ Total Cost Delta: +$25.00/month
183
+ - CloudFront: +$20.00/month
184
+ - S3: +$5.00/month
185
+
186
+ Backend Infrastructure Cost Analysis
187
+ ====================================
188
+ Total Cost Delta: +$45.00/month
189
+ - Lambda: +$30.00/month
190
+ - API Gateway: +$15.00/month
191
+
192
+ Data Infrastructure Cost Analysis
193
+ ==================================
194
+ Total Cost Delta: +$80.00/month
195
+ - RDS: +$60.00/month
196
+ - ElastiCache: +$20.00/month
197
+ ```
198
+
199
+ ## Application-Specific Configuration
200
+
201
+ Each application has its own configuration file with appropriate thresholds:
202
+
203
+ ### Frontend Infrastructure
204
+ ```yaml
205
+ thresholds:
206
+ default:
207
+ warning: 30
208
+ error: 100
209
+ ```
210
+
211
+ ### Backend Infrastructure
212
+ ```yaml
213
+ thresholds:
214
+ default:
215
+ warning: 50
216
+ error: 200
217
+ ```
218
+
219
+ ### Data Infrastructure
220
+ ```yaml
221
+ thresholds:
222
+ default:
223
+ warning: 100
224
+ error: 500
225
+ ```
226
+
227
+ ## Workspace Management
228
+
229
+ This monorepo uses npm workspaces for dependency management:
230
+
231
+ ```json
232
+ {
233
+ "workspaces": [
234
+ "packages/*"
235
+ ]
236
+ }
237
+ ```
238
+
239
+ Benefits:
240
+ - Single `node_modules` at root
241
+ - Shared dependencies across packages
242
+ - Faster installation
243
+ - Consistent versions
244
+
245
+ ## Troubleshooting
246
+
247
+ ### Pipeline Runs All Analyses Even for Single Application Changes
248
+
249
+ **Issue**: All cost analysis jobs run even when only one application changed
250
+
251
+ **Solution**: This is intentional for simplicity. To optimize:
252
+
253
+ 1. Use GitLab CI rules to detect changed files
254
+ 2. Skip analysis jobs for unchanged applications
255
+ 3. Example:
256
+
257
+ ```yaml
258
+ cost-analysis:frontend:
259
+ rules:
260
+ - changes:
261
+ - packages/frontend-infra/**/*
262
+ ```
263
+
264
+ ### Different Applications Have Different Cost Thresholds
265
+
266
+ **Issue**: Need different thresholds for different applications
267
+
268
+ **Solution**: Each application has its own `.cdk-cost-analyzer.yml` file. Configure thresholds independently:
269
+
270
+ ```yaml
271
+ # packages/frontend-infra/.cdk-cost-analyzer.yml
272
+ thresholds:
273
+ default:
274
+ warning: 30
275
+ error: 100
276
+
277
+ # packages/data-infra/.cdk-cost-analyzer.yml
278
+ thresholds:
279
+ default:
280
+ warning: 100
281
+ error: 500
282
+ ```
283
+
284
+ ### Dependency Conflicts Between Applications
285
+
286
+ **Issue**: Different applications need different versions of the same dependency
287
+
288
+ **Solution**: Use workspace overrides in root `package.json`:
289
+
290
+ ```json
291
+ {
292
+ "overrides": {
293
+ "aws-cdk-lib": "^2.118.0"
294
+ }
295
+ }
296
+ ```
297
+
298
+ ### Cost Analysis Takes Too Long
299
+
300
+ **Issue**: Parallel analysis still takes too long
301
+
302
+ **Solution**:
303
+ 1. Enable pricing cache across all jobs
304
+ 2. Use GitLab CI cache with shared key
305
+ 3. Consider running analysis only on merge requests, not all commits
306
+
307
+ ## Best Practices
308
+
309
+ ### Monorepo Organization
310
+
311
+ - **Keep applications independent**: Minimize cross-application dependencies
312
+ - **Share common code**: Create shared packages for reusable constructs
313
+ - **Consistent naming**: Use consistent naming conventions across applications
314
+ - **Clear ownership**: Document which team owns which application
315
+
316
+ ### Cost Management
317
+
318
+ - **Set appropriate thresholds**: Different applications have different cost profiles
319
+ - **Review regularly**: Periodically review and adjust thresholds
320
+ - **Track trends**: Monitor cost changes over time per application
321
+ - **Optimize independently**: Each application can be optimized separately
322
+
323
+ ### Deployment Strategy
324
+
325
+ - **Deploy independently**: Each application can be deployed on its own schedule
326
+ - **Test thoroughly**: Test each application independently before deployment
327
+ - **Use environments**: Maintain separate dev/staging/prod environments per application
328
+ - **Coordinate dependencies**: If applications depend on each other, coordinate deployments
329
+
330
+ ## Next Steps
331
+
332
+ - Review [Configuration Documentation](../../docs/CONFIGURATION.md) for advanced options
333
+ - Explore [Single-Stack Example](../single-stack/) for simpler projects
334
+ - Check [Troubleshooting Guide](../../docs/TROUBLESHOOTING.md) for common issues
335
+
336
+ ## Additional Resources
337
+
338
+ - [npm Workspaces Documentation](https://docs.npmjs.com/cli/v8/using-npm/workspaces)
339
+ - [AWS CDK Documentation](https://docs.aws.amazon.com/cdk/)
340
+ - [CDK Cost Analyzer Documentation](../../README.md)
341
+ - [GitLab CI/CD Documentation](https://docs.gitlab.com/ee/ci/)
@@ -0,0 +1,27 @@
1
+ {
2
+ "name": "cdk-cost-analyzer-monorepo-example",
3
+ "version": "1.0.0",
4
+ "description": "Monorepo CDK application example with cost analysis",
5
+ "private": true,
6
+ "workspaces": [
7
+ "packages/*"
8
+ ],
9
+ "scripts": {
10
+ "build": "npm run build --workspaces",
11
+ "test": "npm test --workspaces",
12
+ "clean": "npm run clean --workspaces"
13
+ },
14
+ "keywords": [
15
+ "aws",
16
+ "cdk",
17
+ "monorepo",
18
+ "cost-analysis",
19
+ "example"
20
+ ],
21
+ "author": "ANWB",
22
+ "license": "MIT",
23
+ "devDependencies": {
24
+ "@types/node": "^22.10.2",
25
+ "typescript": "^5.7.2"
26
+ }
27
+ }
@@ -0,0 +1,34 @@
1
+ # CDK Cost Analyzer Configuration for Backend Infrastructure
2
+
3
+ thresholds:
4
+ default:
5
+ warning: 50 # USD per month
6
+ error: 200 # USD per month
7
+
8
+ usageAssumptions:
9
+ lambda:
10
+ invocationsPerMonth: 2000000
11
+ averageDurationMs: 300
12
+ memoryMB: 512
13
+
14
+ apiGateway:
15
+ requestsPerMonth: 2000000
16
+
17
+ dynamodb:
18
+ readCapacityUnits: 10
19
+ writeCapacityUnits: 10
20
+ storageGB: 25
21
+
22
+ synthesis:
23
+ appPath: .
24
+ outputPath: cdk.out
25
+
26
+ exclusions:
27
+ resourceTypes:
28
+ - AWS::IAM::Role
29
+ - AWS::IAM::Policy
30
+ - AWS::Logs::LogGroup
31
+
32
+ cache:
33
+ enabled: true
34
+ durationHours: 24
@@ -0,0 +1,16 @@
1
+ #!/usr/bin/env node
2
+ import 'source-map-support/register';
3
+ import * as cdk from 'aws-cdk-lib';
4
+ import { BackendStack } from '../lib/backend-stack';
5
+
6
+ const app = new cdk.App();
7
+
8
+ new BackendStack(app, 'BackendStack', {
9
+ env: {
10
+ account: process.env.CDK_DEFAULT_ACCOUNT,
11
+ region: process.env.CDK_DEFAULT_REGION || 'us-east-1',
12
+ },
13
+ description: 'Monorepo example - Backend infrastructure (Lambda, API Gateway, DynamoDB)',
14
+ });
15
+
16
+ app.synth();
@@ -0,0 +1,7 @@
1
+ {
2
+ "app": "npx ts-node --prefer-ts-exts bin/app.ts",
3
+ "context": {
4
+ "@aws-cdk/core:enablePartitionLiterals": true,
5
+ "@aws-cdk/aws-lambda:recognizeLayerVersion": true
6
+ }
7
+ }
@@ -0,0 +1,128 @@
1
+ import * as cdk from 'aws-cdk-lib';
2
+ import * as lambda from 'aws-cdk-lib/aws-lambda';
3
+ import * as dynamodb from 'aws-cdk-lib/aws-dynamodb';
4
+ import * as apigateway from 'aws-cdk-lib/aws-apigateway';
5
+ import { Construct } from 'constructs';
6
+
7
+ /**
8
+ * Backend infrastructure stack
9
+ *
10
+ * Creates Lambda functions, API Gateway, and DynamoDB table
11
+ */
12
+ export class BackendStack extends cdk.Stack {
13
+ constructor(scope: Construct, id: string, props?: cdk.StackProps) {
14
+ super(scope, id, props);
15
+
16
+ // DynamoDB table
17
+ const table = new dynamodb.Table(this, 'DataTable', {
18
+ tableName: 'backend-data',
19
+ partitionKey: {
20
+ name: 'id',
21
+ type: dynamodb.AttributeType.STRING,
22
+ },
23
+ sortKey: {
24
+ name: 'timestamp',
25
+ type: dynamodb.AttributeType.NUMBER,
26
+ },
27
+ billingMode: dynamodb.BillingMode.PROVISIONED,
28
+ readCapacity: 10,
29
+ writeCapacity: 10,
30
+ removalPolicy: cdk.RemovalPolicy.DESTROY,
31
+ });
32
+
33
+ // Lambda function for API handler
34
+ const apiHandler = new lambda.Function(this, 'ApiHandler', {
35
+ functionName: 'backend-api-handler',
36
+ runtime: lambda.Runtime.NODEJS_18_X,
37
+ handler: 'index.handler',
38
+ code: lambda.Code.fromInline(`
39
+ const { DynamoDBClient, PutItemCommand, QueryCommand } = require('@aws-sdk/client-dynamodb');
40
+ const client = new DynamoDBClient({});
41
+
42
+ exports.handler = async (event) => {
43
+ const tableName = process.env.TABLE_NAME;
44
+
45
+ try {
46
+ if (event.httpMethod === 'POST') {
47
+ const body = JSON.parse(event.body);
48
+ await client.send(new PutItemCommand({
49
+ TableName: tableName,
50
+ Item: {
51
+ id: { S: body.id },
52
+ timestamp: { N: Date.now().toString() },
53
+ data: { S: JSON.stringify(body.data) }
54
+ }
55
+ }));
56
+ return {
57
+ statusCode: 201,
58
+ headers: { 'Content-Type': 'application/json' },
59
+ body: JSON.stringify({ message: 'Item created' })
60
+ };
61
+ } else {
62
+ const result = await client.send(new QueryCommand({
63
+ TableName: tableName,
64
+ KeyConditionExpression: 'id = :id',
65
+ ExpressionAttributeValues: { ':id': { S: event.pathParameters.id } }
66
+ }));
67
+ return {
68
+ statusCode: 200,
69
+ headers: { 'Content-Type': 'application/json' },
70
+ body: JSON.stringify(result.Items)
71
+ };
72
+ }
73
+ } catch (error) {
74
+ return {
75
+ statusCode: 500,
76
+ headers: { 'Content-Type': 'application/json' },
77
+ body: JSON.stringify({ error: error.message })
78
+ };
79
+ }
80
+ };
81
+ `),
82
+ memorySize: 512,
83
+ timeout: cdk.Duration.seconds(30),
84
+ environment: {
85
+ TABLE_NAME: table.tableName,
86
+ },
87
+ });
88
+
89
+ // Grant Lambda permissions to access DynamoDB
90
+ table.grantReadWriteData(apiHandler);
91
+
92
+ // API Gateway
93
+ const api = new apigateway.RestApi(this, 'Api', {
94
+ restApiName: 'Backend API',
95
+ description: 'Backend REST API',
96
+ deployOptions: {
97
+ stageName: 'prod',
98
+ throttlingRateLimit: 100,
99
+ throttlingBurstLimit: 200,
100
+ },
101
+ });
102
+
103
+ // API Gateway integration
104
+ const integration = new apigateway.LambdaIntegration(apiHandler);
105
+
106
+ const items = api.root.addResource('items');
107
+ items.addMethod('POST', integration);
108
+
109
+ const item = items.addResource('{id}');
110
+ item.addMethod('GET', integration);
111
+
112
+ // Stack outputs
113
+ new cdk.CfnOutput(this, 'ApiUrl', {
114
+ value: api.url,
115
+ description: 'API Gateway endpoint URL',
116
+ });
117
+
118
+ new cdk.CfnOutput(this, 'TableName', {
119
+ value: table.tableName,
120
+ description: 'DynamoDB table name',
121
+ });
122
+
123
+ new cdk.CfnOutput(this, 'FunctionName', {
124
+ value: apiHandler.functionName,
125
+ description: 'Lambda function name',
126
+ });
127
+ }
128
+ }
@@ -0,0 +1,30 @@
1
+ {
2
+ "name": "backend-infra",
3
+ "version": "1.0.0",
4
+ "description": "Backend infrastructure CDK application",
5
+ "bin": {
6
+ "backend-infra": "bin/app.js"
7
+ },
8
+ "scripts": {
9
+ "build": "tsc",
10
+ "watch": "tsc -w",
11
+ "test": "jest",
12
+ "cdk": "cdk",
13
+ "synth": "cdk synth",
14
+ "deploy": "cdk deploy",
15
+ "clean": "rm -rf cdk.out node_modules"
16
+ },
17
+ "devDependencies": {
18
+ "@types/jest": "^29.5.14",
19
+ "@types/node": "^22.10.2",
20
+ "aws-cdk": "^2.232.1",
21
+ "jest": "^29.7.0",
22
+ "ts-jest": "^29.2.5",
23
+ "ts-node": "^10.9.2",
24
+ "typescript": "^5.7.2"
25
+ },
26
+ "dependencies": {
27
+ "aws-cdk-lib": "^2.232.1",
28
+ "constructs": "^10.4.2"
29
+ }
30
+ }
@@ -0,0 +1,11 @@
1
+ {
2
+ "extends": "../../../tsconfig.json",
3
+ "compilerOptions": {
4
+ "outDir": "dist",
5
+ "rootDir": "."
6
+ },
7
+ "exclude": [
8
+ "node_modules",
9
+ "cdk.out"
10
+ ]
11
+ }
@@ -0,0 +1,38 @@
1
+ # CDK Cost Analyzer Configuration for Data Infrastructure
2
+
3
+ thresholds:
4
+ default:
5
+ warning: 100 # USD per month
6
+ error: 500 # USD per month
7
+
8
+ usageAssumptions:
9
+ rds:
10
+ instanceClass: db.t3.medium
11
+ storageGB: 100
12
+ backupRetentionDays: 7
13
+ multiAZ: false
14
+
15
+ elasticache:
16
+ nodeType: cache.t3.micro
17
+ numNodes: 2
18
+ engineType: redis
19
+
20
+ s3:
21
+ storageGB: 1000
22
+ getRequests: 500000
23
+ putRequests: 50000
24
+ dataTransferGB: 200
25
+
26
+ synthesis:
27
+ appPath: .
28
+ outputPath: cdk.out
29
+
30
+ exclusions:
31
+ resourceTypes:
32
+ - AWS::IAM::Role
33
+ - AWS::IAM::Policy
34
+ - AWS::EC2::SecurityGroup
35
+
36
+ cache:
37
+ enabled: true
38
+ durationHours: 24
@@ -0,0 +1,16 @@
1
+ #!/usr/bin/env node
2
+ import 'source-map-support/register';
3
+ import * as cdk from 'aws-cdk-lib';
4
+ import { DataStack } from '../lib/data-stack';
5
+
6
+ const app = new cdk.App();
7
+
8
+ new DataStack(app, 'DataStack', {
9
+ env: {
10
+ account: process.env.CDK_DEFAULT_ACCOUNT,
11
+ region: process.env.CDK_DEFAULT_REGION || 'us-east-1',
12
+ },
13
+ description: 'Monorepo example - Data infrastructure (RDS, ElastiCache, S3)',
14
+ });
15
+
16
+ app.synth();
@@ -0,0 +1,7 @@
1
+ {
2
+ "app": "npx ts-node --prefer-ts-exts bin/app.ts",
3
+ "context": {
4
+ "@aws-cdk/core:enablePartitionLiterals": true,
5
+ "@aws-cdk/aws-lambda:recognizeLayerVersion": true
6
+ }
7
+ }