From 0cce2f5ad99d4c66ab3a7a401a0415f596a97b0e Mon Sep 17 00:00:00 2001 From: Momo Kornher Date: Wed, 19 Mar 2025 12:15:21 +0000 Subject: [PATCH] chore(cli): code org --- .../tmp-toolkit-helpers/src/util/objects.ts | 32 +++++ .../src/util/string-manipulation.ts | 7 ++ .../api/deployments/hotswap-deployments.ts | 68 +++++------ .../api/hotswap/appsync-mapping-templates.ts | 9 +- .../lib/api/hotswap/code-build-projects.ts | 9 +- packages/aws-cdk/lib/api/hotswap/common.ts | 114 ++++++------------ .../aws-cdk/lib/api/hotswap/ecs-services.ts | 25 ++-- .../lib/api/hotswap/lambda-functions.ts | 10 +- .../lib/api/hotswap/s3-bucket-deployments.ts | 6 +- .../hotswap/stepfunctions-state-machines.ts | 6 +- packages/aws-cdk/lib/legacy-exports-source.ts | 3 +- 11 files changed, 135 insertions(+), 154 deletions(-) diff --git a/packages/@aws-cdk/tmp-toolkit-helpers/src/util/objects.ts b/packages/@aws-cdk/tmp-toolkit-helpers/src/util/objects.ts index 91872162d..2ff69c990 100644 --- a/packages/@aws-cdk/tmp-toolkit-helpers/src/util/objects.ts +++ b/packages/@aws-cdk/tmp-toolkit-helpers/src/util/objects.ts @@ -215,3 +215,35 @@ export function splitBySize(data: any, maxSizeBytes: number): [any, any] { ]; } } + +type Exclude = { [key: string]: Exclude | true }; + +/** + * This function transforms all keys (recursively) in the provided `val` object. + * + * @param val The object whose keys need to be transformed. + * @param transform The function that will be applied to each key. + * @param exclude The keys that will not be transformed and copied to output directly + * @returns A new object with the same values as `val`, but with all keys transformed according to `transform`. + */ +export function transformObjectKeys(val: any, transform: (str: string) => string, exclude: Exclude = {}): any { + if (val == null || typeof val !== 'object') { + return val; + } + if (Array.isArray(val)) { + // For arrays we just pass parent's exclude object directly + // since it makes no sense to specify different exclude options for each array element + return val.map((input: any) => transformObjectKeys(input, transform, exclude)); + } + const ret: { [k: string]: any } = {}; + for (const [k, v] of Object.entries(val)) { + const childExclude = exclude[k]; + if (childExclude === true) { + // we don't transform this object if the key is specified in exclude + ret[transform(k)] = v; + } else { + ret[transform(k)] = transformObjectKeys(v, transform, childExclude); + } + } + return ret; +} diff --git a/packages/@aws-cdk/tmp-toolkit-helpers/src/util/string-manipulation.ts b/packages/@aws-cdk/tmp-toolkit-helpers/src/util/string-manipulation.ts index 098beacd1..0165abb3d 100644 --- a/packages/@aws-cdk/tmp-toolkit-helpers/src/util/string-manipulation.ts +++ b/packages/@aws-cdk/tmp-toolkit-helpers/src/util/string-manipulation.ts @@ -35,3 +35,10 @@ function roundPercentage(num: number): number { function millisecondsToSeconds(num: number): number { return num / 1000; } + +/** + * This function lower cases the first character of the string provided. + */ +export function lowerCaseFirstCharacter(str: string): string { + return str.length > 0 ? `${str[0].toLowerCase()}${str.slice(1)}` : str; +} diff --git a/packages/aws-cdk/lib/api/deployments/hotswap-deployments.ts b/packages/aws-cdk/lib/api/deployments/hotswap-deployments.ts index 913ac837e..d0355c786 100644 --- a/packages/aws-cdk/lib/api/deployments/hotswap-deployments.ts +++ b/packages/aws-cdk/lib/api/deployments/hotswap-deployments.ts @@ -17,17 +17,15 @@ import { EvaluateCloudFormationTemplate } from '../evaluate-cloudformation-templ import { isHotswappableAppSyncChange } from '../hotswap/appsync-mapping-templates'; import { isHotswappableCodeBuildProjectChange } from '../hotswap/code-build-projects'; import type { - ChangeHotswapResult, + HotswapChange, HotswapOperation, - NonHotswappableChange, + RejectedChange, HotswapPropertyOverrides, - ClassifiedResourceChanges, HotswapResult, } from '../hotswap/common'; import { ICON, - reportNonHotswappableChange, - reportNonHotswappableResource, + nonHotswappableResource, } from '../hotswap/common'; import { isHotswappableEcsServiceChange } from '../hotswap/ecs-services'; import { isHotswappableLambdaFunctionChange } from '../hotswap/lambda-functions'; @@ -48,7 +46,7 @@ type HotswapDetector = ( change: ResourceChange, evaluateCfnTemplate: EvaluateCloudFormationTemplate, hotswapPropertyOverrides: HotswapPropertyOverrides, -) => Promise; +) => Promise; type HotswapMode = 'hotswap-only' | 'fall-back'; @@ -72,17 +70,13 @@ const RESOURCE_DETECTORS: { [key: string]: HotswapDetector } = { logicalId: string, change: ResourceChange, evaluateCfnTemplate: EvaluateCloudFormationTemplate, - ): Promise => { + ): Promise => { // If the policy is for a S3BucketDeploymentChange, we can ignore the change if (await skipChangeForS3DeployCustomResourcePolicy(logicalId, change, evaluateCfnTemplate)) { return []; } - return reportNonHotswappableResource( - change, - NonHotswappableReason.RESOURCE_UNSUPPORTED, - 'This resource type is not supported for hotswap deployments', - ); + return [nonHotswappableResource(change)]; }, 'AWS::CDK::Metadata': async () => [], @@ -162,7 +156,7 @@ async function hotswapDeployment( }); const stackChanges = cfn_diff.fullDiff(currentTemplate.deployedRootTemplate, stack.template); - const { hotswapOperations, nonHotswappableChanges } = await classifyResourceChanges( + const { hotswappable: hotswapOperations, nonHotswappable: nonHotswappableChanges } = await classifyResourceChanges( stackChanges, evaluateCfnTemplate, sdk, @@ -196,6 +190,11 @@ async function hotswapDeployment( }; } +interface ClassifiedChanges { + hotswappable: HotswapOperation[]; + nonHotswappable: RejectedChange[]; +} + /** * Classifies all changes to all resources as either hotswappable or not. * Metadata changes are excluded from the list of (non)hotswappable resources. @@ -206,19 +205,18 @@ async function classifyResourceChanges( sdk: SDK, nestedStackNames: { [nestedStackName: string]: NestedStackTemplates }, hotswapPropertyOverrides: HotswapPropertyOverrides, -): Promise { +): Promise { const resourceDifferences = getStackResourceDifferences(stackChanges); - const promises: Array<() => Promise> = []; + const promises: Array<() => Promise> = []; const hotswappableResources = new Array(); - const nonHotswappableResources = new Array(); + const nonHotswappableResources = new Array(); for (const logicalId of Object.keys(stackChanges.outputs.changes)) { nonHotswappableResources.push({ hotswappable: false, reason: NonHotswappableReason.OUTPUT, description: 'output was changed', logicalId, - rejectedChanges: [], resourceType: 'Stack Output', }); } @@ -233,8 +231,8 @@ async function classifyResourceChanges( sdk, hotswapPropertyOverrides, ); - hotswappableResources.push(...nestedHotswappableResources.hotswapOperations); - nonHotswappableResources.push(...nestedHotswappableResources.nonHotswappableChanges); + hotswappableResources.push(...nestedHotswappableResources.hotswappable); + nonHotswappableResources.push(...nestedHotswappableResources.nonHotswappable); continue; } @@ -256,18 +254,12 @@ async function classifyResourceChanges( RESOURCE_DETECTORS[resourceType](logicalId, hotswappableChangeCandidate, evaluateCfnTemplate, hotswapPropertyOverrides), ); } else { - reportNonHotswappableChange( - nonHotswappableResources, - hotswappableChangeCandidate, - NonHotswappableReason.RESOURCE_UNSUPPORTED, - undefined, - 'This resource type is not supported for hotswap deployments', - ); + nonHotswappableResources.push(nonHotswappableResource(hotswappableChangeCandidate)); } } // resolve all detector results - const changesDetectionResults: Array = []; + const changesDetectionResults: Array = []; for (const detectorResultPromises of promises) { // Constant set of promises per resource // eslint-disable-next-line @cdklabs/promiseall-no-unbounded-parallelism @@ -284,8 +276,8 @@ async function classifyResourceChanges( } return { - hotswapOperations: hotswappableResources, - nonHotswappableChanges: nonHotswappableResources, + hotswappable: hotswappableResources, + nonHotswappable: nonHotswappableResources, }; } @@ -348,18 +340,17 @@ async function findNestedHotswappableChanges( evaluateCfnTemplate: EvaluateCloudFormationTemplate, sdk: SDK, hotswapPropertyOverrides: HotswapPropertyOverrides, -): Promise { +): Promise { const nestedStack = nestedStackTemplates[logicalId]; if (!nestedStack.physicalName) { return { - hotswapOperations: [], - nonHotswappableChanges: [ + hotswappable: [], + nonHotswappable: [ { hotswappable: false, logicalId, reason: NonHotswappableReason.NESTED_STACK_CREATION, description: `physical name for AWS::CloudFormation::Stack '${logicalId}' could not be found in CloudFormation, so this is a newly created nested stack and cannot be hotswapped`, - rejectedChanges: [], resourceType: 'AWS::CloudFormation::Stack', }, ], @@ -425,14 +416,13 @@ function makeRenameDifference( function isCandidateForHotswapping( change: cfn_diff.ResourceDifference, logicalId: string, -): HotswapOperation | NonHotswappableChange | ResourceChange { +): RejectedChange | ResourceChange { // a resource has been removed OR a resource has been added; we can't short-circuit that change if (!change.oldValue) { return { hotswappable: false, resourceType: change.newValue!.Type, logicalId, - rejectedChanges: [], reason: NonHotswappableReason.RESOURCE_CREATION, description: `resource '${logicalId}' was created by this deployment`, }; @@ -441,7 +431,6 @@ function isCandidateForHotswapping( hotswappable: false, resourceType: change.oldValue!.Type, logicalId, - rejectedChanges: [], reason: NonHotswappableReason.RESOURCE_DELETION, description: `resource '${logicalId}' was destroyed by this deployment`, }; @@ -453,7 +442,6 @@ function isCandidateForHotswapping( hotswappable: false, resourceType: change.newValue?.Type, logicalId, - rejectedChanges: [], reason: NonHotswappableReason.RESOURCE_TYPE_CHANGED, description: `resource '${logicalId}' had its type changed from '${change.oldValue?.Type}' to '${change.newValue?.Type}'`, }; @@ -530,7 +518,7 @@ function formatWaiterErrorResult(result: WaiterResult) { async function logNonHotswappableChanges( ioSpan: IMessageSpan, - nonHotswappableChanges: NonHotswappableChange[], + nonHotswappableChanges: RejectedChange[], hotswapMode: HotswapMode, ): Promise { if (nonHotswappableChanges.length === 0) { @@ -560,12 +548,12 @@ async function logNonHotswappableChanges( } for (const change of nonHotswappableChanges) { - if (change.rejectedChanges.length > 0) { + if (change.rejectedProperties?.length) { messages.push(format( ' logicalID: %s, type: %s, rejected changes: %s, reason: %s', chalk.bold(change.logicalId), chalk.bold(change.resourceType), - chalk.bold(change.rejectedChanges), + chalk.bold(change.rejectedProperties), chalk.red(change.description), )); } else { diff --git a/packages/aws-cdk/lib/api/hotswap/appsync-mapping-templates.ts b/packages/aws-cdk/lib/api/hotswap/appsync-mapping-templates.ts index c2014c832..9c8ef74cf 100644 --- a/packages/aws-cdk/lib/api/hotswap/appsync-mapping-templates.ts +++ b/packages/aws-cdk/lib/api/hotswap/appsync-mapping-templates.ts @@ -3,13 +3,12 @@ import type { GetSchemaCreationStatusCommandInput, } from '@aws-sdk/client-appsync'; import { - type ChangeHotswapResult, + type HotswapChange, classifyChanges, - lowerCaseFirstCharacter, - transformObjectKeys, } from './common'; import type { ResourceChange } from '../../../../@aws-cdk/tmp-toolkit-helpers/src/api/io/payloads/hotswap'; import { ToolkitError } from '../../toolkit/error'; +import { lowerCaseFirstCharacter, transformObjectKeys } from '../../util'; import type { SDK } from '../aws-auth'; import type { EvaluateCloudFormationTemplate } from '../evaluate-cloudformation-template'; @@ -18,7 +17,7 @@ export async function isHotswappableAppSyncChange( logicalId: string, change: ResourceChange, evaluateCfnTemplate: EvaluateCloudFormationTemplate, -): Promise { +): Promise { const isResolver = change.newValue.Type === 'AWS::AppSync::Resolver'; const isFunction = change.newValue.Type === 'AWS::AppSync::FunctionConfiguration'; const isGraphQLSchema = change.newValue.Type === 'AWS::AppSync::GraphQLSchema'; @@ -27,7 +26,7 @@ export async function isHotswappableAppSyncChange( return []; } - const ret: ChangeHotswapResult = []; + const ret: HotswapChange[] = []; const classifiedChanges = classifyChanges(change, [ 'RequestMappingTemplate', diff --git a/packages/aws-cdk/lib/api/hotswap/code-build-projects.ts b/packages/aws-cdk/lib/api/hotswap/code-build-projects.ts index 659a3e557..a451c0917 100644 --- a/packages/aws-cdk/lib/api/hotswap/code-build-projects.ts +++ b/packages/aws-cdk/lib/api/hotswap/code-build-projects.ts @@ -1,11 +1,10 @@ import type { UpdateProjectCommandInput } from '@aws-sdk/client-codebuild'; import { - type ChangeHotswapResult, + type HotswapChange, classifyChanges, - lowerCaseFirstCharacter, - transformObjectKeys, } from './common'; import type { ResourceChange } from '../../../../@aws-cdk/tmp-toolkit-helpers/src/api/io/payloads/hotswap'; +import { lowerCaseFirstCharacter, transformObjectKeys } from '../../util'; import type { SDK } from '../aws-auth'; import type { EvaluateCloudFormationTemplate } from '../evaluate-cloudformation-template'; @@ -13,12 +12,12 @@ export async function isHotswappableCodeBuildProjectChange( logicalId: string, change: ResourceChange, evaluateCfnTemplate: EvaluateCloudFormationTemplate, -): Promise { +): Promise { if (change.newValue.Type !== 'AWS::CodeBuild::Project') { return []; } - const ret: ChangeHotswapResult = []; + const ret: HotswapChange[] = []; const classifiedChanges = classifyChanges(change, ['Source', 'Environment', 'SourceVersion']); classifiedChanges.reportNonHotswappablePropertyChanges(ret); diff --git a/packages/aws-cdk/lib/api/hotswap/common.ts b/packages/aws-cdk/lib/api/hotswap/common.ts index 3b7be7bec..ffe8c14da 100644 --- a/packages/aws-cdk/lib/api/hotswap/common.ts +++ b/packages/aws-cdk/lib/api/hotswap/common.ts @@ -54,10 +54,22 @@ export interface HotswapOperation { readonly apply: (sdk: SDK) => Promise; } -export interface NonHotswappableChange { +export interface RejectedChange { + /** + * Marks the change as not hotswappable + */ readonly hotswappable: false; + /** + * The friendly type of the rejected change + */ readonly resourceType: string; - readonly rejectedChanges: Array; + /** + * The list of properties that are cause for the rejection + */ + readonly rejectedProperties?: Array; + /** + * The logical ID of the resource that is not hotswappable + */ readonly logicalId: string; /** * Why was this change was deemed non-hotswappable @@ -67,7 +79,7 @@ export interface NonHotswappableChange { * Tells the user exactly why this change was deemed non-hotswappable and what its logical ID is. * If not specified, `displayReason` default to state that the properties listed in `rejectedChanges` are not hotswappable. */ - readonly description?: string; + readonly description: string; /** * Whether or not to show this change when listing non-hotswappable changes in HOTSWAP_ONLY mode. Does not affect * listing in FALL_BACK mode. @@ -77,12 +89,7 @@ export interface NonHotswappableChange { readonly hotswapOnlyVisible?: boolean; } -export type ChangeHotswapResult = Array; - -export interface ClassifiedResourceChanges { - hotswapOperations: HotswapOperation[]; - nonHotswappableChanges: NonHotswappableChange[]; -} +export type HotswapChange = HotswapOperation | RejectedChange; export enum HotswapMode { /** @@ -101,8 +108,6 @@ export enum HotswapMode { FULL_DEPLOYMENT = 'full-deployment', } -type Exclude = { [key: string]: Exclude | true }; - /** * Represents configuration property overrides for hotswap deployments */ @@ -149,46 +154,9 @@ export class EcsHotswapProperties { } } -/** - * This function transforms all keys (recursively) in the provided `val` object. - * - * @param val The object whose keys need to be transformed. - * @param transform The function that will be applied to each key. - * @param exclude The keys that will not be transformed and copied to output directly - * @returns A new object with the same values as `val`, but with all keys transformed according to `transform`. - */ -export function transformObjectKeys(val: any, transform: (str: string) => string, exclude: Exclude = {}): any { - if (val == null || typeof val !== 'object') { - return val; - } - if (Array.isArray(val)) { - // For arrays we just pass parent's exclude object directly - // since it makes no sense to specify different exclude options for each array element - return val.map((input: any) => transformObjectKeys(input, transform, exclude)); - } - const ret: { [k: string]: any } = {}; - for (const [k, v] of Object.entries(val)) { - const childExclude = exclude[k]; - if (childExclude === true) { - // we don't transform this object if the key is specified in exclude - ret[transform(k)] = v; - } else { - ret[transform(k)] = transformObjectKeys(v, transform, childExclude); - } - } - return ret; -} - -/** - * This function lower cases the first character of the string provided. - */ -export function lowerCaseFirstCharacter(str: string): string { - return str.length > 0 ? `${str[0].toLowerCase()}${str.slice(1)}` : str; -} - type PropDiffs = Record>; -export class ClassifiedChanges { +class ClassifiedChanges { public constructor( public readonly change: ResourceChange, public readonly hotswappableProps: PropDiffs, @@ -196,20 +164,19 @@ export class ClassifiedChanges { ) { } - public reportNonHotswappablePropertyChanges(ret: ChangeHotswapResult): void { + public reportNonHotswappablePropertyChanges(ret: HotswapChange[]): void { const nonHotswappablePropNames = Object.keys(this.nonHotswappableProps); if (nonHotswappablePropNames.length > 0) { const tagOnlyChange = nonHotswappablePropNames.length === 1 && nonHotswappablePropNames[0] === 'Tags'; const reason = tagOnlyChange ? NonHotswappableReason.TAGS : NonHotswappableReason.PROPERTIES; const description = tagOnlyChange ? 'Tags are not hotswappable' : `resource properties '${nonHotswappablePropNames}' are not hotswappable on this resource type`; - reportNonHotswappableChange( - ret, + ret.push(nonHotswappableChange( this.change, reason, - this.nonHotswappableProps, description, - ); + this.nonHotswappableProps, + )); } } @@ -233,38 +200,31 @@ export function classifyChanges(xs: ResourceChange, hotswappablePropNames: strin return new ClassifiedChanges(xs, hotswappableProps, nonHotswappableProps); } -export function reportNonHotswappableChange( - ret: ChangeHotswapResult, +export function nonHotswappableChange( change: ResourceChange, reason: NonHotswappableReason, + description: string, nonHotswappableProps?: PropDiffs, - description?: string, hotswapOnlyVisible: boolean = true, -): void { - ret.push({ +): RejectedChange { + return { hotswappable: false, - rejectedChanges: Object.keys(nonHotswappableProps ?? change.propertyUpdates), + rejectedProperties: Object.keys(nonHotswappableProps ?? change.propertyUpdates), logicalId: change.logicalId, resourceType: change.newValue.Type, reason, - description: description, + description, hotswapOnlyVisible, - }); + }; } -export function reportNonHotswappableResource( - change: ResourceChange, - reason: NonHotswappableReason, - description?: string, -): ChangeHotswapResult { - return [ - { - hotswappable: false, - rejectedChanges: Object.keys(change.propertyUpdates), - logicalId: change.logicalId, - resourceType: change.newValue.Type, - reason, - description: description, - }, - ]; +export function nonHotswappableResource(change: ResourceChange): RejectedChange { + return { + hotswappable: false, + rejectedProperties: Object.keys(change.propertyUpdates), + logicalId: change.logicalId, + resourceType: change.newValue.Type, + reason: NonHotswappableReason.RESOURCE_UNSUPPORTED, + description: 'This resource type is not supported for hotswap deployments', + }; } diff --git a/packages/aws-cdk/lib/api/hotswap/ecs-services.ts b/packages/aws-cdk/lib/api/hotswap/ecs-services.ts index 595bb4947..76219afc2 100644 --- a/packages/aws-cdk/lib/api/hotswap/ecs-services.ts +++ b/packages/aws-cdk/lib/api/hotswap/ecs-services.ts @@ -1,13 +1,13 @@ import type { HotswapPropertyOverrides, - ChangeHotswapResult, + HotswapChange, } from './common'; import { - classifyChanges, lowerCaseFirstCharacter, - reportNonHotswappableChange, - transformObjectKeys, + classifyChanges, + nonHotswappableChange, } from './common'; import { NonHotswappableReason, type ResourceChange } from '../../../../@aws-cdk/tmp-toolkit-helpers/src/api/io/payloads/hotswap'; +import { lowerCaseFirstCharacter, transformObjectKeys } from '../../util'; import type { SDK } from '../aws-auth'; import type { EvaluateCloudFormationTemplate } from '../evaluate-cloudformation-template'; @@ -18,13 +18,13 @@ export async function isHotswappableEcsServiceChange( change: ResourceChange, evaluateCfnTemplate: EvaluateCloudFormationTemplate, hotswapPropertyOverrides: HotswapPropertyOverrides, -): Promise { +): Promise { // the only resource change we can evaluate here is an ECS TaskDefinition if (change.newValue.Type !== 'AWS::ECS::TaskDefinition') { return []; } - const ret: ChangeHotswapResult = []; + const ret: HotswapChange[] = []; // We only allow a change in the ContainerDefinitions of the TaskDefinition for now - // it contains the image and environment variables, so seems like a safe bet for now. @@ -55,27 +55,24 @@ export async function isHotswappableEcsServiceChange( * * This logic prevents us from logging that change as non-hotswappable when we hotswap it. */ - reportNonHotswappableChange( - ret, + ret.push(nonHotswappableChange( change, NonHotswappableReason.DEPENDENCY_UNSUPPORTED, - undefined, 'No ECS services reference the changed task definition', + undefined, false, - ); + )); } if (resourcesReferencingTaskDef.length > ecsServicesReferencingTaskDef.length) { // if something besides an ECS Service is referencing the TaskDefinition, // hotswap is not possible in FALL_BACK mode const nonEcsServiceTaskDefRefs = resourcesReferencingTaskDef.filter((r) => r.Type !== ECS_SERVICE_RESOURCE_TYPE); for (const taskRef of nonEcsServiceTaskDefRefs) { - reportNonHotswappableChange( - ret, + ret.push(nonHotswappableChange( change, NonHotswappableReason.DEPENDENCY_UNSUPPORTED, - undefined, `A resource '${taskRef.LogicalId}' with Type '${taskRef.Type}' that is not an ECS Service was found referencing the changed TaskDefinition '${logicalId}'`, - ); + )); } } diff --git a/packages/aws-cdk/lib/api/hotswap/lambda-functions.ts b/packages/aws-cdk/lib/api/hotswap/lambda-functions.ts index 5adedf3d4..0cbec1906 100644 --- a/packages/aws-cdk/lib/api/hotswap/lambda-functions.ts +++ b/packages/aws-cdk/lib/api/hotswap/lambda-functions.ts @@ -1,7 +1,7 @@ import { Writable } from 'stream'; import type { PropertyDifference } from '@aws-cdk/cloudformation-diff'; import type { FunctionConfiguration, UpdateFunctionConfigurationCommandInput } from '@aws-sdk/client-lambda'; -import type { ChangeHotswapResult } from './common'; +import type { HotswapChange } from './common'; import { classifyChanges } from './common'; import type { AffectedResource, ResourceChange } from '../../../../@aws-cdk/tmp-toolkit-helpers/src/api/io/payloads/hotswap'; import { ToolkitError } from '../../toolkit/error'; @@ -17,7 +17,7 @@ export async function isHotswappableLambdaFunctionChange( logicalId: string, change: ResourceChange, evaluateCfnTemplate: EvaluateCloudFormationTemplate, -): Promise { +): Promise { // if the change is for a Lambda Version, we just ignore it // we will publish a new version when we get to hotswapping the actual Function this Version points to // (Versions can't be changed in CloudFormation anyway, they're immutable) @@ -35,7 +35,7 @@ export async function isHotswappableLambdaFunctionChange( return []; } - const ret: ChangeHotswapResult = []; + const ret: HotswapChange[] = []; const classifiedChanges = classifyChanges(change, ['Code', 'Environment', 'Description']); classifiedChanges.reportNonHotswappablePropertyChanges(ret); @@ -145,8 +145,8 @@ export async function isHotswappableLambdaFunctionChange( /** * Determines which changes to this Alias are hotswappable or not */ -function classifyAliasChanges(change: ResourceChange): ChangeHotswapResult { - const ret: ChangeHotswapResult = []; +function classifyAliasChanges(change: ResourceChange): HotswapChange[] { + const ret: HotswapChange[] = []; const classifiedChanges = classifyChanges(change, ['FunctionVersion']); classifiedChanges.reportNonHotswappablePropertyChanges(ret); diff --git a/packages/aws-cdk/lib/api/hotswap/s3-bucket-deployments.ts b/packages/aws-cdk/lib/api/hotswap/s3-bucket-deployments.ts index 0a293bbe1..0dbc5e052 100644 --- a/packages/aws-cdk/lib/api/hotswap/s3-bucket-deployments.ts +++ b/packages/aws-cdk/lib/api/hotswap/s3-bucket-deployments.ts @@ -1,4 +1,4 @@ -import type { ChangeHotswapResult } from './common'; +import type { HotswapChange } from './common'; import type { ResourceChange } from '../../../../@aws-cdk/tmp-toolkit-helpers/src/api/io/payloads/hotswap'; import type { SDK } from '../aws-auth'; import type { EvaluateCloudFormationTemplate } from '../evaluate-cloudformation-template'; @@ -15,10 +15,10 @@ export async function isHotswappableS3BucketDeploymentChange( logicalId: string, change: ResourceChange, evaluateCfnTemplate: EvaluateCloudFormationTemplate, -): Promise { +): Promise { // In old-style synthesis, the policy used by the lambda to copy assets Ref's the assets directly, // meaning that the changes made to the Policy are artifacts that can be safely ignored - const ret: ChangeHotswapResult = []; + const ret: HotswapChange[] = []; if (change.newValue.Type !== CDK_BUCKET_DEPLOYMENT_CFN_TYPE) { return []; diff --git a/packages/aws-cdk/lib/api/hotswap/stepfunctions-state-machines.ts b/packages/aws-cdk/lib/api/hotswap/stepfunctions-state-machines.ts index 5fa253d62..17fb6d4f4 100644 --- a/packages/aws-cdk/lib/api/hotswap/stepfunctions-state-machines.ts +++ b/packages/aws-cdk/lib/api/hotswap/stepfunctions-state-machines.ts @@ -1,4 +1,4 @@ -import { type ChangeHotswapResult, classifyChanges } from './common'; +import { type HotswapChange, classifyChanges } from './common'; import type { ResourceChange } from '../../../../@aws-cdk/tmp-toolkit-helpers/src/api/io/payloads/hotswap'; import type { SDK } from '../aws-auth'; import type { EvaluateCloudFormationTemplate } from '../evaluate-cloudformation-template'; @@ -7,11 +7,11 @@ export async function isHotswappableStateMachineChange( logicalId: string, change: ResourceChange, evaluateCfnTemplate: EvaluateCloudFormationTemplate, -): Promise { +): Promise { if (change.newValue.Type !== 'AWS::StepFunctions::StateMachine') { return []; } - const ret: ChangeHotswapResult = []; + const ret: HotswapChange[] = []; const classifiedChanges = classifyChanges(change, ['DefinitionString']); classifiedChanges.reportNonHotswappablePropertyChanges(ret); diff --git a/packages/aws-cdk/lib/legacy-exports-source.ts b/packages/aws-cdk/lib/legacy-exports-source.ts index 81c7b85a2..029517409 100644 --- a/packages/aws-cdk/lib/legacy-exports-source.ts +++ b/packages/aws-cdk/lib/legacy-exports-source.ts @@ -5,7 +5,7 @@ // Note: All type exports are in `legacy-exports.ts` export * from './legacy-logging-source'; -export { deepClone, flatten, ifDefined, isArray, isEmpty, numberFromBool, partition, padLeft as leftPad, contentHash, deepMerge } from './util'; +export { deepClone, flatten, ifDefined, isArray, isEmpty, numberFromBool, partition, padLeft as leftPad, contentHash, deepMerge, lowerCaseFirstCharacter } from './util'; export { deployStack } from './api/deployments/deploy-stack'; export { cli, exec } from './cli/cli'; export { SdkProvider } from './api/aws-auth'; @@ -19,7 +19,6 @@ export { RequireApproval } from './diff'; export { formatAsBanner } from './cli/util/console-formatters'; export { setSdkTracing as enableTracing } from './api/aws-auth/tracing'; export { aliases, command, describe } from './commands/docs'; -export { lowerCaseFirstCharacter } from './api/hotswap/common'; export { Deployments } from './api/deployments'; export { cliRootDir as rootDir } from './cli/root-dir'; export { latestVersionIfHigher, versionNumber } from './cli/version';