4
votes

I'm using CDK to create a stack with some ELB resources. Everything seems to be working correctly, but I end up with two CloudFormation stacks. One named demo and another that has a randomly generated name like awseb-e-jkmuguqm3e-stack.

The demo stack has the ElasticBeanstalk Application and Environment, but the other stack has a bunch of load balancer resources, including an AutoScalingGroup, LaunchConfiguration, ScalingPolicy, etc, that I assume are created as part of the ELB stuff, but I would think they'd end up in the same stack?

disclaimer: this might be entirely expected behavior, as everything works, but being new to CDK I figured someone might know why i get an extra stack here, and maybe there is something I can do to prevent it

I've defined an AppStack (cdk-app/index.ts):

export class AppStack extends cdk.Stack {
  constructor(scope: cdk.App, id: string, props?: cdk.StackProps) {
    super(scope, id, props);


    const stackName = _.get(props, ['stackName'], '');

    const app = new elasticBeanstalk.CfnApplication(this, `${stackName}EbsApplication`, {
      applicationName: `${_.toLower(stackName)}-ebs-app`
    });

    const ebsInstanceRole = new iam.Role(
      this,
      `${stackName}EBSInstanceRole`,
      {
        roleName: `${_.toLower(stackName)}-ebs-role`,
        assumedBy: new iam.ServicePrincipal('ec2.amazonaws.com'),
      }
    );

    // create an instance profile the that instances in our EBS environment will use
    const ebsInstanceProfile = new iam.CfnInstanceProfile(
      this,
      `${stackName}InstanceProfile`,
      {
        instanceProfileName: `${_.toLower(stackName)}-ebs-instance-profile`,
        roles: [
          ebsInstanceRole.roleName,
        ],
      }
    );

    const env = new elasticBeanstalk.CfnEnvironment(this, 'Environment', {
      environmentName: `${_.toLower(stackName)}-ebs-env`,
      applicationName: `${_.toLower(stackName)}-ebs-app`,
      solutionStackName: '64bit Amazon Linux 2 v5.0.2 running Node.js 12',
      optionSettings: [
        {
          namespace: 'aws:autoscaling:launchconfiguration',
          optionName: 'IamInstanceProfile',
          value: ebsInstanceProfile.instanceProfileName,

        }
      ]
    });
  }
}

export default AppStack;

I use the stack (index.ts):

import AppStack from "./cdk-app";

const app = new cdk.App();

const appStack = new AppStack(app, 'demoAppStack', { stackName: 'demo' });

app.synth();
1
cant see where you create a stack. the code just creates resources with a prefix from a variable called stackName - Logemann
@Marc sorry, this code all lives within the constructor for a stack, I'll update the example - Donald P
Without knowing much about the stack code itself I want to bring up two things to clarify here. 1. You have exported the stack twice export class AppStack extends cdk.Stack and export default AppStack; 2. How are you importing the stack when you are using it just before app.synth();? - dmahapatro
@dmahapatro im importing it using the default export, ie import App stack from '../AppStack', I'll update example code. It is exporting twice but I don't think that should matter (the named export doesn't get used). Thank you for looking it over. - Donald P
@Elegie I have not :/ - Donald P

1 Answers

0
votes

I believe this is just how Elastic Beanstalk works. It creates a nested stack for you (i.e., awseb-e-jkmuguqm3e-stack in your case). If you want to avoid it, I think you'd need to stop using Elastic Beanstalk.

Also worth noting what you are seeing is not CDK-specific. You'll also see the additional 'random' stack created when defining an EB stack using Cloudformation and when creating an EB environment via the AWS console.