@btc-embedded/cdk-extensions 0.22.21 → 0.22.23
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.
- package/.jsii +880 -182
- package/AGENTS.md +252 -0
- package/API.md +777 -52
- package/CHANGELOG.md +4 -0
- package/assets/cli/catnip.js +1 -1
- package/lib/constructs/EventPipe.js +1 -1
- package/lib/constructs/ExportedService.js +1 -1
- package/lib/constructs/S3Bucket.js +1 -1
- package/lib/constructs/SecureRestApi.js +1 -1
- package/lib/constructs/SecureRestApiV2.js +1 -1
- package/lib/constructs/api-keys/ApiKeyClientAuthorization.js +1 -1
- package/lib/constructs/api-keys/ApiKeyManagement.js +1 -1
- package/lib/constructs/api-keys/ApiKeyPreTokenHandler.js +1 -1
- package/lib/constructs/api-keys/ApiKeyStore.js +1 -1
- package/lib/extensions/ApiGatewayExtension.d.ts +17 -0
- package/lib/extensions/ApiGatewayExtension.js +31 -32
- package/lib/extensions/ApplicationContainer.js +1 -1
- package/lib/extensions/ApplicationLoadBalancerExtension.d.ts +16 -0
- package/lib/extensions/ApplicationLoadBalancerExtension.js +28 -28
- package/lib/extensions/ApplicationLoadBalancerExtensionV2.d.ts +27 -7
- package/lib/extensions/ApplicationLoadBalancerExtensionV2.js +16 -7
- package/lib/extensions/CloudMapExtension.d.ts +15 -0
- package/lib/extensions/CloudMapExtension.js +7 -3
- package/lib/extensions/DeactivatableServiceExtension.js +1 -1
- package/lib/extensions/DeploymentConfigExtension.js +1 -1
- package/lib/extensions/DocumentDbAccessExtension.d.ts +14 -2
- package/lib/extensions/DocumentDbAccessExtension.js +9 -3
- package/lib/extensions/DomainEventMessagingExtension.js +1 -1
- package/lib/extensions/EfsMountExtension.js +1 -1
- package/lib/extensions/ExtraContainerExtension.js +1 -1
- package/lib/extensions/HTTPApiExtension.d.ts +30 -1
- package/lib/extensions/HTTPApiExtension.js +14 -7
- package/lib/extensions/LogExtension.js +1 -1
- package/lib/extensions/ModifyContainerDefinitionExtension.js +1 -1
- package/lib/extensions/ModifyTaskDefinitionExtension.js +1 -1
- package/lib/extensions/OpenIdExtension.d.ts +14 -0
- package/lib/extensions/OpenIdExtension.js +9 -3
- package/lib/extensions/OpenTelemetryExtension.js +1 -1
- package/lib/extensions/PostgresDbAccessExtension.d.ts +30 -7
- package/lib/extensions/PostgresDbAccessExtension.js +24 -29
- package/lib/extensions/SharedVolumeExtension.js +1 -1
- package/lib/extensions/TcpKeepAliveExtension.js +1 -1
- package/lib/platform/ApiGateway.d.ts +29 -1
- package/lib/platform/ApiGateway.js +31 -2
- package/lib/platform/ApiGatewayVpcLink.js +2 -2
- package/lib/platform/ApplicationLoadBalancer.js +1 -1
- package/lib/platform/ApplicationLoadBalancerV2.js +2 -2
- package/lib/platform/AuroraPostgresDB.d.ts +63 -3
- package/lib/platform/AuroraPostgresDB.js +45 -7
- package/lib/platform/BTCLogGroup.js +1 -1
- package/lib/platform/CognitoUserPool.js +2 -2
- package/lib/platform/DefaultUserPoolClients.js +1 -1
- package/lib/platform/DocumentDB.d.ts +10 -2
- package/lib/platform/DocumentDB.js +12 -7
- package/lib/platform/EcsCluster.js +1 -1
- package/lib/platform/EfsFileSystem.js +1 -1
- package/lib/platform/HostedZone.js +1 -1
- package/lib/platform/PrivateDnsNamespace.js +1 -1
- package/lib/platform/ResourceServer.js +1 -1
- package/lib/platform/Vpc.js +1 -1
- package/lib/platform/VpcV2.js +1 -1
- package/lib/stacks/ApplicationStack.js +1 -1
- package/lib/utils/BasePlatformStackResolver.js +1 -1
- package/lib/utils/StackParameter.js +1 -1
- package/package.json +1 -1
package/AGENTS.md
ADDED
|
@@ -0,0 +1,252 @@
|
|
|
1
|
+
# AGENTS.md — Developer & Agentic Coding Guide
|
|
2
|
+
|
|
3
|
+
AWS CDK construct library (`@btc-embedded/cdk-extensions`). **Projen-managed**: never edit
|
|
4
|
+
`package.json`, `.gitignore`, `.eslintrc.json`, or `tsconfig.json` directly — modify
|
|
5
|
+
`.projenrc.ts` and run `npx projen` to regenerate them.
|
|
6
|
+
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
## Build / Lint / Test Commands
|
|
10
|
+
|
|
11
|
+
```bash
|
|
12
|
+
yarn build # Full pipeline: compile → bundle → test → package
|
|
13
|
+
yarn compile # jsii compilation only (produces lib/)
|
|
14
|
+
yarn typecheck # Type-check src + test without emitting (tsc --noEmit)
|
|
15
|
+
yarn test # Run all Jest tests
|
|
16
|
+
yarn test <pattern> # Run a single test file or name pattern (args forwarded to Jest)
|
|
17
|
+
yarn test:watch # Jest in watch mode
|
|
18
|
+
yarn eslint # Run ESLint interactively
|
|
19
|
+
yarn eslint:ci # Lint with CI reporter, fail on any warning
|
|
20
|
+
yarn bundle # Bundle all Lambda handlers + CLI with esbuild
|
|
21
|
+
yarn integ # Run integration test snapshots
|
|
22
|
+
yarn integ:update # Update integration test snapshots
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
### Running a Single Test
|
|
26
|
+
|
|
27
|
+
```bash
|
|
28
|
+
# By filename pattern
|
|
29
|
+
yarn test S3Bucket
|
|
30
|
+
|
|
31
|
+
# By path
|
|
32
|
+
yarn test test/constructs/S3Bucket.test.ts
|
|
33
|
+
|
|
34
|
+
# By test name pattern
|
|
35
|
+
yarn test S3Bucket --testNamePattern "developer stack"
|
|
36
|
+
```
|
|
37
|
+
|
|
38
|
+
Type errors in tests are caught by `yarn typecheck`, not by Jest itself
|
|
39
|
+
(`diagnostics: false` in ts-jest keeps test runs fast).
|
|
40
|
+
|
|
41
|
+
---
|
|
42
|
+
|
|
43
|
+
## Project Structure
|
|
44
|
+
|
|
45
|
+
```
|
|
46
|
+
src/
|
|
47
|
+
constructs/ Higher-level CDK constructs (S3Bucket, SecureRestApi, EventPipe, …)
|
|
48
|
+
extensions/ ECS ServiceExtension subclasses
|
|
49
|
+
platform/ Base-platform constructs (VPC, ECS cluster, Aurora, Cognito, …)
|
|
50
|
+
stacks/ ApplicationStack base class
|
|
51
|
+
utils/ StackParameter, BasePlatformStackResolver, helpers
|
|
52
|
+
cli/ catnip CLI (excluded from jsii; bundled with esbuild)
|
|
53
|
+
test/ Jest tests — mirrors src/ layout
|
|
54
|
+
assets/cli/ Bundled CLI binary
|
|
55
|
+
docs/ API docs, ADRs (docs/adr/), RFCs (docs/rfc/), construct docs
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
---
|
|
59
|
+
|
|
60
|
+
## Architecture Patterns
|
|
61
|
+
|
|
62
|
+
### Platform / Application Stack Split
|
|
63
|
+
|
|
64
|
+
- **Base Platform Stack** — deployed once per environment; holds shared infra (VPC, ECS
|
|
65
|
+
cluster, Aurora, Cognito, EFS, …). Lives in `src/platform/`.
|
|
66
|
+
- **Application Stack** — per-service stacks that import from the base platform. Constructs
|
|
67
|
+
live in `src/constructs/` and `src/extensions/`.
|
|
68
|
+
|
|
69
|
+
### `fromBasePlatform()` Pattern
|
|
70
|
+
|
|
71
|
+
Every platform construct exposes a static `fromBasePlatform(scope, id, basePlatformStackName?)`
|
|
72
|
+
that reconstructs the construct from CloudFormation `Fn::ImportValue` exports.
|
|
73
|
+
|
|
74
|
+
```typescript
|
|
75
|
+
static fromBasePlatform(scope: Construct, id: string, stackName?: string): IVpc {
|
|
76
|
+
class Import extends Construct implements IVpc {
|
|
77
|
+
readonly fqdn = Vpc.fqdnParameter.import(scope, stackName);
|
|
78
|
+
}
|
|
79
|
+
return new Import(scope, id);
|
|
80
|
+
}
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
### `StackParameter` — Cross-Stack References
|
|
84
|
+
|
|
85
|
+
Wraps `CfnOutput` (export) and `Fn.importValue` (import) with structured naming:
|
|
86
|
+
`{stackName}:{prefix}[-v{version}]:{key}` — e.g. `platform-stack:cognito-v2:user-pool-id`.
|
|
87
|
+
Declare as `private static readonly` on the owning class; call `.export(this, value)` in the
|
|
88
|
+
constructor and `.import(scope, stackName)` in `fromBasePlatform`.
|
|
89
|
+
|
|
90
|
+
### `BasePlatformStackResolver` — Context Propagation
|
|
91
|
+
|
|
92
|
+
`ApplicationStack` stores `basePlatformStackName` in CDK context under
|
|
93
|
+
`cdk-extensions:basePlatformStackName`. `BasePlatformStackResolver.resolve(scope, propsValue?)`
|
|
94
|
+
reads it as a fallback, so child constructs can omit the prop when inside an `ApplicationStack`.
|
|
95
|
+
|
|
96
|
+
### Abstract Base Class Pattern for Platform Constructs
|
|
97
|
+
|
|
98
|
+
1. `interface IFoo` — public contract
|
|
99
|
+
2. `abstract class FooBase extends Construct implements IFoo` — shared methods
|
|
100
|
+
3. `class Foo extends FooBase` — creates resources, exports parameters
|
|
101
|
+
4. `fromBasePlatform()` returns `new class Import extends FooBase { … }()` — imports values
|
|
102
|
+
|
|
103
|
+
### ECS Service Extensions
|
|
104
|
+
|
|
105
|
+
Extensions extend `ServiceExtension`. Key lifecycle hooks:
|
|
106
|
+
|
|
107
|
+
- `prehook(parent, scope)` — resolve references before service creation
|
|
108
|
+
- `addHooks()` — register `ContainerMutatingHook` instances
|
|
109
|
+
- `modifyServiceProps(props)` — modify ECS service props
|
|
110
|
+
- `useTaskDefinition(td)` — add containers, volumes, IAM policies
|
|
111
|
+
- `useService(service)` — post-creation wiring
|
|
112
|
+
|
|
113
|
+
---
|
|
114
|
+
|
|
115
|
+
## JSII Constraints
|
|
116
|
+
|
|
117
|
+
JSII enforces a strict subset of TypeScript. Violating these causes `jsii` compilation errors.
|
|
118
|
+
|
|
119
|
+
- **No** `Omit`, `Pick`, `Required`, `Partial`, complex type aliases, or property re-declaration
|
|
120
|
+
in interfaces
|
|
121
|
+
- **No** `require()` imports (use ES module `import`)
|
|
122
|
+
- Extend interfaces with `extends`; never re-declare inherited properties
|
|
123
|
+
|
|
124
|
+
**Workaround pattern:**
|
|
125
|
+
|
|
126
|
+
```typescript
|
|
127
|
+
// ✅ Correct: extend without re-declaring; validate at runtime
|
|
128
|
+
export interface MyProps extends BaseProps {}
|
|
129
|
+
|
|
130
|
+
constructor(props: MyProps) {
|
|
131
|
+
if (!props.optionalField) throw new Error("MyConstruct: 'optionalField' is required");
|
|
132
|
+
super({ cpu: props.cpu }); // No ! needed after validation
|
|
133
|
+
}
|
|
134
|
+
```
|
|
135
|
+
|
|
136
|
+
---
|
|
137
|
+
|
|
138
|
+
## Code Style Guidelines
|
|
139
|
+
|
|
140
|
+
### Naming
|
|
141
|
+
|
|
142
|
+
| Entity | Convention | Example |
|
|
143
|
+
| -------------------------- | ------------------------------------ | ----------------------------------------- |
|
|
144
|
+
| Classes / constructs | PascalCase | `ApplicationContainer`, `BTCLogGroup` |
|
|
145
|
+
| Construct logical IDs | PascalCase | `new Certificate(this, "Certificate", …)` |
|
|
146
|
+
| Props interfaces | `<Class>Props` | `EcsClusterProps` |
|
|
147
|
+
| Abstract base classes | `<Class>Base` | `CognitoUserPoolBase` |
|
|
148
|
+
| Import interfaces | `I<Class>` | `IVpc`, `IEfsFileSystem` |
|
|
149
|
+
| Enums | PascalCase name, UPPER_CASE values | `EfsAccessMode.READ_ONLY` |
|
|
150
|
+
| Module-level constants | `UPPER_CASE_SNAKE` | `BASE_PLATFORM_STACK_NAME_CONTEXT_KEY` |
|
|
151
|
+
| Functions / methods | camelCase | `kebabCase()`, `resolveBasePlatform()` |
|
|
152
|
+
| Resource names / log paths | kebab-case via `kebabCase()` utility | `/${app}/${kebabCase(id)}` |
|
|
153
|
+
|
|
154
|
+
### Imports
|
|
155
|
+
|
|
156
|
+
Order (enforced by `import/order` lint rule): **builtin → external**, alphabetized
|
|
157
|
+
ascending, case-insensitive. Use namespace imports (`import * as ecs from "aws-cdk-lib/aws-ecs"`)
|
|
158
|
+
when many items from a module are needed.
|
|
159
|
+
|
|
160
|
+
```typescript
|
|
161
|
+
import { Construct } from "constructs";
|
|
162
|
+
import * as cdk from "aws-cdk-lib";
|
|
163
|
+
import * as ecs from "aws-cdk-lib/aws-ecs";
|
|
164
|
+
import { ServiceExtension } from "@aws-cdk-containers/ecs-service-extensions";
|
|
165
|
+
|
|
166
|
+
import { StackParameter } from "../utils";
|
|
167
|
+
import { kebabCase } from "./common";
|
|
168
|
+
```
|
|
169
|
+
|
|
170
|
+
### Types and Interfaces
|
|
171
|
+
|
|
172
|
+
- Public API props: `interface` with `readonly` properties
|
|
173
|
+
- Explicit return types on all `public` methods; infer on private helpers
|
|
174
|
+
- Prefer `??` (nullish coalescing) and ternaries over `if/else` for simple defaults
|
|
175
|
+
- No `!` non-null assertions after runtime validation (TypeScript control flow is trusted)
|
|
176
|
+
|
|
177
|
+
### Error Handling
|
|
178
|
+
|
|
179
|
+
```typescript
|
|
180
|
+
// Constructor validation format
|
|
181
|
+
if (!props.cpu) throw new Error("ApplicationContainer: 'cpu' is required");
|
|
182
|
+
if (!/^[a-z][a-z0-9-]+$/.test(prefix)) {
|
|
183
|
+
throw new Error(`prefix '${prefix}' must be kebab-case (like 'foo-bar')`);
|
|
184
|
+
}
|
|
185
|
+
```
|
|
186
|
+
|
|
187
|
+
### Member Ordering (enforced by ESLint)
|
|
188
|
+
|
|
189
|
+
`public static` fields → `public static` methods → `protected static` → `private static` →
|
|
190
|
+
instance fields → constructor → instance methods.
|
|
191
|
+
|
|
192
|
+
### Formatting (Prettier defaults via eslint-plugin-prettier)
|
|
193
|
+
|
|
194
|
+
2-space indent, double quotes, trailing commas, semicolons. Formatting errors surface as ESLint
|
|
195
|
+
errors — run `yarn eslint` to auto-fix.
|
|
196
|
+
|
|
197
|
+
### General
|
|
198
|
+
|
|
199
|
+
- `const` for immutable bindings; `let` where reassignment is needed
|
|
200
|
+
- Spread for prop merging: `{ ...props, override: value }`
|
|
201
|
+
- Minimal inline comments — only for non-obvious behaviour
|
|
202
|
+
- No `require()` calls anywhere in `src/` (enforced by `@typescript-eslint/no-require-imports`)
|
|
203
|
+
|
|
204
|
+
---
|
|
205
|
+
|
|
206
|
+
## Testing Philosophy
|
|
207
|
+
|
|
208
|
+
- Use `Template.fromStack(stack)` for CloudFormation resource assertions
|
|
209
|
+
- One general usage test + targeted corner cases — avoid redundant coverage
|
|
210
|
+
- Remove tests that are fully covered by a higher-level test
|
|
211
|
+
- **Workflow**: write comprehensive tests first → get approval → implement → simplify tests
|
|
212
|
+
as needed
|
|
213
|
+
|
|
214
|
+
```typescript
|
|
215
|
+
import { App, Stack } from "aws-cdk-lib";
|
|
216
|
+
import { Template } from "aws-cdk-lib/assertions";
|
|
217
|
+
|
|
218
|
+
test("creates S3 bucket with versioning", () => {
|
|
219
|
+
const app = new App();
|
|
220
|
+
const stack = new Stack(app, "TestStack");
|
|
221
|
+
new S3Bucket(stack, "Bucket", { versioned: true });
|
|
222
|
+
const template = Template.fromStack(stack);
|
|
223
|
+
template.hasResourceProperties("AWS::S3::Bucket", {
|
|
224
|
+
VersioningConfiguration: { Status: "Enabled" },
|
|
225
|
+
});
|
|
226
|
+
});
|
|
227
|
+
```
|
|
228
|
+
|
|
229
|
+
---
|
|
230
|
+
|
|
231
|
+
## Local Testing with yalc
|
|
232
|
+
|
|
233
|
+
```bash
|
|
234
|
+
# In cdk-extensions — publish locally
|
|
235
|
+
yarn build && npx yalc publish
|
|
236
|
+
|
|
237
|
+
# In consumer project — link
|
|
238
|
+
npx yalc add @btc-embedded/cdk-extensions && yarn install
|
|
239
|
+
|
|
240
|
+
# After further changes in cdk-extensions
|
|
241
|
+
yarn build && npx yalc push
|
|
242
|
+
```
|
|
243
|
+
|
|
244
|
+
---
|
|
245
|
+
|
|
246
|
+
## Commit Format
|
|
247
|
+
|
|
248
|
+
```
|
|
249
|
+
<type>: <description>
|
|
250
|
+
```
|
|
251
|
+
|
|
252
|
+
Types: `feat`, `feat!` (breaking), `fix`, `refactor`, `chore`, `misc`, `test`
|