cloudtools / awacs

Python library for AWS Access Policy Language creation
BSD 2-Clause "Simplified" License
395 stars 102 forks source link

Unable to Create IAM Policy Statement (awacs.aws.Statement) that is a troposphere.Ref #139

Closed michael-burt closed 4 years ago

michael-burt commented 4 years ago

I am trying to make a awacs.aws.Statement that will generate the following template:

Parameters:
  Parameter-SomeArnList:
    Description: Comma-delimited list of some ARNs
    Type: CommaDelimitedList
Resources:
  SomePolicy:
    Type: AWS::IAM::ManagedPolicy
    Properties:
      PolicyDocument:
        Version: '2012-10-17'
        Statement:
          - Action:
              - cloudformation:DescribeStacks
            Effect: Allow
            Resource: !Ref 'ParameterSomeArnList'

where Parameter-SomeArnList is a CommaDelimitedList parameter.

Using troposphere and awacs, I construct this template as follows:

import troposphere
from troposphere import iam

import awacs

ex_template = troposphere.Template()

ex_template.add_parameter(
    troposphere.Parameter(
        title="ParameterSomeArnList",
        Type="CommaDelimitedList",
        Description="Comma-delimited list of some ARNs"
    )
)

ex_template.add_resource(
    iam.ManagedPolicy(
        title="Example",
        PolicyDocument=awacs.aws.Policy(
            Version="2012-10-17",
            Statement=[
                awacs.aws.Statement(
                    Action=[awacs.aws.Action(prefix="cloudformation", action="DescribeStacks")],
                    Effect="Allow",
                    Resource=troposphere.Ref("ParameterWorkerNodeCfnArns")
                )
            ]
        )
    )
)

ex_template.to_yaml()

you will hit an error though:

Traceback (most recent call last):
  File "<stdin>", line 10, in <module>
  File "/lib/python3.7/site-packages/awacs/__init__.py", line 128, in __init__
    sup.__init__(None, props=self.props, **kwargs)
  File "/lib/python3.7/site-packages/awacs/__init__.py", line 39, in __init__
    self.__setattr__(k, v)
  File "/lib/python3.7/site-packages/awacs/__init__.py", line 80, in __setattr__
    self._raise_type(name, value, expected_type)
  File "/lib/python3.7/site-packages/awacs/__init__.py", line 89, in _raise_type
    (name, type(value), expected_type))
TypeError: Resource is <class 'troposphere.Ref'>, expected <class 'list'>

You can make a very minor change to awacs/aws.py to fix this issue, although it requires awacs to import troposphere.

michael-burt commented 4 years ago

It seems like this will never be implemented in this repo. For those experiencing this issue, I have forked the repository to support the use of troposphere.Ref() as a Resource argument in the aws.Statement class. The fork lives here: https://github.com/Unsupervisedcom/awacs