Question: How do I customize a resource property value when there is a gap between CDK higher level constructs and a CloudFormation resource?

I want to modify a resource property value when there's a gap between AWS Cloud Development Kit (AWS CDK) L3/L2 constructs and an AWS CloudFormation.

Short descriptionIn some cases, higher level constructs (L3 and L2) will have a resource property that can't be modified. To work around this issue, use AWS CDK escape hatches to move to a lower level of abstraction and modify the resource property value.Example of an Amazon Virtual Private Cloud (Amazon VPC) using AWS CDK Python:vpc = ec2.Vpc(self, "MyCDKVPC",             max_azs=2,            cidr='60.0.0.0/16',            subnet_configuration=[                ec2.SubnetConfiguration(                    name="public",                    subnet_type=ec2.SubnetType.PUBLIC,                    cidr_mask=24,                ),                ec2.SubnetConfiguration(                    name="private",                    subnet_type=ec2.SubnetType.PRIVATE_WITH_NAT,                    cidr_mask=24,                )            ]        )The preceding example Amazon VPC is defined using the L2 construct aws_cdk.aws_ec2.Vpc, which has two Availability Zones (AZ) with the CidrBlock set to 60.0.0.0/16. The example Amazon VPC also contains two PublicSubnets and two PrivateSubnets spread across the two AZs.When generating a CloudFormation to check the AWS::EC2::Subnet resource, the CidrBlock will start from the first IP range 60.0.0.0/24 and can't be modified.PublicSubnet1:    Type: AWS::EC2::Subnet    Properties:      ...      CidrBlock: 60.0.0.0/24  PublicSubnet2:    Type: AWS::EC2::Subnet    Properties:      ...      CidrBlock: 60.0.1.0/24  PrivateSubnet1:    Type: AWS::EC2::Subnet    Properties:      ...      CidrBlock: 60.0.2.0/24  PrivateSubnet2:    Type: AWS::EC2::Subnet    Properties:      ...      CidrBlock: 60.0.3.0/24To resolve this issue, do these steps:Retrieve generated subnets inside the Amazon VPC (which are the L2 PublicSubnet construct and the L2 PrivateSubnet construct).Use the AWS CDK escape hatch, node.default_child, on the L2 constructs and cast it as the L1 CfnSubnet resource.Modify the cidr_block directly or by using raw overrides.Verify the cidr_block update on the CloudFormation template.

ResolutionTo use an AWS CDK escape hatch to modify the CidrBlock value of a lower abstraction layer for PublicSubnets or PrivateSubnets, do these steps:Important: The following steps apply to PublicSubnets. To apply to PrivateSubnets, replace all instances of PublicSubnet with PrivateSubnet.1.    Retrieve a list of PublicSubnets in the Amazon VPC by using the vpc.public_subnets attribute:public_subnets = vpc.public_subnetsNote: Each element inside the generated list is a L2 PublicSubnet construct. See the following example printout:########## confirm public_subnets is a L2 construct ##########print(public_subnets)  # printout: [<aws_cdk.aws_ec2.PublicSubnet object at 0x7f3f48acb490>, <aws_cdk.aws_ec2.PublicSubnet object at 0x7f3f48acb0502.    Use the node.default_child attribute on the desired L2 construct (for this example aws_cdk.aws_ec2.PublicSubnet). Then, cast it as the L1 CfnSubnet resource (for this example aws_cdk.aws_ec2.CfnSubnet):########## confirm cfn_public_subnet is a L1 construct ##########for public_subnet in public_subnets:    cfn_public_subnet = public_subnet.node.default_child     print(cfn_public_subnet)     # printout: <aws_cdk.aws_ec2.CfnSubnet object at 0x7f3f48acb710>    # printout: <aws_cdk.aws_ec2.CfnSubnet object at 0x7f3f48acb950>3.    After accessing the L1 CfnSubnet resource, modify the CidrBlock on the L1 CfnSubnet construct by using one of the following methods:Modify the cidr_block directlyModify the cidr_block by using raw overridesExample of modifying the cidr_block directly or by using raw overrides:public_subnets = vpc.public_subnets        public_subnet_index = 0                for public_subnet in public_subnets:            cfn_public_subnet = public_subnet.node.default_child                        ########### 1) modify the cidr_block property directly ###########            cfn_public_subnet.cidr_block = "60.0." + str(public_subnet_index + example_start_value) + ".0/24")                        ########### 2) modify the cidr_block by using raw overrides ###########            cfn_public_subnet.add_property_override("CidrBlock", "60.0." + str(public_subnet_index + example_start_value) + ".0/24")                        public_subnet_index += 1Important: Make sure to replace example_start_value with your specified value. For example, if you want to modify your public_subnet to start from 60.0.100.0/24, then set your example_start_value to 100.4.    Verify the CidrBlock update inside the AWS::EC2::Subnet resource on the newly generated CloudFormation template by running the cdk synth command:cdk synthExample output:PublicSubnet1:    Type: AWS::EC2::Subnet    Properties:      ...      CidrBlock: 60.0.100.0/24 <---  PublicSubnet2:    Type: AWS::EC2::Subnet    Properties:      ...      CidrBlock: 60.0.101.0/24  PrivateSubnet1:    Type: AWS::EC2::Subnet    Properties:      ...      CidrBlock: <example_custom_value>/24  PrivateSubnet2:    Type: AWS::EC2::Subnet    Properties:      ...      CidrBlock: <example_custom_value>/24Related informationPrivateSubnetvpc.private_subnets