troposphere icon indicating copy to clipboard operation
troposphere copied to clipboard

Role titles with non-alphanumeric values

Open vishcious opened this issue 8 years ago • 7 comments

Troposphere is awesome! Thank you everyone for working on it.

I was able to create a Role with title value containing "-" i.e. alphanumeric. This passes troposphere validation, but fails when running the template. Has anyone else seen this behavior?

vishcious avatar May 18 '16 21:05 vishcious

Thanks for the issue. Can you post a small sample code showing this behavior?

markpeek avatar May 19 '16 00:05 markpeek

Sure thing. I just replaced the title of the role in the Lambda sample with "Lambda-Execution-Role" like here

from troposphere.constants import NUMBER
from troposphere import FindInMap, GetAtt, Join, Output
from troposphere import Parameter, Ref, Template
from troposphere.awslambda import Function, Code, MEMORY_VALUES
from troposphere.cloudformation import CustomResource
from troposphere.ec2 import Instance
from troposphere.ec2 import SecurityGroup
from troposphere.iam import Role, Policy


t = Template()

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

ExistingVPC = t.add_parameter(Parameter(
    "ExistingVPC",
    Type="AWS::EC2::VPC::Id",
    Description=(
        "The VPC ID that includes the security groups in the "
        "ExistingSecurityGroups parameter."
    ),
))

InstanceType = t.add_parameter(Parameter(
    "InstanceType",
    Default="t2.micro",
    Type="String",
    AllowedValues=["t2.micro", "m1.small"],
))

ExistingSecurityGroups = t.add_parameter(Parameter(
    "ExistingSecurityGroups",
    Type="List<AWS::EC2::SecurityGroup::Id>",
))

MemorySize = t.add_parameter(Parameter(
    'LambdaMemorySize',
    Type=NUMBER,
    Description='Amount of memory to allocate to the Lambda Function',
    Default='128',
    AllowedValues=MEMORY_VALUES
))

Timeout = t.add_parameter(Parameter(
    'LambdaTimeout',
    Type=NUMBER,
    Description='Timeout in seconds for the Lambda function',
    Default='60'
))

t.add_mapping("AWSInstanceType2Arch",
              {u'm1.small': {u'Arch': u'PV64'},
               u't2.micro': {u'Arch': u'HVM64'}}
              )

t.add_mapping("AWSRegionArch2AMI",
              {u'ap-northeast-1': {u'HVM64': u'ami-cbf90ecb',
                                   u'PV64': u'ami-27f90e27'},
               u'ap-southeast-1': {u'HVM64': u'ami-68d8e93a',
                                   u'PV64': u'ami-acd9e8fe'},
               u'ap-southeast-2': {u'HVM64': u'ami-fd9cecc7',
                                   u'PV64': u'ami-ff9cecc5'},
               u'cn-north-1': {u'HVM64': u'ami-f239abcb',
                               u'PV64': u'ami-fa39abc3'},
               u'eu-central-1': {u'HVM64': u'ami-a8221fb5',
                                 u'PV64': u'ami-ac221fb1'},
               u'eu-west-1': {u'HVM64': u'ami-a10897d6',
                              u'PV64': u'ami-bf0897c8'},
               u'sa-east-1': {u'HVM64': u'ami-b52890a8',
                              u'PV64': u'ami-bb2890a6'},
               u'us-east-1': {u'HVM64': u'ami-1ecae776',
                              u'PV64': u'ami-1ccae774'},
               u'us-west-1': {u'HVM64': u'ami-d114f295',
                              u'PV64': u'ami-d514f291'},
               u'us-west-2': {u'HVM64': u'ami-e7527ed7',
                              u'PV64': u'ami-ff527ecf'}}
              )

code = [
    "var response = require('cfn-response');",
    "exports.handler = function(event, context) {",
    "   var responseData = {Value: event.ResourceProperties.List};",
    "   responseData.Value.push(event.ResourceProperties.AppendedItem);",
    "   response.send(event, context, response.SUCCESS, responseData);",
    "};",
]

