Ejemplo n.º 1
0
    def test_parameter_label_replace(self):
        t = Template()
        p1 = t.add_parameter(Parameter("Foo"))
        t.add_parameter(Parameter("Bar"))
        t.set_parameter_label(p1, "Foo label")
        t.set_parameter_label("Foo", "Bar label")

        self.assertEqual(t.metadata, {
            "AWS::CloudFormation::Interface": {
                "ParameterLabels": {
                    "Foo": {"default": "Bar label"},
                },
            },
        })
Ejemplo n.º 2
0
import custom_resources.awslambda
import custom_resources.cloudformation
import cfnutils.output

template = Template()

custom_resources.use_custom_resources_stack_name_parameter(template)

param_role = template.add_parameter(
    Parameter(
        "Role",
        Default="arn:aws:iam::000000000000:role/xxx",
        Type=constants.STRING,
        Description="ARN of role to run as",
    ))
template.set_parameter_label(param_role, "Lambda role ARN")

param_s3_bucket_name = template.add_parameter(
    Parameter(
        "S3BucketName",
        Default="",
        Type=constants.STRING,
        Description="Location of the Lambda ZIP file, bucket name",
    ))
template.set_parameter_label(param_s3_bucket_name, "Lambda S3 bucket")

param_s3_key = template.add_parameter(
    Parameter(
        "S3Key",
        Default="",
        Type=constants.STRING,
Ejemplo n.º 3
0
param_authorizer_param_stack = template.add_parameter(
    Parameter(
        "AuthorizerParamStackParam",
        Type=constants.STRING,
        Default="authorizer-params",
        Description="StackName of the Params stack",
    ))

param_authorizer_lae_arn = template.add_parameter(
    Parameter(
        "AuthorizerLaeParam",
        Type="AWS::SSM::Parameter::Value<String>",
        Default='/authorizer/lae-arn',
        Description="Parameter name to get Lambda@Edge ARN from",
    ))
template.set_parameter_label(param_authorizer_lae_arn,
                             "Authorizer Lambda@Edge parameter")

param_label = template.add_parameter(
    Parameter(
        "Label",
        Default="example.authorizer",
        Type=constants.STRING,
        Description=
        "Label inside the Hosted Zone to create. e.g. 'authorizer' for 'authorizer.example.org'",
    ))
template.set_parameter_label(param_label, "Label")

param_hosted_zone_name = template.add_parameter(
    Parameter(
        "HostedZone",
        Default="example.org",
Ejemplo n.º 4
0
    Description='SSH keypair that the instance will be deployed with.',
    Type=constants.KEY_PAIR_NAME,
))

instance_type = t.add_parameter(Parameter(
    'InstanceType',
    Description='The EC2 instance type.',
    Default='t3.small',
    Type='String',
    AllowedValues=[
        't3.micro', 't3.small',
        't3.small', 't3.medium',
        't3.large', 't3.xlarge',
    ],
))
t.set_parameter_label(instance_type, 'Instance Type')

###########################################
#             Security Group
###########################################

ec2_security_group = t.add_resource(SecurityGroup(
    'Ec2SecurityGroup',
    VpcId=Ref(vpc),
    GroupDescription='Security group for Minecraft EC2 instance.',
    Tags=Tags(
        Name=Sub('$minecraft-sg'),
    )
))

ec2_minecraft_tcp_ingress = t.add_resource(SecurityGroupIngress(
Ejemplo n.º 5
0
    GetAtt, ImportValue
import custom_resources.ssm
import custom_resources.cloudformation
import cfnutils.output

template = Template()

custom_resources.use_custom_resources_stack_name_parameter(template)

param_authorizer_stack = template.add_parameter(
    Parameter(
        "ParamAuthorizerStack",
        Default="authorizer",
        Type=constants.STRING,
    ))
template.set_parameter_label(param_authorizer_stack, "Authorizer StackName")

param_laearn = template.add_parameter(
    Parameter(
        "ParamLaeArn",
        Type=constants.STRING,
        Description="ARN of the Lambda@Edge function",
    ))
template.set_parameter_label(param_laearn, "Lambda@Edge ARN")

cloudformation_tags = template.add_resource(
    custom_resources.cloudformation.Tags("CfnTags"))

# Don't simply import-output the Lambda@Edge ARN, but do it via a Parameter
# This allows us to migrate to a new L@E function gradually (otherwise, the output value would be locked and can't
# change)
import cfnutils.output

template = Template()

custom_resources.use_custom_resources_stack_name_parameter(template)

template.add_transform('AWS::Serverless-2016-10-31')

param_s3_bucket_name = template.add_parameter(
    Parameter(
        "S3BucketName",
        Default="",
        Type=constants.STRING,
        Description="Location of the Lambda ZIP file, bucket name",
    ))
template.set_parameter_label(param_s3_bucket_name, "Lambda S3 bucket")

param_s3_key = template.add_parameter(
    Parameter(
        "S3Key",
        Default="",
        Type=constants.STRING,
        Description="Location of the Lambda ZIP file, path",
    ))
template.set_parameter_label(param_s3_key, "Lambda S3 key")

param_label = template.add_parameter(
    Parameter(
        "Label",
        Default="authorizer",
        Type=constants.STRING,
def main():

    t = Template()
    AddAMIMap(t)

    t.set_version("2010-09-09")

    t.set_description(
        "DCV 2017 Remote Desktop with Xilinx Vivado (using AWS FPGA Developer AMI)"
    )

    tags = Tags(Name=Ref("AWS::StackName"))

    # user data
    InstUserData = list()
    InstUserData = [
        '#!/usr/bin/env bash\n',
        '\n',
        'set -x\n',
        '\n',
        '##exit 0\n',  # use this to disable all user-data and bring up files
        '\n',
        'my_wait_handle="', Ref('InstanceWaitHandle'), '"\n',
        'user_name="', Ref('UserName'), '"\n',
        'user_pass="******"\n',
        '\n',
    ]

    with open('_include/dcv-install.sh', 'r',) as ud_file:
        user_data_file = ud_file.readlines()

    for l in user_data_file:
        InstUserData.append(l)

    VPCId = t.add_parameter(Parameter(
        'VPCId',
        Type="AWS::EC2::VPC::Id",
        Description="VPC ID for where the remote desktop instance should be launched"
    ))
    t.set_parameter_label(VPCId, "VPC ID")
    t.add_parameter_to_group(VPCId, "Instance Configuration")

    Subnet = t.add_parameter(Parameter(
        'Subnet',
        Type="AWS::EC2::Subnet::Id",
        Description="For the Subnet ID, you should choose one in the "
                    "Availability Zone where you want the instance launched"
    ))
    t.set_parameter_label(Subnet, "Subnet ID")
    t.add_parameter_to_group(Subnet, "Instance Configuration")

    ExistingSecurityGroup = t.add_parameter(Parameter(
        'ExistingSecurityGroup',
        Type="String",
        Default="NO_VALUE",
        Description="OPTIONAL: Needs to be a SG ID, for example sg-abcd1234efgh. "
                    "This is an already existing Security Group ID that is "
                    "in the same VPC, this is an addition to the security groups that "
                    "are automatically created to enable access to the remote desktop,"
                    "leave as NO_VALUE if you choose not to use this"
    ))
    t.set_parameter_label(ExistingSecurityGroup, "OPTIONAL: Existing Security Group (e.g. sg-abcd1234efgh)")
    t.add_parameter_to_group(ExistingSecurityGroup, "Instance Configuration")

    remoteDesktopInstanceType = t.add_parameter(Parameter(
        'remoteDesktopInstanceType',
        Type="String",
        Description="This is the instance type that will be used. As this is a "
                    "2D workstation, we are not supporting GPU instance types.",
        Default="m4.xlarge",
        AllowedValues=[
            "m4.large",
            "m4.xlarge",
            "m4.2xlarge",
            "m4.4xlarge",
            "m4.10xlarge",
            "m5.large",
            "m5.xlarge",
            "m5.2xlarge",
            "m5.4xlarge",
            "m5.12xlarge",
            "m5.24xlarge",
            "z1d.large",
            "z1d.xlarge",
            "z1d.2xlarge",
            "z1d.3xlarge",
            "z1d.6xlarge",
            "z1d.12xlarge",
            "z1d.metal"
        ],
        ConstraintDescription= "Must an EC2 instance type from the list"
    ))
    t.set_parameter_label(remoteDesktopInstanceType, "Remote Desktop Instance Type")
    t.add_parameter_to_group(remoteDesktopInstanceType, "Instance Configuration")

    EC2KeyName = t.add_parameter(Parameter(
        'EC2KeyName',
        Type="AWS::EC2::KeyPair::KeyName",
        Description="Name of an existing EC2 KeyPair to enable SSH access to the instance.",
        ConstraintDescription="REQUIRED: Must be a valid EC2 key pair"
    ))
    t.set_parameter_label(EC2KeyName, "EC2 Key Name")
    t.add_parameter_to_group(EC2KeyName, "Instance Configuration")

    OperatingSystem = t.add_parameter(Parameter(
        'OperatingSystem',
        Type="String",
        Description="Operating System of the AMI",
        Default="centos7",
        AllowedValues=[
            "centos7"
        ],
        ConstraintDescription="Must be: centos7"
    ))
    t.set_parameter_label(OperatingSystem, "Operating System of AMI")
    t.add_parameter_to_group(OperatingSystem, "Instance Configuration")

    StaticPrivateIpAddress = t.add_parameter(Parameter(
        'StaticPrivateIpAddress',
        Type="String",
        Default="NO_VALUE",
        Description="OPTIONAL: If you already have a private VPC address range, you can "
                    "specify the private IP address to use, leave as NO_VALUE if you choose not to use this",
    ))
    t.set_parameter_label(StaticPrivateIpAddress, "OPTIONAL: Static Private IP Address")
    t.add_parameter_to_group(StaticPrivateIpAddress, "Instance Configuration")

    UsePublicIp = t.add_parameter(Parameter(
        'UsePublicIp',
        Type="String",
        Description="Should a public IP address be given to the instance, "
                    "this is overridden by CreateElasticIP=True",
        Default="True",
        ConstraintDescription="True/False",
        AllowedValues=[
            "True",
            "False"
        ]
    ))
    t.set_parameter_label(UsePublicIp, "Assign a public IP Address")
    t.add_parameter_to_group(UsePublicIp, "Instance Configuration")

    CreateElasticIP = t.add_parameter(Parameter(
        'CreateElasticIP',
        Type="String",
        Description="Should an Elastic IP address be created and assigned, "
                    "this allows for persistent IP address assignment",
        Default="True",
        ConstraintDescription="True/False",
        AllowedValues=[
            "True",
            "False"
        ]
    ))
    t.set_parameter_label(CreateElasticIP, "Create an Elastic IP address")
    t.add_parameter_to_group(CreateElasticIP, "Instance Configuration")

    S3BucketName = t.add_parameter(Parameter(
        'S3BucketName',
        Type="String",
        Default="NO_VALUE",
        Description="OPTIONAL: S3 bucket to allow this instance read access (List and Get),"
                    "leave as NO_VALUE if you choose not to use this"
    ))
    t.set_parameter_label(S3BucketName, "OPTIONAL: S3 bucket for read access")
    t.add_parameter_to_group(S3BucketName, "Instance Configuration")

    AccessCidr = t.add_parameter(Parameter(
        'AccessCidr',
        Type="String",
        Description="This is the CIDR block for allowing remote access, for ports 22 and 8443",
        Default="111.222.333.444/32",
        AllowedPattern="(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})\\.(\\d{1,3})/(\\d{1,2})",
        ConstraintDescription="Must be a valid CIDR x.x.x.x/x"
    ))
    t.set_parameter_label(AccessCidr, "CIDR block for remote access (ports 22 and 8443)")
    t.add_parameter_to_group(AccessCidr, "Instance Configuration")

    UserName = t.add_parameter(Parameter(
        'UserName',
        Type="String",
        Description="User name for DCV remote desktop login, default is \"simuser\".",
        Default="simuser",
        MinLength="4",
    ))
    t.set_parameter_label(UserName, "User name for DCV login")
    t.add_parameter_to_group(UserName, "DCV Configuration")

    UserPass = t.add_parameter(Parameter(
        'UserPass',
        Type="String",
        Description="Password for DCV remote desktop login. The default password is Ch4ng3M3!",
        Default="Ch4ng3M3!",
        MinLength="8",
        AllowedPattern="^((?=.*[a-z])(?=.*[A-Z])(?=.*[\\d])|(?=.*[a-z])(?=.*[A-Z])(?=.*[\\W_])|(?=.*[a-z])(?=.*[\\d])(?=.*[\\W_])|(?=.*[A-Z])(?=.*[\\d])(?=.*[\\W_])).+$",
        ConstraintDescription="Password must contain at least one element from three of the following sets: lowercase letters, uppercase letters, base 10 digits, non-alphanumeric characters",
        NoEcho=True
    ))
    t.set_parameter_label(UserPass, "Password for DCV login")
    t.add_parameter_to_group(UserPass, "DCV Configuration")


    # end parameters

    RootRole = t.add_resource(iam.Role(
        "RootRole",
        AssumeRolePolicyDocument={
            "Version": "2012-10-17",
            "Statement": [ {
                "Effect": "Allow",
                "Principal": {
                    "Service": ["ec2.amazonaws.com"],
                 },
                "Action": ["sts:AssumeRole"]
            }]
        }
    ))

    dcvBucketPolicy= t.add_resource(PolicyType(
        "dcvBucketPolicy",
        PolicyName="dcvBucketPolicy",
        Roles=[Ref(RootRole)],
        PolicyDocument={
            "Version": "2012-10-17",
            "Statement": [
                {
                    "Effect": "Allow",
                    "Action": ["s3:GetObject"],
                    "Resource": "arn:aws:s3:::dcv-license.us-east-1/*"
                }
            ],
        },
    )),

    BucketPolicy= t.add_resource(PolicyType(
        "BucketPolicy",
        PolicyName="BucketPolicy",
        Roles=[Ref(RootRole)],
        PolicyDocument={
            "Version": "2012-10-17",
            "Statement": [
                {
                    "Effect": "Allow",
                    "Action": ["s3:GetObject"],
                    "Resource": {"Fn::Join":["", ["arn:aws:s3:::", {"Ref": "S3BucketName"},"/*"]]}
                },
                {
                    "Effect": "Allow",
                    "Action": [ "s3:ListBucket"],
                    "Resource": {"Fn::Join":["", ["arn:aws:s3:::", {"Ref": "S3BucketName"}]]}
                }
            ],
        },
        Condition="Has_Bucket"
    )),

    remoteDesktopSecurityGroup = t.add_resource(SecurityGroup(
        "remoteDesktopSecurityGroup",
        VpcId = Ref(VPCId),
        GroupDescription = "Remote Desktop Secuirty group",
        SecurityGroupIngress=[
            ec2.SecurityGroupRule(
                IpProtocol="tcp",
                FromPort="8443",
                ToPort="8443",
                CidrIp=Ref(AccessCidr),
            ),
        ]
    ))

    SshSecurityGroup = t.add_resource(SecurityGroup(
        "SshSecurityGroup",
        VpcId = Ref(VPCId),
        GroupDescription = "SSH Secuirty group",
        SecurityGroupIngress=[
            ec2.SecurityGroupRule(
                IpProtocol="tcp",
                FromPort="22",
                ToPort="22",
                CidrIp=Ref(AccessCidr),
            ),
        ]
    ))

    RootInstanceProfile = t.add_resource(InstanceProfile(
        "RootInstanceProfile",
        Roles=[Ref(RootRole)]
    ))

    remoteDesktopInstance = t.add_resource(ec2.Instance(
        'remoteDesktopInstance',
        ImageId=FindInMap("AWSRegionAMI", Ref("AWS::Region"), Ref(OperatingSystem)),
        KeyName=Ref(EC2KeyName),
        InstanceType=(Ref(remoteDesktopInstanceType)),
        DisableApiTermination='false',
        NetworkInterfaces=[
            NetworkInterfaceProperty(
                SubnetId=Ref(Subnet),
                GroupSet=If(
                    "not_existing_sg",
                    [Ref(remoteDesktopSecurityGroup), Ref(SshSecurityGroup)],
                    [Ref(remoteDesktopSecurityGroup), Ref(SshSecurityGroup), Ref(ExistingSecurityGroup)]
                ),
                AssociatePublicIpAddress=Ref(UsePublicIp),
                DeviceIndex='0',
                DeleteOnTermination='true',
                PrivateIpAddress=If(
                    "Has_Static_Private_IP",
                    Ref(StaticPrivateIpAddress),
                    Ref("AWS::NoValue"),
                )
            )
        ],
        IamInstanceProfile=(Ref(RootInstanceProfile)),
        UserData=Base64(Join('', InstUserData)),
    ))

    EIPAddress = t.add_resource(EIP(
        'EIPAddress',
        Domain='vpc',
        InstanceId=Ref(remoteDesktopInstance),
        Condition="create_elastic_ip"
    ))

    t.add_condition(
        "not_existing_sg",
        Equals(Ref(ExistingSecurityGroup), "NO_VALUE")
    )

    t.add_condition(
        "Has_Public_Ip",
        Equals(Ref(UsePublicIp), "True")
    )

    t.add_condition(
        "Has_Bucket",
        Not(Equals(Ref(S3BucketName), "NO_VALUE"))
    )

    t.add_condition(
        "create_elastic_ip",
        Equals(Ref(CreateElasticIP), "True")
    )

    t.add_condition(
        "Has_Static_Private_IP",
        Not(Equals(Ref(StaticPrivateIpAddress), "NO_VALUE"))
    )

    waithandle = t.add_resource(WaitConditionHandle('InstanceWaitHandle'))

    instanceWaitCondition = t.add_resource(WaitCondition(
        "instanceWaitCondition",
        Handle=Ref(waithandle),
        Timeout="3600",
        DependsOn="remoteDesktopInstance"
    ))

    t.add_output([
        Output(
            "DCVConnectionLink",
            Description="Connect to the DCV Remote Desktop with this URL",
            Value=Join("", [
                "https://",
                GetAtt("remoteDesktopInstance", 'PublicIp'),
                ":8443"
            ])
        ),
        Output(
            "DCVUserName",
            Description="Login name for DCV session",
            Value=(Ref(UserName))
        ),
        Output(
            "SSHTunnelCommand",
            Description='Command for setting up SSH tunnel to remote desktop, use "localhost:18443" for DCV client',
            Value=Join("", [
                "ssh -i <file.pem> -L 18443:localhost:8443 -l centos ",
                GetAtt("remoteDesktopInstance", 'PublicIp')
            ])
        ),
    ])

    #print(t.to_json(indent=2))
    print(to_yaml(t.to_json(indent=2), clean_up=True))
Ejemplo n.º 8
0
parser.add_argument(
    '--output-dir',
    help='Where to place the Zip-files and the CloudFormation template',
    default='output')

args = parser.parse_args()

template = Template("Custom Resources")

s3_bucket = template.add_parameter(
    troposphere.Parameter(
        "S3Bucket",
        Type=constants.STRING,
        Description="S3 bucket where the ZIP files are located",
    ))
template.set_parameter_label(s3_bucket, "S3 bucket")
lambda_code_location = template.add_parameter_to_group(s3_bucket,
                                                       "Lambda code location")

s3_path = template.add_parameter(
    troposphere.Parameter(
        "S3Path",
        Type=constants.STRING,
        Default='',
        Description=
        "Path prefix where the ZIP files are located (should probably end with a '/')",
    ))
template.set_parameter_label(s3_path, "S3 path")
template.add_parameter_to_group(s3_path, lambda_code_location)