diff --git a/packages/@aws-cdk/aws-autoscaling/lib/lifecycle-hook.ts b/packages/@aws-cdk/aws-autoscaling/lib/lifecycle-hook.ts index 8ad24858ddaee..200a6b7045a41 100644 --- a/packages/@aws-cdk/aws-autoscaling/lib/lifecycle-hook.ts +++ b/packages/@aws-cdk/aws-autoscaling/lib/lifecycle-hook.ts @@ -3,6 +3,7 @@ import iam = require('@aws-cdk/aws-iam'); import cdk = require('@aws-cdk/cdk'); import { IAutoScalingGroup } from './auto-scaling-group'; import { cloudformation } from './autoscaling.generated'; +import { LazyDependable } from './util'; /** * Basic properties for a lifecycle hook @@ -95,6 +96,14 @@ export class LifecycleHook extends cdk.Construct implements api.ILifecycleHook { roleArn: this.role.roleArn, }); + // A LifecycleHook resource is going to do a permissions test upon creation, + // so we have to make sure the role has full permissions before creating the + // lifecycle hook. + // The LazyDependable makes sure we take a dependency on anything that gets + // added to the dependencyElements array, even if it happens after this + // point. + resource.addDependency(new LazyDependable(this.role)); + this.lifecycleHookName = resource.lifecycleHookName; } } diff --git a/packages/@aws-cdk/aws-autoscaling/lib/util.ts b/packages/@aws-cdk/aws-autoscaling/lib/util.ts new file mode 100644 index 0000000000000..01301981713da --- /dev/null +++ b/packages/@aws-cdk/aws-autoscaling/lib/util.ts @@ -0,0 +1,12 @@ +import cdk = require('@aws-cdk/cdk'); +/** + * Allow lazy evaluation of a list of dependables + */ +export class LazyDependable implements cdk.IDependable { + constructor(private readonly dependableSource: cdk.IDependable) { + } + + public get dependencyElements(): cdk.IDependable[] { + return this.dependableSource.dependencyElements; + } +} \ No newline at end of file diff --git a/packages/@aws-cdk/aws-autoscaling/test/test.lifecyclehooks.ts b/packages/@aws-cdk/aws-autoscaling/test/test.lifecyclehooks.ts index 18ec1d112199e..70b7858be3a3a 100644 --- a/packages/@aws-cdk/aws-autoscaling/test/test.lifecyclehooks.ts +++ b/packages/@aws-cdk/aws-autoscaling/test/test.lifecyclehooks.ts @@ -1,4 +1,4 @@ -import { expect, haveResource } from '@aws-cdk/assert'; +import { expect, haveResource, ResourcePart } from '@aws-cdk/assert'; import autoscaling_api = require('@aws-cdk/aws-autoscaling-api'); import ec2 = require('@aws-cdk/aws-ec2'); import iam = require('@aws-cdk/aws-iam'); @@ -31,6 +31,14 @@ export = { NotificationTargetARN: "target:arn", })); + // Lifecycle Hook has a dependency on the policy object + expect(stack).to(haveResource('AWS::AutoScaling::LifecycleHook', { + DependsOn: [ + "ASGLifecycleHookTransitionRole3AAA6BB7", + "ASGLifecycleHookTransitionRoleDefaultPolicy2E50C7DB" + ] + }, ResourcePart.CompleteDefinition)); + expect(stack).to(haveResource('AWS::IAM::Role', { AssumeRolePolicyDocument: { Statement: [ diff --git a/packages/@aws-cdk/aws-ecs/test/ec2/integ.lb-awsvpc-nw.expected.json b/packages/@aws-cdk/aws-ecs/test/ec2/integ.lb-awsvpc-nw.expected.json index 59c11214bb09f..6db17a600e7e2 100644 --- a/packages/@aws-cdk/aws-ecs/test/ec2/integ.lb-awsvpc-nw.expected.json +++ b/packages/@aws-cdk/aws-ecs/test/ec2/integ.lb-awsvpc-nw.expected.json @@ -686,7 +686,11 @@ "Arn" ] } - } + }, + "DependsOn": [ + "EcsClusterDefaultAutoScalingGroupLifecycleHookDrainHookRoleA38EC83B", + "EcsClusterDefaultAutoScalingGroupLifecycleHookDrainHookRoleDefaultPolicy75002F88" + ] }, "TaskDefTaskRole1EDB4A67": { "Type": "AWS::IAM::Role", diff --git a/packages/@aws-cdk/aws-ecs/test/ec2/integ.lb-bridge-nw.expected.json b/packages/@aws-cdk/aws-ecs/test/ec2/integ.lb-bridge-nw.expected.json index 142dcdb1f2580..7b6ed2f8fae52 100644 --- a/packages/@aws-cdk/aws-ecs/test/ec2/integ.lb-bridge-nw.expected.json +++ b/packages/@aws-cdk/aws-ecs/test/ec2/integ.lb-bridge-nw.expected.json @@ -707,7 +707,11 @@ "Arn" ] } - } + }, + "DependsOn": [ + "EcsClusterDefaultAutoScalingGroupLifecycleHookDrainHookRoleA38EC83B", + "EcsClusterDefaultAutoScalingGroupLifecycleHookDrainHookRoleDefaultPolicy75002F88" + ] }, "TaskDefTaskRole1EDB4A67": { "Type": "AWS::IAM::Role",