AppendItemToListFunction = t.add_resource(Function(
    "AppendItemToListFunction",
    Code=Code(
        ZipFile=Join("", code)
    ),
    Handler="index.handler",
    Role=GetAtt("LambdaExecutionRole", "Arn"),
    Runtime="nodejs",
    MemorySize=Ref(MemorySize),
    Timeout=Ref(Timeout)
))

LambdaExecutionRole = t.add_resource(Role(
    "Lambda-Execution-Role",
    Path="/",
    Policies=[Policy(
        PolicyName="root",
        PolicyDocument={
            "Version": "2012-10-17",
            "Statement": [{
                "Action": ["logs:*"],
                "Resource": "arn:aws:logs:*:*:*",
                "Effect": "Allow"
            }]
        })],
    AssumeRolePolicyDocument={"Version": "2012-10-17", "Statement": [
        {"Action": ["sts:AssumeRole"], "Effect": "Allow",
         "Principal": {"Service": ["lambda.amazonaws.com"]}}]},
))

MyEC2Instance = t.add_resource(Instance(
    "MyEC2Instance",
    SecurityGroupIds=GetAtt("AllSecurityGroups", "Value"),
    InstanceType=Ref(InstanceType),
    ImageId=FindInMap("AWSRegionArch2AMI", Ref("AWS::Region"),
                      FindInMap("AWSInstanceType2Arch", Ref(InstanceType),
                                "Arch")),
))

AllSecurityGroups = t.add_resource(CustomResource(
    "AllSecurityGroups",
    List=Ref(ExistingSecurityGroups),
    AppendedItem=Ref("SecurityGroup"),
    ServiceToken=GetAtt(AppendItemToListFunction, "Arn"),
))

SecurityGroup = t.add_resource(SecurityGroup(
    "SecurityGroup",
    SecurityGroupIngress=[
        {"ToPort": "80", "IpProtocol": "tcp", "CidrIp": "0.0.0.0/0",
         "FromPort": "80"}],
    VpcId=Ref(ExistingVPC),
    GroupDescription="Allow HTTP traffic to the host",
    SecurityGroupEgress=[
        {"ToPort": "80", "IpProtocol": "tcp", "CidrIp": "0.0.0.0/0",
         "FromPort": "80"}],
))

AllSecurityGroups = t.add_output(Output(
    "AllSecurityGroups",
    Description="Security Groups that are associated with the EC2 instance",
    Value=Join(", ", GetAtt(AllSecurityGroups, "Value")),
))

print(t.to_json())

vishcious avatar May 19 '16 03:05 vishcious

The problem seems to be that validate_title in the Role class (https://github.com/cloudtools/troposphere/blob/master/troposphere/iam.py#L75) does not call the parent validate_title method. ~~Adding super(Role, self).validate_title(self) in the method should fix that.~~ Removing both validations (and probably keeping the validators for the new RoleName and GroupName attributes) like in #429 should fix this

iam.Group has the same problem.

benbridts avatar Jul 26 '16 21:07 benbridts

The docs list "-' as an allowed character in Role names:

http://docs.aws.amazon.com/IAM/latest/UserGuide/reference_iam-limits.html

jonathanunderwood avatar Oct 10 '16 13:10 jonathanunderwood

I'm having similar troubles with topics, '-' is an allowed character. Is there a workaround?

cfurst avatar Jun 11 '20 03:06 cfurst

@cfurst assuming an SNS topic? The title is for CloudFormation. You should be adding the name with a "-" via the TopicName property. If you're using the same string for title and TopicName, you likely should strip the "-" from the title.

markpeek avatar Jun 11 '20 04:06 markpeek

Got it! Thanks for getting back to me so quickly!! Am a bit rusty with CloudFormation. Thanks for bearing with me.

Iphonicized and mobilized.

On Jun 11, 2020, at 1:00 AM, Mark Peek [email protected] wrote:

 @cfurst assuming an SNS topic? The title is for CloudFormation. You should be adding the name with a "-" via the TopicName property. If you're using the same string for title and TopicName, you likely should strip the "-" from the title.

— You are receiving this because you were mentioned. Reply to this email directly, view it on GitHub, or unsubscribe.

cfurst avatar Jun 11 '20 15:06 cfurst