Skip to content

Commit

Permalink
refactor(cli): collate existing files into new deployments api (#33094)
Browse files Browse the repository at this point in the history
### Reason for this change

Cleaning up the CLI code base in preparation for splitting out the library parts.
It's currently quite hard to reason about the existing api code as its spread across many files and deep subpath imports.
This change attempts to partly rectify the situation by grouping files with strong interdependencies together and creating a unified import location.
The change deliberately gives up on potential feature reusability of some helpers in order to create locality. 

### Description of changes

Collating existing files and APIs into a new submodule `api/deployments`.
Updated imports accordingly.
No functional changes.

### Describe any new or updated permissions being added

n/a

### Description of how you validated changes

exiting tests

### Checklist
- [x] My code adheres to the [CONTRIBUTING GUIDE](https://github.com/aws/aws-cdk/blob/main/CONTRIBUTING.md) and [DESIGN GUIDELINES](https://github.com/aws/aws-cdk/blob/main/docs/DESIGN_GUIDELINES.md)

----

*By submitting this pull request, I confirm that my contribution is made under the terms of the Apache-2.0 license*
  • Loading branch information
mrgrain authored Jan 23, 2025
1 parent 8506d31 commit ac90399
Show file tree
Hide file tree
Showing 43 changed files with 233 additions and 223 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import { loadStructuredFile, serializeStructure } from '../../serialize';
import { ToolkitError } from '../../toolkit/error';
import { rootDir } from '../../util/directories';
import type { SDK, SdkProvider } from '../aws-auth';
import type { SuccessfulDeployStackResult } from '../deploy-stack';
import type { SuccessfulDeployStackResult } from '../deployments';
import { Mode } from '../plugin/mode';

export type BootstrapSource = { source: 'legacy' } | { source: 'default' } | { source: 'custom'; templateFile: string };
Expand Down
3 changes: 2 additions & 1 deletion packages/aws-cdk/lib/api/bootstrap/deploy-bootstrap.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,8 @@ import {
} from './bootstrap-props';
import * as logging from '../../logging';
import type { SDK, SdkProvider } from '../aws-auth';
import { assertIsSuccessfulDeployStackResult, deployStack, SuccessfulDeployStackResult } from '../deploy-stack';
import { assertIsSuccessfulDeployStackResult, SuccessfulDeployStackResult } from '../deployments';
import { deployStack } from '../deployments/deploy-stack';
import { NoBootstrapStackEnvironmentResources } from '../environment-resources';
import { Mode } from '../plugin/mode';
import { DEFAULT_TOOLKIT_STACK_NAME, ToolkitInfo } from '../toolkit-info';
Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import * as cxschema from '@aws-cdk/cloud-assembly-schema';
import * as cdk_assets from 'cdk-assets';
import { AssetManifest } from 'cdk-assets';

export class AssetManifestBuilder {
private readonly manifest: cxschema.AssetManifest = {
Expand All @@ -26,7 +26,7 @@ export class AssetManifestBuilder {
};
}

public toManifest(directory: string): cdk_assets.AssetManifest {
return new cdk_assets.AssetManifest(directory, this.manifest);
public toManifest(directory: string): AssetManifest {
return new AssetManifest(directory, this.manifest);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,11 +12,11 @@ import {
type IS3Client,
type ISecretsManagerClient,
} from 'cdk-assets';
import type { SDK } from '../api';
import type { SdkProvider } from '../api/aws-auth/sdk-provider';
import { Mode } from '../api/plugin/mode';
import { debug, error, info } from '../logging';
import { ToolkitError } from '../toolkit/error';
import type { SDK } from '..';
import { debug, error, info } from '../../logging';
import { ToolkitError } from '../../toolkit/error';
import type { SdkProvider } from '../aws-auth';
import { Mode } from '../plugin';

export interface PublishAssetsOptions {
/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,11 @@ import * as path from 'path';
import * as cxschema from '@aws-cdk/cloud-assembly-schema';
import * as cxapi from '@aws-cdk/cx-api';
import * as chalk from 'chalk';
import { EnvironmentResources } from './api/environment-resources';
import { ToolkitInfo } from './api/toolkit-info';
import { debug } from './logging';
import { ToolkitError } from './toolkit/error';
import { AssetManifestBuilder } from './util/asset-manifest-builder';
import { AssetManifestBuilder } from './asset-manifest-builder';
import { debug } from '../../logging';
import { ToolkitError } from '../../toolkit/error';
import { EnvironmentResources } from '../environment-resources';
import { ToolkitInfo } from '../toolkit-info';

/**
* Take the metadata assets from the given stack and add them to the given asset manifest
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { debug } from '../../logging';
import { ToolkitError } from '../../toolkit/error';
import { SDK } from '../aws-auth/sdk';
import { SDK } from '../aws-auth';

export async function determineAllowCrossAccountAssetPublishing(sdk: SDK, customStackName?: string): Promise<boolean> {
try {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,15 @@ import {
type Tag,
} from '@aws-sdk/client-cloudformation';
import { AssetManifest, FileManifestEntry } from 'cdk-assets';
import { StackStatus } from './cloudformation/stack-status';
import { makeBodyParameter, TemplateBodyParameter } from './template-body-parameter';
import { AssetManifestBuilder } from './asset-manifest-builder';
import { debug } from '../../logging';
import { deserializeStructure } from '../../serialize';
import { ToolkitError } from '../../toolkit/error';
import { AssetManifestBuilder } from '../../util/asset-manifest-builder';
import { formatErrorMessage } from '../../util/error';
import type { ICloudFormationClient, SdkProvider } from '../aws-auth';
import type { Deployments } from '../deployments';
import type { Deployments } from './deployments';
import { StackStatus } from '../util/cloudformation/stack-status';
import { makeBodyParameter, TemplateBodyParameter } from '../util/template-body-parameter';

export type ResourcesToImport = ResourceToImport[];
export type ResourceIdentifierSummaries = ResourceIdentifierSummary[];
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,10 @@ import type {
} from '@aws-sdk/client-cloudformation';
import * as chalk from 'chalk';
import * as uuid from 'uuid';
import type { SDK, SdkProvider, ICloudFormationClient } from './aws-auth';
import type { EnvironmentResources } from './environment-resources';
import { CfnEvaluationException } from './evaluate-cloudformation-template';
import { HotswapMode, HotswapPropertyOverrides, ICON } from './hotswap/common';
import { tryHotswapDeployment } from './hotswap-deployments';
import { addMetadataAssetsToManifest } from '../assets';
import { debug, info, warning } from '../logging';
import { AssetManifestBuilder } from './asset-manifest-builder';
import { publishAssets } from './asset-publishing';
import { addMetadataAssetsToManifest } from './assets';
import { determineAllowCrossAccountAssetPublishing } from './checks';
import {
changeSetHasNoChanges,
CloudFormationStack,
Expand All @@ -26,47 +23,20 @@ import {
ParameterValues,
ParameterChanges,
ResourcesToImport,
} from './util/cloudformation';
import { StackActivityMonitor, type StackActivityProgress } from './util/cloudformation/stack-activity-monitor';
import { type TemplateBodyParameter, makeBodyParameter } from './util/template-body-parameter';
import { AssetManifestBuilder } from '../util/asset-manifest-builder';
import { determineAllowCrossAccountAssetPublishing } from './util/checks';
import { publishAssets } from '../util/asset-publishing';
import { StringWithoutPlaceholders } from './util/placeholders';
import { ToolkitError } from '../toolkit/error';
import { formatErrorMessage } from '../util/error';

export type DeployStackResult =
| SuccessfulDeployStackResult
| NeedRollbackFirstDeployStackResult
| ReplacementRequiresRollbackStackResult
;

/** Successfully deployed a stack */
export interface SuccessfulDeployStackResult {
readonly type: 'did-deploy-stack';
readonly noOp: boolean;
readonly outputs: { [name: string]: string };
readonly stackArn: string;
}

/** The stack is currently in a failpaused state, and needs to be rolled back before the deployment */
export interface NeedRollbackFirstDeployStackResult {
readonly type: 'failpaused-need-rollback-first';
readonly reason: 'not-norollback' | 'replacement';
readonly status: string;
}

/** The upcoming change has a replacement, which requires deploying with --rollback */
export interface ReplacementRequiresRollbackStackResult {
readonly type: 'replacement-requires-rollback';
}

export function assertIsSuccessfulDeployStackResult(x: DeployStackResult): asserts x is SuccessfulDeployStackResult {
if (x.type !== 'did-deploy-stack') {
throw new ToolkitError(`Unexpected deployStack result. This should not happen: ${JSON.stringify(x)}. If you are seeing this error, please report it at https://github.com/aws/aws-cdk/issues/new/choose.`);
}
}
} from './cloudformation';
import { ChangeSetDeploymentMethod, DeploymentMethod } from './deployment-method';
import { DeployStackResult, SuccessfulDeployStackResult } from './deployment-result';
import { tryHotswapDeployment } from './hotswap-deployments';
import { debug, info, warning } from '../../logging';
import { ToolkitError } from '../../toolkit/error';
import { formatErrorMessage } from '../../util/error';
import type { SDK, SdkProvider, ICloudFormationClient } from '../aws-auth';
import type { EnvironmentResources } from '../environment-resources';
import { CfnEvaluationException } from '../evaluate-cloudformation-template';
import { HotswapMode, HotswapPropertyOverrides, ICON } from '../hotswap/common';
import { StackActivityMonitor, type StackActivityProgress } from '../util/cloudformation/stack-activity-monitor';
import { StringWithoutPlaceholders } from '../util/placeholders';
import { type TemplateBodyParameter, makeBodyParameter } from '../util/template-body-parameter';

export interface DeployStackOptions {
/**
Expand Down Expand Up @@ -251,36 +221,6 @@ export interface DeployStackOptions {
readonly assetParallelism?: boolean;
}

export type DeploymentMethod = DirectDeploymentMethod | ChangeSetDeploymentMethod;

export interface DirectDeploymentMethod {
readonly method: 'direct';
}

export interface ChangeSetDeploymentMethod {
readonly method: 'change-set';

/**
* Whether to execute the changeset or leave it in review.
*
* @default true
*/
readonly execute?: boolean;

/**
* Optional name to use for the CloudFormation change set.
* If not provided, a name will be generated automatically.
*/
readonly changeSetName?: string;

/**
* Indicates if the change set imports resources that already exist.
*
* @default false
*/
readonly importExistingResources?: boolean;
}

export async function deployStack(options: DeployStackOptions): Promise<DeployStackResult> {
const stackArtifact = options.stack;

Expand Down
29 changes: 29 additions & 0 deletions packages/aws-cdk/lib/api/deployments/deployment-method.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
export type DeploymentMethod = DirectDeploymentMethod | ChangeSetDeploymentMethod;

export interface DirectDeploymentMethod {
readonly method: 'direct';
}

export interface ChangeSetDeploymentMethod {
readonly method: 'change-set';

/**
* Whether to execute the changeset or leave it in review.
*
* @default true
*/
readonly execute?: boolean;

/**
* Optional name to use for the CloudFormation change set.
* If not provided, a name will be generated automatically.
*/
readonly changeSetName?: string;

/**
* Indicates if the change set imports resources that already exist.
*
* @default false
*/
readonly importExistingResources?: boolean;
}
33 changes: 33 additions & 0 deletions packages/aws-cdk/lib/api/deployments/deployment-result.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import { ToolkitError } from '../../toolkit/error';

export type DeployStackResult =
| SuccessfulDeployStackResult
| NeedRollbackFirstDeployStackResult
| ReplacementRequiresRollbackStackResult
;

/** Successfully deployed a stack */
export interface SuccessfulDeployStackResult {
readonly type: 'did-deploy-stack';
readonly noOp: boolean;
readonly outputs: { [name: string]: string };
readonly stackArn: string;
}

/** The stack is currently in a failpaused state, and needs to be rolled back before the deployment */
export interface NeedRollbackFirstDeployStackResult {
readonly type: 'failpaused-need-rollback-first';
readonly reason: 'not-norollback' | 'replacement';
readonly status: string;
}

/** The upcoming change has a replacement, which requires deploying with --rollback */
export interface ReplacementRequiresRollbackStackResult {
readonly type: 'replacement-requires-rollback';
}

export function assertIsSuccessfulDeployStackResult(x: DeployStackResult): asserts x is SuccessfulDeployStackResult {
if (x.type !== 'did-deploy-stack') {
throw new ToolkitError(`Unexpected deployStack result. This should not happen: ${JSON.stringify(x)}. If you are seeing this error, please report it at https://github.com/aws/aws-cdk/issues/new/choose.`);
}
}
Loading

0 comments on commit ac90399

Please sign in to comment.