cdk-bootstrapless-synthesizer
A bootstrapless stack synthesizer that is designated to generate templates that can be directly used by AWS CloudFormation.
Please use ^1.0.0 for cdk version 1.x.x, use ^2.0.0 for cdk version 2.x.x
Usage
import { BootstraplessStackSynthesizer } from 'cdk-bootstrapless-synthesizer';
main.ts
const app = new App();
new MyStack(app, 'my-stack-dev', {
synthesizer: new BootstraplessStackSynthesizer({
templateBucketName: 'cfn-template-bucket',
fileAssetBucketName: 'file-asset-bucket-${AWS::Region}',
fileAssetRegionSet: ['us-west-1', 'us-west-2'],
fileAssetPrefix: 'file-asset-prefix/latest/',
imageAssetRepositoryName: 'your-ecr-repo-name',
imageAssetAccountId: '1234567890',
imageAssetTagPrefix: 'latest-',
imageAssetRegionSet: ['us-west-1', 'us-west-2'],
}),
});
env.BSS_TEMPLATE_BUCKET_NAME = 'cfn-template-bucket';
env.BSS_FILE_ASSET_BUCKET_NAME = 'file-asset-bucket-\${AWS::Region}';
env.BSS_FILE_ASSET_REGION_SET = 'us-west-1,us-west-2';
env.BSS_FILE_ASSET_PREFIX = 'file-asset-prefix/latest/';
env.BSS_IMAGE_ASSET_REPOSITORY_NAME = 'your-ecr-repo-name';
env.BSS_IMAGE_ASSET_ACCOUNT_ID = '1234567890';
env.BSS_IMAGE_ASSET_TAG_PREFIX = 'latest-';
env.BSS_IMAGE_ASSET_REGION_SET = 'us-west-1,us-west-2';
new MyStack(app, 'my-stack-dev2', {
synthesizer: new BootstraplessStackSynthesizer(),
});
main.ts
Synth AWS CloudFormation templates, assets and upload them
$ cdk synth
$ npx cdk-assets publish -p cdk.out/my-stack-dev.assets.json -v
Limitations
When using BSS_IMAGE_ASSET_ACCOUNT_ID
to push ECR repository to shared account, you need use Aspect
to grant the role with policy to pull the repository from cross account. Or using the following WithCrossAccount
techniques.
Currently only below scenarios are supported,
- ECS
- SageMaker training job integrated with Step Functions
- AWS Batch
- AWS Lambda
For other scenarios, the feature request or pull request are welcome.
function OverrideRepositoryAccount(scope: Construct, id: string, repo: IRepository): IRepository {
class Import extends RepositoryBase {
public repositoryName = repo.repositoryName;
public repositoryArn = Repository.arnForLocalRepository(repo.repositoryName, scope, env.BSS_IMAGE_ASSET_ACCOUNT_ID);
public addToResourcePolicy(_statement: iam.PolicyStatement): iam.AddToResourcePolicyResult {
return { statementAdded: false };
}
}
return new Import(scope, id);
}
function WithCrossAccount(image: DockerImageAsset): DockerImageAsset {
image.repository = OverrideRepositoryAccount(image, 'CrossAccountRepo', image.repository);
return image;
}
export class SampleStack extends Stack {
constructor(scope: Construct, id: string, props: StackProps = {}) {
super(scope, id, props);
const image = WithCrossAccount(new DockerImageAsset(this, 'MyBuildImage', {
directory: path.join(__dirname, '../docker'),
}));
new CfnOutput(this, 'output', { value: image.imageUri });
const taskDefinition = new ecs.FargateTaskDefinition(this, 'TaskDef');
taskDefinition.addContainer('DefaultContainer', {
image: ecs.ContainerImage.fromDockerImageAsset(image),
memoryLimitMiB: 512,
});
fromAsset(this, 'stepfunctions', {
directory: path.join(__dirname, '../docker'),
});
}
}
main.ts
Sample Project
See Sample Project
API Reference
See API Reference for API details.