From e7526dde0a18059f4fd3b7ee0c4c9aa0017bd136 Mon Sep 17 00:00:00 2001 From: Mate GABRI Date: Sat, 15 Jun 2019 16:35:20 +1000 Subject: [PATCH] feat(app-delivery): Add CAPABILITY_AUTO_EXPAND (#2851) Add CAPABILITY_AUTO_EXPAND to the default capabilities of the CloudFormation stack deploy role. --- .../lib/pipeline-deploy-stack-action.ts | 10 ++--- .../test/test.pipeline-deploy-stack-action.ts | 38 ++++++++++++++++++- 2 files changed, 42 insertions(+), 6 deletions(-) diff --git a/packages/@aws-cdk/app-delivery/lib/pipeline-deploy-stack-action.ts b/packages/@aws-cdk/app-delivery/lib/pipeline-deploy-stack-action.ts index 8570fe3b7926c..bc8cbf9dbafa7 100644 --- a/packages/@aws-cdk/app-delivery/lib/pipeline-deploy-stack-action.ts +++ b/packages/@aws-cdk/app-delivery/lib/pipeline-deploy-stack-action.ts @@ -63,7 +63,7 @@ export interface PipelineDeployStackActionProps { * information * * @see https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/using-iam-template.html#using-iam-capabilities - * @default [AnonymousIAM], unless `adminPermissions` is true + * @default [AnonymousIAM, AutoExpand], unless `adminPermissions` is true */ readonly capabilities?: cfn.CloudFormationCapabilities[]; @@ -168,11 +168,11 @@ export class PipelineDeployStackAction extends cdk.Construct { function cfnCapabilities(adminPermissions: boolean, capabilities?: cfn.CloudFormationCapabilities[]): cfn.CloudFormationCapabilities[] { if (adminPermissions && capabilities === undefined) { - // admin true default capability to NamedIAM - return [cfn.CloudFormationCapabilities.NamedIAM]; + // admin true default capability to NamedIAM and AutoExpand + return [cfn.CloudFormationCapabilities.NamedIAM, cfn.CloudFormationCapabilities.AutoExpand]; } else if (capabilities === undefined) { - // else capabilities are undefined set AnonymousIAM - return [cfn.CloudFormationCapabilities.AnonymousIAM]; + // else capabilities are undefined set AnonymousIAM and AutoExpand + return [cfn.CloudFormationCapabilities.AnonymousIAM, cfn.CloudFormationCapabilities.AutoExpand]; } else { // else capabilities are defined use them return capabilities; diff --git a/packages/@aws-cdk/app-delivery/test/test.pipeline-deploy-stack-action.ts b/packages/@aws-cdk/app-delivery/test/test.pipeline-deploy-stack-action.ts index c8d53b5cc8505..5fa390ab01a0e 100644 --- a/packages/@aws-cdk/app-delivery/test/test.pipeline-deploy-stack-action.ts +++ b/packages/@aws-cdk/app-delivery/test/test.pipeline-deploy-stack-action.ts @@ -86,12 +86,20 @@ export = nodeunit.testCase({ const stackWithAnonymousCapability = new cdk.Stack(undefined, 'AnonymousIAM', { env: { account: '123456789012', region: 'us-east-1' } }); + const stackWithAutoExpandCapability = new cdk.Stack(undefined, 'AutoExpand', + { env: { account: '123456789012', region: 'us-east-1' } }); + + const stackWithAnonymousAndAutoExpandCapability = new cdk.Stack(undefined, 'AnonymousIAMAndAutoExpand', + { env: { account: '123456789012', region: 'us-east-1' } }); + const selfUpdatingStack = createSelfUpdatingStack(pipelineStack); const pipeline = selfUpdatingStack.pipeline; const selfUpdateStage1 = pipeline.addStage({ name: 'SelfUpdate1' }); const selfUpdateStage2 = pipeline.addStage({ name: 'SelfUpdate2' }); const selfUpdateStage3 = pipeline.addStage({ name: 'SelfUpdate3' }); + const selfUpdateStage4 = pipeline.addStage({ name: 'SelfUpdate4' }); + const selfUpdateStage5 = pipeline.addStage({ name: 'SelfUpdate5' }); new PipelineDeployStackAction(pipelineStack, 'SelfUpdatePipeline', { stage: selfUpdateStage1, @@ -114,6 +122,20 @@ export = nodeunit.testCase({ capabilities: [cfn.CloudFormationCapabilities.AnonymousIAM], adminPermissions: false, }); + new PipelineDeployStackAction(pipelineStack, 'DeployStack3', { + stage: selfUpdateStage4, + stack: stackWithAutoExpandCapability, + input: selfUpdatingStack.synthesizedApp, + capabilities: [cfn.CloudFormationCapabilities.AutoExpand], + adminPermissions: false, + }); + new PipelineDeployStackAction(pipelineStack, 'DeployStack4', { + stage: selfUpdateStage5, + stack: stackWithAnonymousAndAutoExpandCapability, + input: selfUpdatingStack.synthesizedApp, + capabilities: [cfn.CloudFormationCapabilities.AnonymousIAM, cfn.CloudFormationCapabilities.AutoExpand], + adminPermissions: false, + }); expect(pipelineStack).to(haveResource('AWS::CodePipeline::Pipeline', hasPipelineAction({ Configuration: { StackName: "TestStack", @@ -148,6 +170,20 @@ export = nodeunit.testCase({ ActionMode: "CHANGE_SET_REPLACE", } }))); + expect(pipelineStack).to(haveResource('AWS::CodePipeline::Pipeline', hasPipelineAction({ + Configuration: { + StackName: "AutoExpand", + ActionMode: "CHANGE_SET_REPLACE", + Capabilities: "CAPABILITY_AUTO_EXPAND", + } + }))); + expect(pipelineStack).to(haveResource('AWS::CodePipeline::Pipeline', hasPipelineAction({ + Configuration: { + StackName: "AnonymousIAMAndAutoExpand", + ActionMode: "CHANGE_SET_REPLACE", + Capabilities: "CAPABILITY_IAM,CAPABILITY_AUTO_EXPAND", + } + }))); test.done(); }, 'users can use admin permissions'(test: nodeunit.Test) { @@ -178,7 +214,7 @@ export = nodeunit.testCase({ Configuration: { StackName: "TestStack", ActionMode: "CHANGE_SET_REPLACE", - Capabilities: "CAPABILITY_NAMED_IAM", + Capabilities: "CAPABILITY_NAMED_IAM,CAPABILITY_AUTO_EXPAND", } }))); test.done();