@fjall/components-infrastructure 0.96.0 → 0.99.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.
- package/dist/lib/app.d.ts +68 -1
- package/dist/lib/app.js +113 -4
- package/dist/lib/config/aws/__t17fixture.d.ts +1 -0
- package/dist/lib/config/aws/__t17fixture.js +3 -0
- package/dist/lib/config/aws/__t17fixtureType.d.ts +2 -0
- package/dist/lib/config/aws/__t17fixtureType.js +1 -0
- package/dist/lib/config/aws/alarmTopic.js +8 -4
- package/dist/lib/config/aws/cloudTrail.js +1 -1
- package/dist/lib/config/aws/disasterRecovery.js +11 -16
- package/dist/lib/config/aws/ecrDefaultImage.d.ts +0 -1
- package/dist/lib/config/aws/ecrDefaultImage.js +13 -23
- package/dist/lib/config/aws/identityCenter.d.ts +10 -3
- package/dist/lib/config/aws/identityCenter.js +101 -37
- package/dist/lib/config/aws/identityCenterGroupMembership.js +8 -2
- package/dist/lib/config/aws/identityCenterMembership.d.ts +11 -0
- package/dist/lib/config/aws/identityCenterMembership.js +61 -0
- package/dist/lib/config/aws/index.d.ts +1 -1
- package/dist/lib/config/aws/index.js +1 -1
- package/dist/lib/config/aws/ipam.js +6 -11
- package/dist/lib/config/aws/oidcConnector.js +5 -1
- package/dist/lib/config/aws/scpPreset.js +4 -1
- package/dist/lib/patterns/aws/_eslint_test_tmp/leak.d.ts +1 -0
- package/dist/lib/patterns/aws/_eslint_test_tmp/leak.js +4 -0
- package/dist/lib/patterns/aws/account.js +2 -4
- package/dist/lib/patterns/aws/apexDomainPattern.js +10 -10
- package/dist/lib/patterns/aws/bastionFactory.d.ts +10 -0
- package/dist/lib/patterns/aws/bastionFactory.js +29 -0
- package/dist/lib/patterns/aws/buildkite.d.ts +2 -2
- package/dist/lib/patterns/aws/buildkite.js +51 -97
- package/dist/lib/patterns/aws/cdn.js +1 -1
- package/dist/lib/patterns/aws/clickhouseDatabase.d.ts +172 -0
- package/dist/lib/patterns/aws/clickhouseDatabase.js +600 -0
- package/dist/lib/patterns/aws/compute.d.ts +4 -6
- package/dist/lib/patterns/aws/compute.js +7 -13
- package/dist/lib/patterns/aws/computeEcs.d.ts +93 -5
- package/dist/lib/patterns/aws/computeEcs.js +867 -37
- package/dist/lib/patterns/aws/computeEcsTypes.d.ts +528 -25
- package/dist/lib/patterns/aws/computeEcsTypes.js +10 -0
- package/dist/lib/patterns/aws/computeLambda.d.ts +0 -5
- package/dist/lib/patterns/aws/computeLambda.js +1 -2
- package/dist/lib/patterns/aws/database.d.ts +50 -8
- package/dist/lib/patterns/aws/database.js +183 -27
- package/dist/lib/patterns/aws/domain.js +6 -4
- package/dist/lib/patterns/aws/index.d.ts +1 -0
- package/dist/lib/patterns/aws/index.js +1 -0
- package/dist/lib/patterns/aws/interfaces/compute.d.ts +7 -1
- package/dist/lib/patterns/aws/interfaces/database.d.ts +187 -8
- package/dist/lib/patterns/aws/interfaces/database.js +17 -3
- package/dist/lib/patterns/aws/interfaces/index.d.ts +2 -1
- package/dist/lib/patterns/aws/interfaces/index.js +3 -1
- package/dist/lib/patterns/aws/interfaces/messaging.d.ts +7 -0
- package/dist/lib/patterns/aws/interfaces/migrationContributor.d.ts +47 -0
- package/dist/lib/patterns/aws/interfaces/migrationContributor.js +9 -0
- package/dist/lib/patterns/aws/messaging.d.ts +66 -10
- package/dist/lib/patterns/aws/messaging.js +115 -20
- package/dist/lib/patterns/aws/network.js +16 -7
- package/dist/lib/patterns/aws/organisation.d.ts +4 -0
- package/dist/lib/patterns/aws/organisation.js +22 -4
- package/dist/lib/patterns/aws/storage.d.ts +1 -2
- package/dist/lib/patterns/aws/storage.js +3 -2
- package/dist/lib/patterns/aws/vpcPeer.js +3 -1
- package/dist/lib/resources/aws/analytics/clickhouse.js +18 -9
- package/dist/lib/resources/aws/analytics/clickhouseAlarms.d.ts +24 -9
- package/dist/lib/resources/aws/analytics/clickhouseAlarms.js +61 -10
- package/dist/lib/resources/aws/analytics/clickhouseConstants.d.ts +3 -3
- package/dist/lib/resources/aws/analytics/clickhouseConstants.js +3 -3
- package/dist/lib/resources/aws/analytics/clickhouseTypes.d.ts +7 -1
- package/dist/lib/resources/aws/analytics/clickhouseUserData.d.ts +1 -1
- package/dist/lib/resources/aws/analytics/clickhouseUserData.js +53 -3
- package/dist/lib/resources/aws/base/awsStack.js +4 -2
- package/dist/lib/resources/aws/compute/__tmp__/regression-shape.d.ts +2 -0
- package/dist/lib/resources/aws/compute/__tmp__/regression-shape.js +11 -0
- package/dist/lib/resources/aws/compute/asgInlineLifecycleHook.d.ts +52 -0
- package/dist/lib/resources/aws/compute/asgInlineLifecycleHook.js +60 -0
- package/dist/lib/resources/aws/compute/blockDeviceVolume.d.ts +8 -0
- package/dist/lib/resources/aws/compute/blockDeviceVolume.js +10 -0
- package/dist/lib/resources/aws/compute/ec2.d.ts +132 -12
- package/dist/lib/resources/aws/compute/ec2.js +163 -23
- package/dist/lib/resources/aws/compute/ec2GracefulTerminationHandler.d.ts +41 -0
- package/dist/lib/resources/aws/compute/ec2GracefulTerminationHandler.js +194 -0
- package/dist/lib/resources/aws/compute/ec2GracefulTerminationLambda.source.cjs +458 -0
- package/dist/lib/resources/aws/compute/ecs.d.ts +27 -1
- package/dist/lib/resources/aws/compute/ecs.js +42 -2
- package/dist/lib/resources/aws/compute/ecsConstants.d.ts +9 -0
- package/dist/lib/resources/aws/compute/ecsConstants.js +16 -0
- package/dist/lib/resources/aws/compute/ecsImages.js +32 -20
- package/dist/lib/resources/aws/compute/ecsLifecycleHookMigration.d.ts +96 -0
- package/dist/lib/resources/aws/compute/ecsLifecycleHookMigration.js +113 -0
- package/dist/lib/resources/aws/compute/ecsNetworking.d.ts +2 -1
- package/dist/lib/resources/aws/compute/ecsNetworking.js +18 -6
- package/dist/lib/resources/aws/compute/ecsServiceFactory.d.ts +13 -4
- package/dist/lib/resources/aws/compute/ecsServiceFactory.js +155 -33
- package/dist/lib/resources/aws/compute/ecsTaskDefinition.d.ts +31 -1
- package/dist/lib/resources/aws/compute/ecsTaskDefinition.js +102 -6
- package/dist/lib/resources/aws/compute/ecsTypes.d.ts +173 -13
- package/dist/lib/resources/aws/compute/ecsValidation.d.ts +9 -0
- package/dist/lib/resources/aws/compute/ecsValidation.js +63 -0
- package/dist/lib/resources/aws/compute/index.d.ts +2 -0
- package/dist/lib/resources/aws/compute/index.js +2 -0
- package/dist/lib/resources/aws/compute/lambda.d.ts +7 -13
- package/dist/lib/resources/aws/compute/lambda.js +30 -38
- package/dist/lib/resources/aws/compute/lifecycleHookLambda.source.cjs +192 -0
- package/dist/lib/resources/aws/compute/persistentDataVolume.d.ts +104 -0
- package/dist/lib/resources/aws/compute/persistentDataVolume.js +245 -0
- package/dist/lib/resources/aws/compute/persistentDataVolumeLambda.source.cjs +398 -0
- package/dist/lib/resources/aws/compute/samApplication.d.ts +15 -0
- package/dist/lib/resources/aws/compute/samApplication.js +27 -0
- package/dist/lib/resources/aws/database/clickhouseConstants.d.ts +159 -0
- package/dist/lib/resources/aws/database/clickhouseConstants.js +181 -0
- package/dist/lib/resources/aws/database/clickhouseSchemas.d.ts +71 -0
- package/dist/lib/resources/aws/database/clickhouseSchemas.js +157 -0
- package/dist/lib/resources/aws/database/clickhouseSecurityGroup.d.ts +14 -0
- package/dist/lib/resources/aws/database/clickhouseSecurityGroup.js +23 -0
- package/dist/lib/resources/aws/database/clickhouseUserData.d.ts +69 -0
- package/dist/lib/resources/aws/database/clickhouseUserData.js +371 -0
- package/dist/lib/resources/aws/database/clickhouseXmlRenderer.d.ts +56 -0
- package/dist/lib/resources/aws/database/clickhouseXmlRenderer.js +112 -0
- package/dist/lib/resources/aws/database/rdsAurora.d.ts +8 -1
- package/dist/lib/resources/aws/database/rdsAurora.js +42 -32
- package/dist/lib/resources/aws/database/rdsAuroraGlobal.d.ts +15 -2
- package/dist/lib/resources/aws/database/rdsAuroraGlobal.js +39 -43
- package/dist/lib/resources/aws/database/rdsDefaults.d.ts +6 -0
- package/dist/lib/resources/aws/database/rdsDefaults.js +7 -1
- package/dist/lib/resources/aws/database/rdsHelpers.d.ts +3 -3
- package/dist/lib/resources/aws/database/rdsHelpers.js +1 -0
- package/dist/lib/resources/aws/database/rdsInstance.d.ts +8 -1
- package/dist/lib/resources/aws/database/rdsInstance.js +51 -34
- package/dist/lib/resources/aws/database/rdsProxyOutput.d.ts +1 -1
- package/dist/lib/resources/aws/database/rdsProxyOutput.js +1 -1
- package/dist/lib/resources/aws/iam/delegationRole.js +1 -1
- package/dist/lib/resources/aws/iam/identityCenter/groupMembership.d.ts +9 -0
- package/dist/lib/resources/aws/iam/identityCenter/groupMembership.js +12 -0
- package/dist/lib/resources/aws/iam/identityCenter/index.d.ts +1 -0
- package/dist/lib/resources/aws/iam/identityCenter/index.js +1 -0
- package/dist/lib/resources/aws/iam/identityCenter/permissionSet.d.ts +1 -0
- package/dist/lib/resources/aws/iam/identityCenter/permissionSet.js +1 -0
- package/dist/lib/resources/aws/logging/logGroup.d.ts +0 -8
- package/dist/lib/resources/aws/logging/logGroup.js +0 -11
- package/dist/lib/resources/aws/messaging/defaultEventBus.d.ts +7 -0
- package/dist/lib/resources/aws/messaging/defaultEventBus.js +21 -0
- package/dist/lib/resources/aws/messaging/eventBridgeRule.d.ts +96 -0
- package/dist/lib/resources/aws/messaging/eventBridgeRule.js +110 -0
- package/dist/lib/resources/aws/messaging/eventTargets.d.ts +84 -0
- package/dist/lib/resources/aws/messaging/eventTargets.js +152 -0
- package/dist/lib/resources/aws/messaging/eventbridge.d.ts +25 -2
- package/dist/lib/resources/aws/messaging/eventbridge.js +22 -10
- package/dist/lib/resources/aws/messaging/index.d.ts +5 -0
- package/dist/lib/resources/aws/messaging/index.js +2 -0
- package/dist/lib/resources/aws/messaging/schedule.d.ts +118 -0
- package/dist/lib/resources/aws/messaging/schedule.js +64 -0
- package/dist/lib/resources/aws/messaging/sns.d.ts +2 -1
- package/dist/lib/resources/aws/messaging/sqs.d.ts +2 -1
- package/dist/lib/resources/aws/messaging/subscription.d.ts +112 -0
- package/dist/lib/resources/aws/messaging/subscription.js +67 -0
- package/dist/lib/resources/aws/messaging/utils.d.ts +6 -0
- package/dist/lib/resources/aws/messaging/utils.js +10 -0
- package/dist/lib/resources/aws/monitoring/clickhouseAlarms.d.ts +60 -0
- package/dist/lib/resources/aws/monitoring/clickhouseAlarms.js +139 -0
- package/dist/lib/resources/aws/monitoring/index.d.ts +2 -0
- package/dist/lib/resources/aws/monitoring/index.js +2 -0
- package/dist/lib/resources/aws/monitoring/scheduleAlarms.d.ts +47 -0
- package/dist/lib/resources/aws/monitoring/scheduleAlarms.js +106 -0
- package/dist/lib/resources/aws/networking/crossAccountDelegationRecord.js +6 -4
- package/dist/lib/resources/aws/networking/crossAccountReturnRoutes.js +17 -13
- package/dist/lib/resources/aws/networking/dnsRecord/dnsRecordBase.js +7 -5
- package/dist/lib/resources/aws/networking/domainCertificate.d.ts +2 -2
- package/dist/lib/resources/aws/networking/domainCertificate.js +6 -4
- package/dist/lib/resources/aws/networking/hostedZone.js +6 -5
- package/dist/lib/resources/aws/networking/serviceDiscovery.d.ts +96 -0
- package/dist/lib/resources/aws/networking/serviceDiscovery.js +96 -0
- package/dist/lib/resources/aws/networking/vpc.d.ts +4 -1
- package/dist/lib/resources/aws/networking/vpc.js +4 -1
- package/dist/lib/resources/aws/networking/vpcPeeringConnection.js +21 -3
- package/dist/lib/resources/aws/organisation/costAllocationTagActivator.d.ts +16 -5
- package/dist/lib/resources/aws/organisation/costAllocationTagActivator.js +17 -3
- package/dist/lib/resources/aws/organisation/index.d.ts +1 -1
- package/dist/lib/resources/aws/organisation/organisationPolicy.d.ts +2 -0
- package/dist/lib/resources/aws/organisation/organisationPolicy.js +3 -2
- package/dist/lib/resources/aws/secrets/secret.d.ts +7 -0
- package/dist/lib/resources/aws/secrets/secret.js +4 -3
- package/dist/lib/resources/aws/storage/bucketDeployment.d.ts +16 -0
- package/dist/lib/resources/aws/storage/bucketDeployment.js +17 -0
- package/dist/lib/resources/aws/storage/ecr.js +5 -5
- package/dist/lib/resources/aws/storage/index.d.ts +1 -0
- package/dist/lib/resources/aws/storage/index.js +1 -0
- package/dist/lib/resources/aws/storage/s3.js +10 -3
- package/dist/lib/resources/aws/utilities/customResource.js +18 -9
- package/dist/lib/synth_dump.d.ts +1 -0
- package/dist/lib/synth_dump.js +42 -0
- package/dist/lib/utils/cdkContext.d.ts +2 -0
- package/dist/lib/utils/cdkContext.js +4 -2
- package/dist/lib/utils/connections.js +6 -0
- package/dist/lib/utils/connector.d.ts +12 -0
- package/dist/lib/utils/costAllocationTags.d.ts +9 -0
- package/dist/lib/utils/costAllocationTags.js +11 -1
- package/dist/lib/utils/databaseTypes.d.ts +14 -0
- package/dist/lib/utils/getConfig.d.ts +2 -0
- package/dist/lib/utils/getConfig.js +2 -0
- package/dist/lib/utils/index.d.ts +1 -0
- package/dist/lib/utils/index.js +1 -0
- package/dist/lib/utils/manifestWriter.d.ts +6 -89
- package/dist/lib/utils/manifestWriter.js +36 -23
- package/dist/lib/utils/migrationVersionResolvers.d.ts +2 -0
- package/dist/lib/utils/migrationVersionResolvers.js +2 -0
- package/dist/lib/utils/orgConfigParser.js +2 -1
- package/dist/lib/utils/resolveAlertsTopic.d.ts +14 -0
- package/dist/lib/utils/resolveAlertsTopic.js +30 -0
- package/dist/lib/utils/validationLogger.js +6 -3
- package/package.json +22 -19
package/dist/lib/app.d.ts
CHANGED
|
@@ -10,7 +10,11 @@ import { type INetworkProps, type Network } from "./patterns/aws/network.js";
|
|
|
10
10
|
import { type Cdn } from "./patterns/aws/cdn.js";
|
|
11
11
|
import { type VpcPeer } from "./patterns/aws/vpcPeer.js";
|
|
12
12
|
import { type VpcPeerAccepter } from "./patterns/aws/vpcPeerAccepter.js";
|
|
13
|
-
import { type AnyMessaging } from "./patterns/aws/messaging.js";
|
|
13
|
+
import { type AnyMessaging, type EventBusMessaging } from "./patterns/aws/messaging.js";
|
|
14
|
+
import { Schedule, type ScheduleProps } from "./resources/aws/messaging/schedule.js";
|
|
15
|
+
import { type RemovalPolicyString } from "./resources/aws/messaging/utils.js";
|
|
16
|
+
import { type ServiceRegistrationProps } from "./resources/aws/networking/serviceDiscovery.js";
|
|
17
|
+
import { type IPrivateDnsNamespace, type IService } from "aws-cdk-lib/aws-servicediscovery";
|
|
14
18
|
import { type AnyCompute } from "./patterns/aws/compute.js";
|
|
15
19
|
import { type Storage, type StorageFactoryFn } from "./patterns/aws/storage.js";
|
|
16
20
|
import { type AnyPattern } from "./patterns/aws/pattern.js";
|
|
@@ -63,6 +67,20 @@ export interface IAppOptions {
|
|
|
63
67
|
tunnel?: {
|
|
64
68
|
instanceType?: string;
|
|
65
69
|
} | boolean;
|
|
70
|
+
/**
|
|
71
|
+
* EventBridge default-bus override (T7a, D2 + D17).
|
|
72
|
+
*
|
|
73
|
+
* - `name?` overrides the AWS `EventBus.Name` (defaults to the app name).
|
|
74
|
+
* - `removalPolicy?` overrides the env-resolved default. Default resolves
|
|
75
|
+
* via `env({ default: "DESTROY", production: "RETAIN" })` per D17 — NOT
|
|
76
|
+
* `process.env.NODE_ENV` (which is not set during CDK synth in Fjall's
|
|
77
|
+
* deployment paths). The shape is the normalised string union per
|
|
78
|
+
* D18(d), NOT the raw CDK `RemovalPolicy` enum.
|
|
79
|
+
*/
|
|
80
|
+
eventBus?: {
|
|
81
|
+
name?: string;
|
|
82
|
+
removalPolicy?: RemovalPolicyString;
|
|
83
|
+
};
|
|
66
84
|
}
|
|
67
85
|
/**
|
|
68
86
|
* The basic corner-stone of all Fjall-hosted applications.
|
|
@@ -78,6 +96,9 @@ export declare class App extends CdkApp {
|
|
|
78
96
|
private vpc?;
|
|
79
97
|
private additionalVpcs;
|
|
80
98
|
private defaultEcr;
|
|
99
|
+
private defaultEventBus?;
|
|
100
|
+
private eventBusOverride?;
|
|
101
|
+
private defaultNamespace?;
|
|
81
102
|
private defaultAuditRole;
|
|
82
103
|
private auditRoleExternalId?;
|
|
83
104
|
private bastion?;
|
|
@@ -148,6 +169,37 @@ export declare class App extends CdkApp {
|
|
|
148
169
|
getVpc(name?: string): IVpc;
|
|
149
170
|
getVpcNames(): string[];
|
|
150
171
|
getDefaultContainerRegistry(): Ecr;
|
|
172
|
+
/**
|
|
173
|
+
* Lazy getter for the per-app default custom EventBridge bus (D2).
|
|
174
|
+
*
|
|
175
|
+
* Buses are recreatable in non-prod; the env-resolved default keeps prod
|
|
176
|
+
* history. The override (`App.getApp({ eventBus: { name?, removalPolicy? } })`)
|
|
177
|
+
* is consulted first; absent override falls back to the app name and the
|
|
178
|
+
* `env({ default: "DESTROY", production: "RETAIN" })` resolution per D17.
|
|
179
|
+
* NODE_ENV is not consulted — it is not set during CDK synth in Fjall's
|
|
180
|
+
* deployment paths.
|
|
181
|
+
*/
|
|
182
|
+
getEventBus(): EventBusMessaging;
|
|
183
|
+
/**
|
|
184
|
+
* Lazy getter for the per-app Cloud Map private DNS namespace (D7 + D29 of
|
|
185
|
+
* the ClickHouse Database Factory promotion design).
|
|
186
|
+
*
|
|
187
|
+
* The namespace is constructed in the network stack on first call and
|
|
188
|
+
* reused thereafter — `app.getNamespace() === app.getNamespace()`. Default
|
|
189
|
+
* name is `${toKebab(appName)}.local` per the implementation-defined
|
|
190
|
+
* derivation rule; v1 has no override config option (D29). Returns the
|
|
191
|
+
* `IPrivateDnsNamespace` interface per D18(a), never the concrete class.
|
|
192
|
+
*/
|
|
193
|
+
getNamespace(): IPrivateDnsNamespace;
|
|
194
|
+
/**
|
|
195
|
+
* Register a Cloud Map service against the per-app namespace. Lazily creates
|
|
196
|
+
* the namespace on first call (same construct as `getNamespace()`) and
|
|
197
|
+
* delegates to the `ServiceDiscoveryNamespace` wrapper's `registerService`
|
|
198
|
+
* — keeping both halves of Cloud Map (namespace + services) routed through
|
|
199
|
+
* the wrapper layer per § Wrapper Routing Discipline.
|
|
200
|
+
*/
|
|
201
|
+
registerService(props: ServiceRegistrationProps): IService;
|
|
202
|
+
private ensureNamespace;
|
|
151
203
|
/**
|
|
152
204
|
* Create a cross-account audit role in the Network stack that allows
|
|
153
205
|
* the Fjall platform to use CloudQuery for comprehensive AWS resource auditing.
|
|
@@ -288,6 +340,21 @@ export declare class App extends CdkApp {
|
|
|
288
340
|
* }));
|
|
289
341
|
*/
|
|
290
342
|
addMessaging<T extends AnyMessaging & Construct>(fn: (app: App, scope: Construct) => T): T;
|
|
343
|
+
/**
|
|
344
|
+
* Register an EventBridge schedule against a Fjall wrapper target.
|
|
345
|
+
*
|
|
346
|
+
* Defaults to the messaging stack; set `props.stackPlacement = "compute"`
|
|
347
|
+
* when the schedule's target lives in the compute stack and cross-stack
|
|
348
|
+
* output churn is undesired. `applicationId` is threaded automatically
|
|
349
|
+
* from `app.getName()` for alarm webhook routing per D13.
|
|
350
|
+
*
|
|
351
|
+
* @example
|
|
352
|
+
* app.addSchedule("MetricsCollection", {
|
|
353
|
+
* schedule: "rate(5 minutes)",
|
|
354
|
+
* target: notificationsQueue
|
|
355
|
+
* });
|
|
356
|
+
*/
|
|
357
|
+
addSchedule(id: string, props: Omit<ScheduleProps, "applicationId">): Schedule;
|
|
291
358
|
/**
|
|
292
359
|
* Add a high-level infrastructure pattern to the application.
|
|
293
360
|
*
|
package/dist/lib/app.js
CHANGED
|
@@ -1,9 +1,13 @@
|
|
|
1
1
|
import { App as CdkApp, Aspects, Tags } from "aws-cdk-lib";
|
|
2
|
+
import { maskSensitiveOutput } from "@fjall/util";
|
|
2
3
|
import { Vpc } from "./resources/aws/networking/vpc.js";
|
|
3
|
-
import { createBastion } from "./
|
|
4
|
+
import { createBastion } from "./patterns/aws/bastionFactory.js";
|
|
4
5
|
import { AwsStack } from "./resources/index.js";
|
|
5
6
|
import { EcrFactory } from "./resources/aws/storage/ecr.js";
|
|
6
7
|
import { NetworkFactory } from "./patterns/aws/network.js";
|
|
8
|
+
import { MessagingFactory } from "./patterns/aws/messaging.js";
|
|
9
|
+
import { Schedule } from "./resources/aws/messaging/schedule.js";
|
|
10
|
+
import { ServiceDiscoveryNamespace } from "./resources/aws/networking/serviceDiscovery.js";
|
|
7
11
|
import { StandardTagsAspect } from "./utils/standardTagsAspect.js";
|
|
8
12
|
import { BACKUP_TIER_TAG_KEY, BACKUP_TIER_TAG_MAP } from "./utils/backupTierMapping.js";
|
|
9
13
|
import { randomBytes } from "crypto";
|
|
@@ -28,6 +32,9 @@ export class App extends CdkApp {
|
|
|
28
32
|
vpc;
|
|
29
33
|
additionalVpcs = new Map();
|
|
30
34
|
defaultEcr;
|
|
35
|
+
defaultEventBus;
|
|
36
|
+
eventBusOverride;
|
|
37
|
+
defaultNamespace;
|
|
31
38
|
defaultAuditRole;
|
|
32
39
|
auditRoleExternalId;
|
|
33
40
|
bastion;
|
|
@@ -59,6 +66,9 @@ export class App extends CdkApp {
|
|
|
59
66
|
if (options?.tunnel) {
|
|
60
67
|
this.initialiseTunnel(options.tunnel);
|
|
61
68
|
}
|
|
69
|
+
if (options?.eventBus !== undefined) {
|
|
70
|
+
this.eventBusOverride = options.eventBus;
|
|
71
|
+
}
|
|
62
72
|
}
|
|
63
73
|
applyBackupTag(tier) {
|
|
64
74
|
this.globalTags[BACKUP_TIER_TAG_KEY] = BACKUP_TIER_TAG_MAP[tier];
|
|
@@ -128,6 +138,19 @@ export class App extends CdkApp {
|
|
|
128
138
|
if (options?.tunnel && !App.instance.bastion) {
|
|
129
139
|
App.instance.initialiseTunnel(options.tunnel);
|
|
130
140
|
}
|
|
141
|
+
if (options?.eventBus !== undefined) {
|
|
142
|
+
if (App.instance.eventBusOverride === undefined &&
|
|
143
|
+
App.instance.defaultEventBus === undefined) {
|
|
144
|
+
App.instance.eventBusOverride = options.eventBus;
|
|
145
|
+
}
|
|
146
|
+
else {
|
|
147
|
+
const reason = App.instance.defaultEventBus !== undefined
|
|
148
|
+
? "bus was already materialised via getEventBus()"
|
|
149
|
+
: "override was already set on a prior App.getApp() call";
|
|
150
|
+
FjallLogger.warn(`App.getApp() eventBus override ignored: ${reason}. ` +
|
|
151
|
+
`Pass eventBus options to the first App.getApp() call.`);
|
|
152
|
+
}
|
|
153
|
+
}
|
|
131
154
|
}
|
|
132
155
|
return App.instance;
|
|
133
156
|
}
|
|
@@ -248,6 +271,67 @@ export class App extends CdkApp {
|
|
|
248
271
|
}
|
|
249
272
|
return this.defaultEcr;
|
|
250
273
|
}
|
|
274
|
+
/**
|
|
275
|
+
* Lazy getter for the per-app default custom EventBridge bus (D2).
|
|
276
|
+
*
|
|
277
|
+
* Buses are recreatable in non-prod; the env-resolved default keeps prod
|
|
278
|
+
* history. The override (`App.getApp({ eventBus: { name?, removalPolicy? } })`)
|
|
279
|
+
* is consulted first; absent override falls back to the app name and the
|
|
280
|
+
* `env({ default: "DESTROY", production: "RETAIN" })` resolution per D17.
|
|
281
|
+
* NODE_ENV is not consulted — it is not set during CDK synth in Fjall's
|
|
282
|
+
* deployment paths.
|
|
283
|
+
*/
|
|
284
|
+
getEventBus() {
|
|
285
|
+
if (this.defaultEventBus) {
|
|
286
|
+
return this.defaultEventBus;
|
|
287
|
+
}
|
|
288
|
+
const eventBusName = this.eventBusOverride?.name ?? this.getName();
|
|
289
|
+
const removalPolicy = this.eventBusOverride?.removalPolicy;
|
|
290
|
+
const bus = this.addMessaging(MessagingFactory.build(`${this.stackPrefix}EventBus`, {
|
|
291
|
+
type: "eventBus",
|
|
292
|
+
eventBusName,
|
|
293
|
+
appName: this.name,
|
|
294
|
+
removalPolicy
|
|
295
|
+
}));
|
|
296
|
+
this.defaultEventBus = bus;
|
|
297
|
+
return bus;
|
|
298
|
+
}
|
|
299
|
+
/**
|
|
300
|
+
* Lazy getter for the per-app Cloud Map private DNS namespace (D7 + D29 of
|
|
301
|
+
* the ClickHouse Database Factory promotion design).
|
|
302
|
+
*
|
|
303
|
+
* The namespace is constructed in the network stack on first call and
|
|
304
|
+
* reused thereafter — `app.getNamespace() === app.getNamespace()`. Default
|
|
305
|
+
* name is `${toKebab(appName)}.local` per the implementation-defined
|
|
306
|
+
* derivation rule; v1 has no override config option (D29). Returns the
|
|
307
|
+
* `IPrivateDnsNamespace` interface per D18(a), never the concrete class.
|
|
308
|
+
*/
|
|
309
|
+
getNamespace() {
|
|
310
|
+
return this.ensureNamespace().getNamespace();
|
|
311
|
+
}
|
|
312
|
+
/**
|
|
313
|
+
* Register a Cloud Map service against the per-app namespace. Lazily creates
|
|
314
|
+
* the namespace on first call (same construct as `getNamespace()`) and
|
|
315
|
+
* delegates to the `ServiceDiscoveryNamespace` wrapper's `registerService`
|
|
316
|
+
* — keeping both halves of Cloud Map (namespace + services) routed through
|
|
317
|
+
* the wrapper layer per § Wrapper Routing Discipline.
|
|
318
|
+
*/
|
|
319
|
+
registerService(props) {
|
|
320
|
+
return this.ensureNamespace().registerService(props);
|
|
321
|
+
}
|
|
322
|
+
ensureNamespace() {
|
|
323
|
+
if (this.defaultNamespace) {
|
|
324
|
+
return this.defaultNamespace;
|
|
325
|
+
}
|
|
326
|
+
const networkStack = this.getDefaultNetworkStack();
|
|
327
|
+
const namespace = new ServiceDiscoveryNamespace(networkStack.getStack(), `${this.stackPrefix}Namespace`, {
|
|
328
|
+
vpc: this.getVpc(),
|
|
329
|
+
name: `${toKebab(this.name)}.local`
|
|
330
|
+
});
|
|
331
|
+
networkStack.addConstruct(namespace);
|
|
332
|
+
this.defaultNamespace = namespace;
|
|
333
|
+
return namespace;
|
|
334
|
+
}
|
|
251
335
|
/**
|
|
252
336
|
* Create a cross-account audit role in the Network stack that allows
|
|
253
337
|
* the Fjall platform to use CloudQuery for comprehensive AWS resource auditing.
|
|
@@ -467,6 +551,32 @@ export class App extends CdkApp {
|
|
|
467
551
|
messagingStack.addConstruct(messaging);
|
|
468
552
|
return messaging;
|
|
469
553
|
}
|
|
554
|
+
/**
|
|
555
|
+
* Register an EventBridge schedule against a Fjall wrapper target.
|
|
556
|
+
*
|
|
557
|
+
* Defaults to the messaging stack; set `props.stackPlacement = "compute"`
|
|
558
|
+
* when the schedule's target lives in the compute stack and cross-stack
|
|
559
|
+
* output churn is undesired. `applicationId` is threaded automatically
|
|
560
|
+
* from `app.getName()` for alarm webhook routing per D13.
|
|
561
|
+
*
|
|
562
|
+
* @example
|
|
563
|
+
* app.addSchedule("MetricsCollection", {
|
|
564
|
+
* schedule: "rate(5 minutes)",
|
|
565
|
+
* target: notificationsQueue
|
|
566
|
+
* });
|
|
567
|
+
*/
|
|
568
|
+
addSchedule(id, props) {
|
|
569
|
+
const stack = props.stackPlacement === "compute"
|
|
570
|
+
? this.getDefaultComputeStack()
|
|
571
|
+
: this.getDefaultMessagingStack();
|
|
572
|
+
const schedule = new Schedule(stack.getStack(), id, {
|
|
573
|
+
...props,
|
|
574
|
+
applicationId: this.getName(),
|
|
575
|
+
appName: props.appName ?? this.getName()
|
|
576
|
+
});
|
|
577
|
+
stack.addConstruct(schedule);
|
|
578
|
+
return schedule;
|
|
579
|
+
}
|
|
470
580
|
/**
|
|
471
581
|
* Add a high-level infrastructure pattern to the application.
|
|
472
582
|
*
|
|
@@ -590,9 +700,8 @@ export class App extends CdkApp {
|
|
|
590
700
|
writeManifest(assembly, this.manifestCollector);
|
|
591
701
|
}
|
|
592
702
|
catch (error) {
|
|
593
|
-
|
|
594
|
-
|
|
595
|
-
FjallLogger.warn(`Failed to export Fjall manifest: ${errorMessage}`);
|
|
703
|
+
const maskedMessage = maskSensitiveOutput(error instanceof Error ? error.message : String(error));
|
|
704
|
+
FjallLogger.warn(`Failed to export Fjall manifest: ${maskedMessage}`);
|
|
596
705
|
}
|
|
597
706
|
return assembly;
|
|
598
707
|
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -1,18 +1,22 @@
|
|
|
1
1
|
import { CfnOutput } from "aws-cdk-lib";
|
|
2
|
-
import * as sns from "aws-cdk-lib/aws-sns";
|
|
3
2
|
import { Construct } from "constructs";
|
|
3
|
+
import { SNSTopic } from "../../resources/aws/messaging/sns.js";
|
|
4
4
|
export class SharedAlarmTopic extends Construct {
|
|
5
5
|
topic;
|
|
6
6
|
topicArn;
|
|
7
7
|
constructor(scope, id) {
|
|
8
8
|
super(scope, id);
|
|
9
|
-
const
|
|
9
|
+
const wrapped = new SNSTopic(this, "AlarmNotifications", {
|
|
10
10
|
displayName: "Fjall CloudWatch Alarm Notifications"
|
|
11
11
|
});
|
|
12
|
-
this.topic =
|
|
12
|
+
this.topic = wrapped.getTopic();
|
|
13
|
+
// SharedAlarmTopicArn is a well-known cross-stack export consumed via
|
|
14
|
+
// Fn.importValue (see resolveAlertsTopic + its tests). Do not delete
|
|
15
|
+
// thinking it duplicates the wrapper's AlarmNotificationsTopicArn —
|
|
16
|
+
// the wrapper's auto-output has no exportName and cannot be imported.
|
|
13
17
|
this.topicArn = new CfnOutput(this, "SharedAlarmTopicArn", {
|
|
14
18
|
key: "SharedAlarmTopicArn",
|
|
15
|
-
value:
|
|
19
|
+
value: wrapped.getTopicArn(),
|
|
16
20
|
exportName: "SharedAlarmTopicArn"
|
|
17
21
|
});
|
|
18
22
|
}
|
|
@@ -3,7 +3,7 @@ import { Trail } from "../../resources/aws/logging/cloudTrail.js";
|
|
|
3
3
|
export class ManagementEventsTrail extends Construct {
|
|
4
4
|
constructor(scope, id, props) {
|
|
5
5
|
super(scope, id);
|
|
6
|
-
new Trail(this, "
|
|
6
|
+
new Trail(this, "ManagementEventsTrail", {
|
|
7
7
|
bucketName: `cloudtrail-management-events-${props.accountId}-${props.region}`,
|
|
8
8
|
trailName: "managementEvents",
|
|
9
9
|
isMultiRegionTrail: true
|
|
@@ -2,10 +2,10 @@ import { CfnOutput, Duration, RemovalPolicy } from "aws-cdk-lib";
|
|
|
2
2
|
import { Construct } from "constructs";
|
|
3
3
|
import { BackupVault, BackupPlan } from "../../resources/aws/backup/index.js";
|
|
4
4
|
import { BackupPlanRule, BackupVault as Vault } from "aws-cdk-lib/aws-backup";
|
|
5
|
-
import
|
|
5
|
+
import { cronSchedule } from "../../resources/aws/messaging/index.js";
|
|
6
6
|
import { AccountPrincipal, Effect, PolicyStatement } from "aws-cdk-lib/aws-iam";
|
|
7
|
-
import
|
|
8
|
-
import {
|
|
7
|
+
import { getConfig } from "../../utils/getConfig.js";
|
|
8
|
+
import { toPascalCase } from "../../utils/capitaliseString.js";
|
|
9
9
|
// Backup retention constants (in days)
|
|
10
10
|
const RETENTION_PERIODS = {
|
|
11
11
|
STANDARD: 90,
|
|
@@ -34,16 +34,11 @@ export class DisasterRecovery extends Construct {
|
|
|
34
34
|
customBackupPlans;
|
|
35
35
|
constructor(scope, id, props) {
|
|
36
36
|
super(scope, id);
|
|
37
|
-
|
|
38
|
-
const
|
|
39
|
-
const orgConfigRaw = app.node.tryGetContext("orgConfig");
|
|
40
|
-
const orgConfig = parseOrgConfig(typeof orgConfigRaw === "string" ? orgConfigRaw : undefined);
|
|
41
|
-
const providerAccounts = orgConfig.providerAccounts;
|
|
42
|
-
// Determine if this is a compliance account
|
|
37
|
+
const config = getConfig();
|
|
38
|
+
const providerAccounts = config.providerAccounts;
|
|
43
39
|
const account = providerAccounts.find((pa) => pa.id === props.accountId);
|
|
44
40
|
const isComplianceAccount = account?.environment === "compliance";
|
|
45
|
-
|
|
46
|
-
const disasterRecoveryRegion = orgConfig.disasterRecoveryRegion;
|
|
41
|
+
const disasterRecoveryRegion = config.disasterRecoveryRegion;
|
|
47
42
|
// Look up compliance account for cross-account replication
|
|
48
43
|
// Skip if the compliance account (prevent self-replication)
|
|
49
44
|
const disasterRecoveryAccount = isComplianceAccount
|
|
@@ -110,7 +105,7 @@ export class DisasterRecovery extends Construct {
|
|
|
110
105
|
// Create custom backup plans if provided
|
|
111
106
|
if (props.customBackupPlans && props.customBackupPlans.length > 0) {
|
|
112
107
|
this.customBackupPlans = props.customBackupPlans.map((config) => {
|
|
113
|
-
return new BackupPlan(this, `CustomBackupPlan
|
|
108
|
+
return new BackupPlan(this, `CustomBackupPlan${toPascalCase(config.planName)}`, {
|
|
114
109
|
planName: config.planName,
|
|
115
110
|
rules: config.rules,
|
|
116
111
|
tagValue: config.tagValue,
|
|
@@ -143,7 +138,7 @@ export class DisasterRecovery extends Construct {
|
|
|
143
138
|
return [
|
|
144
139
|
new BackupPlanRule({
|
|
145
140
|
ruleName: `${planName}Daily`,
|
|
146
|
-
scheduleExpression:
|
|
141
|
+
scheduleExpression: cronSchedule({ hour: "2", minute: "0" }), // 2 AM daily
|
|
147
142
|
deleteAfter: Duration.days(RETENTION_PERIODS.STANDARD),
|
|
148
143
|
startWindow: BACKUP_WINDOWS.START,
|
|
149
144
|
completionWindow: BACKUP_WINDOWS.COMPLETION
|
|
@@ -155,7 +150,7 @@ export class DisasterRecovery extends Construct {
|
|
|
155
150
|
return [
|
|
156
151
|
new BackupPlanRule({
|
|
157
152
|
ruleName: `${planName}Daily`,
|
|
158
|
-
scheduleExpression:
|
|
153
|
+
scheduleExpression: cronSchedule({ hour: "2", minute: "0" }), // 2 AM daily
|
|
159
154
|
deleteAfter: Duration.days(RETENTION_PERIODS.ENTERPRISE_CONTINUOUS),
|
|
160
155
|
enableContinuousBackup: true,
|
|
161
156
|
startWindow: BACKUP_WINDOWS.START,
|
|
@@ -171,7 +166,7 @@ export class DisasterRecovery extends Construct {
|
|
|
171
166
|
// Continuous backup (35-day max PITR window)
|
|
172
167
|
new BackupPlanRule({
|
|
173
168
|
ruleName: `${planName}Continuous`,
|
|
174
|
-
scheduleExpression:
|
|
169
|
+
scheduleExpression: cronSchedule({ hour: "2", minute: "0" }), // Daily for continuous backup
|
|
175
170
|
deleteAfter: Duration.days(RETENTION_PERIODS.ENTERPRISE_CONTINUOUS),
|
|
176
171
|
enableContinuousBackup: true,
|
|
177
172
|
startWindow: BACKUP_WINDOWS.START,
|
|
@@ -181,7 +176,7 @@ export class DisasterRecovery extends Construct {
|
|
|
181
176
|
// Hourly snapshots for long-term compliance (7 years)
|
|
182
177
|
new BackupPlanRule({
|
|
183
178
|
ruleName: `${planName}HourlyCompliance`,
|
|
184
|
-
scheduleExpression:
|
|
179
|
+
scheduleExpression: cronSchedule({ minute: "0" }), // Every hour
|
|
185
180
|
deleteAfter: Duration.days(RETENTION_PERIODS.ENTERPRISE_COMPLIANCE),
|
|
186
181
|
moveToColdStorageAfter: Duration.days(RETENTION_PERIODS.COLD_STORAGE_ONE_YEAR),
|
|
187
182
|
startWindow: BACKUP_WINDOWS.START,
|
|
@@ -3,7 +3,6 @@ import { type StackProps } from "aws-cdk-lib";
|
|
|
3
3
|
interface EcrDefaultImageProps extends StackProps {
|
|
4
4
|
region: string;
|
|
5
5
|
accountId: string;
|
|
6
|
-
eventBusArn: string;
|
|
7
6
|
}
|
|
8
7
|
export declare class EcrDefaultImage extends Construct {
|
|
9
8
|
constructor(scope: Construct, id: string, props: EcrDefaultImageProps);
|
|
@@ -5,8 +5,7 @@ import { LogGroup } from "../../resources/aws/logging/logGroup.js";
|
|
|
5
5
|
import { RemovalPolicy } from "aws-cdk-lib";
|
|
6
6
|
import { Role } from "../../resources/aws/iam/role.js";
|
|
7
7
|
import { PolicyDocument, PolicyStatement, ServicePrincipal } from "aws-cdk-lib/aws-iam";
|
|
8
|
-
import {
|
|
9
|
-
import * as Targets from "aws-cdk-lib/aws-events-targets";
|
|
8
|
+
import { EventBusMessaging, EventField } from "../../patterns/aws/messaging.js";
|
|
10
9
|
export class EcrDefaultImage extends Construct {
|
|
11
10
|
constructor(scope, id, props) {
|
|
12
11
|
super(scope, id);
|
|
@@ -86,23 +85,10 @@ export class EcrDefaultImage extends Construct {
|
|
|
86
85
|
},
|
|
87
86
|
role: ecrDefaultImageRole
|
|
88
87
|
});
|
|
89
|
-
const
|
|
90
|
-
|
|
91
|
-
};
|
|
92
|
-
const eventInputTemplate = {
|
|
93
|
-
environmentVariablesOverride: [
|
|
94
|
-
{
|
|
95
|
-
name: "ECR_REPOSITORY",
|
|
96
|
-
value: eventInputMapping.repositoryUri
|
|
97
|
-
}
|
|
98
|
-
]
|
|
99
|
-
};
|
|
100
|
-
new Rule(this, `${id}EventRule`, {
|
|
101
|
-
ruleName: "ecrCreationRule",
|
|
88
|
+
const awsServiceBus = EventBusMessaging.fromAwsServiceBus(this, `${id}EventBus`, props.region, props.accountId);
|
|
89
|
+
awsServiceBus.subscribe(`${id}EventRule`, {
|
|
102
90
|
description: "Trigger the default ECR image build when a new repository is created",
|
|
103
|
-
|
|
104
|
-
eventBus: EventBus.fromEventBusArn(this, `${id}EventBus`, props.eventBusArn),
|
|
105
|
-
eventPattern: {
|
|
91
|
+
pattern: {
|
|
106
92
|
source: ["aws.ecr"],
|
|
107
93
|
detailType: ["AWS API Call via CloudTrail"],
|
|
108
94
|
detail: {
|
|
@@ -110,11 +96,15 @@ export class EcrDefaultImage extends Construct {
|
|
|
110
96
|
eventName: ["CreateRepository"]
|
|
111
97
|
}
|
|
112
98
|
},
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
99
|
+
target: codeBuildProject,
|
|
100
|
+
payload: {
|
|
101
|
+
environmentVariablesOverride: [
|
|
102
|
+
{
|
|
103
|
+
name: "ECR_REPOSITORY",
|
|
104
|
+
value: EventField.fromPath("$.detail.responseElements.repository.repositoryUri")
|
|
105
|
+
}
|
|
106
|
+
]
|
|
107
|
+
}
|
|
118
108
|
});
|
|
119
109
|
}
|
|
120
110
|
}
|
|
@@ -6,16 +6,23 @@ interface IdentityCenterProps extends NestedStackProps {
|
|
|
6
6
|
tags?: KeyValue[];
|
|
7
7
|
}
|
|
8
8
|
export interface PermissionSetConfig {
|
|
9
|
-
|
|
10
|
-
|
|
9
|
+
managedPolicies: string[];
|
|
10
|
+
description?: string;
|
|
11
|
+
sessionDuration?: string;
|
|
11
12
|
}
|
|
13
|
+
export type CustomPermissionSets = Record<string, PermissionSetConfig>;
|
|
12
14
|
export declare class IdentityCenter extends NestedStack {
|
|
13
15
|
identityStoreId: string;
|
|
14
16
|
identityCenterArn: string;
|
|
15
17
|
private listInstancesRole;
|
|
18
|
+
private accountsConfig;
|
|
19
|
+
private customTags?;
|
|
20
|
+
private groupIds;
|
|
16
21
|
constructor(scope: Construct, id: string, props: IdentityCenterProps);
|
|
22
|
+
declarePermissionSets(customs: CustomPermissionSets): void;
|
|
23
|
+
assignGroupMembers(members: Record<string, string[]>): void;
|
|
17
24
|
private createListInstancesRole;
|
|
18
25
|
private listIdentityCenterInstance;
|
|
19
|
-
private
|
|
26
|
+
private createPermissionSetAndAssignments;
|
|
20
27
|
}
|
|
21
28
|
export {};
|