2

在我的对流层代码中,我基本上想创建一个 sns 主题和一个 lambda 执行角色,我可以从 aws 附加一些托管策略。但问题是我找不到仅引用托管策略的 arn 名称的方法。下面是我的代码,但我在这里复制和粘贴托管策略 json 文档。

有没有更好的出路?

from troposphere import FindInMap, GetAtt, Join, Output, Template, Ref, ImportValue
from troposphere.sns import Topic
from troposphere.iam import Role, Policy


t = Template()

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

sns_topic = Topic(TopicName='IngestStateTopic', title='IngestStateTopic')

t.add_resource(sns_topic)

LambdaExecutionRole = t.add_resource(
    Role(
        "LambdaExecutionRole",
        Path="/",
        Policies=[
            Policy(PolicyName="CloudWatchLogsFullAccess",
                   PolicyDocument={
                       "Version":
                       "2012-10-17",
                       "Statement": [{
                           "Action": ["logs:*"],
                           "Effect": "Allow",
                           "Resource": "*"
                       }]
                   }),
            Policy(PolicyName="SnsReadOnlyAccess",
                   PolicyDocument={
                       "Version":
                       "2012-10-17",
                       "Statement": [{
                           "Effect":
                           "Allow",
                           "Action": ["sns:GetTopicAttributes", "sns:List*"],
                           "Resource":
                           "*"
                       }]
                   }),
            Policy(PolicyName="LambdaBasicExecutionRole-Test",
                   PolicyDocument={
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": "logs:CreateLogGroup",
            "Resource": "arn:aws:logs:eu-west-1:498129003450:*"
        },
        {
            "Effect": "Allow",
            "Action": [
                "logs:CreateLogStream",
                "logs:PutLogEvents"
            ],
            "Resource": [
                "arn:aws:logs:eu-west-1:498129003450:log-group:/aws/lambda/lambda_layers_test:*"
            ]
        }
    ]
})
        ],
        AssumeRolePolicyDocument={
            "Version":
            "2012-10-17",
            "Statement": [{
                "Action": ["sts:AssumeRole"],
                "Effect": "Allow",
                "Principal": {
                    "Service": ["lambda.amazonaws.com"]
                }
            }]
        },
    ))

t.add_output(
    Output(
    "IngestServiceArn",
    Description="ARN of the sns topic",
    Value=Ref(sns_topic),
))

t.add_output(
    Output(
    "LambdaExcecutionRole",
    Description="ARN of the lambda plocy document",
    Value=GetAtt(LambdaExecutionRole, "Arn"),
))

with open('sns_lambda_role.yaml', 'w') as s:
    s.write(t.to_yaml())

以下是我的云形成 yaml 文件名:

AWSTemplateFormatVersion: '2010-09-09'
Outputs:
  IngestServiceArn:
    Description: ARN of the sns topic
    Value: !Ref 'IngestStateTopic'
  LambdaExcecutionRole:
    Description: ARN of the lambda plocy document
    Value: !GetAtt 'LambdaExecutionRole.Arn'
Resources:
  IngestStateTopic:
    Properties:
      TopicName: IngestStateTopic
    Type: AWS::SNS::Topic
  LambdaExecutionRole:
    Properties:
      AssumeRolePolicyDocument:
        Statement:
          - Action:
              - sts:AssumeRole
            Effect: Allow
            Principal:
              Service:
                - lambda.amazonaws.com
        Version: '2012-10-17'
      Path: /
      Policies:
        - PolicyDocument:
            Statement:
              - Action:
                  - logs:*
                Effect: Allow
                Resource: '*'
            Version: '2012-10-17'
          PolicyName: CloudWatchLogsFullAccess
        - PolicyDocument:
            Statement:
              - Action:
                  - sns:GetTopicAttributes
                  - sns:List*
                Effect: Allow
                Resource: '*'
            Version: '2012-10-17'
          PolicyName: SnsReadOnlyAccess
        - PolicyDocument:
            Statement:
              - Action: logs:CreateLogGroup
                Effect: Allow
                Resource: arn:aws:logs:eu-west-1:498129003450:*
              - Action:
                  - logs:CreateLogStream
                  - logs:PutLogEvents
                Effect: Allow
                Resource:
                  - arn:aws:logs:eu-west-1:498129003450:log-group:/aws/lambda/lambda_layers_test:*
            Version: '2012-10-17'
          PolicyName: LambdaBasicExecutionRole-Test
    Type: AWS::IAM::Role
4

2 回答 2

5

您可以通过指定 ManagedPolicyArns角色 cloudformation 资源的列表来执行此操作,而不是Policies-文档

{
  "Type" : "AWS::IAM::Role",
  "Properties" : {
      "AssumeRolePolicyDocument" : Json,
      "ManagedPolicyArns" : [ String, ... ],
      "MaxSessionDuration" : Integer,
      "Path" : String,
      "PermissionsBoundary" : String,
      "Policies" : [ Policy, ... ],
      "RoleName" : String
    }
}

对于 ManagedPolicy CloudFormation 具有单独的资源类型 - AWS::IAM::ManagedPolicy

SampleManagedPolicy:
    Type: AWS::IAM::ManagedPolicy
    Properties:
      PolicyDocument:
        Version: "2012-10-17"
        Statement:
          -
            Sid: AllowAllUsersToListAccounts
            Effect: Allow
            Action:
              - iam:ListAccountAliases
              - iam:ListUsers
              - iam:GetAccountSummary
            Resource: "*

示例:

RootRole:
    Type: 'AWS::IAM::Role'
    Properties:
      AssumeRolePolicyDocument:
        Version: 2012-10-17
        Statement:
          - Effect: Allow
            Principal:
              Service:
                - ec2.amazonaws.com
            Action:
              - 'sts:AssumeRole'
      Path: /
      ManagedPolicyArns:
        - !Ref awsExampleManagedPolicyParameterOne            
        - !Ref awsExampleManagedPolicyParameterTwo

所以,如果我们谈论的是对流层——它也有单独的 ManagedPolicy 类:

class ManagedPolicy(AWSObject):
    resource_type = "AWS::IAM::ManagedPolicy"

    props = {
        'Description': (basestring, False),
        'Groups': ([basestring], False),
        'ManagedPolicyName': (basestring, False),
        'Path': (iam_path, False),
        'PolicyDocument': (policytypes, True),
        'Roles': ([basestring], False),
        'Users': ([basestring], False),
    }

你使用Ref函数来引用它。

于 2019-08-06T18:57:33.097 回答
1

您可能想查看允许策略定义的awacs项目。

此外,您可能只需要 Ref() 您的策略来获取它的名称。

于 2019-08-06T15:40:03.397 回答