def _create_role_policy(stack_arn, function_name): cf = boto3.client('cloudformation', region_name=discovery_utils.get_region_from_stack_arn(stack_arn)) try: res = discovery_utils.try_with_backoff(lambda : cf.describe_stack_resources(StackName=stack_arn)) print 'describe_stack_resource(StackName="{}") result: {}'.format(stack_arn, res) except Exception as e: print 'describe_stack_resource(StackName="{}") error: {}'.format(stack_arn, getattr(e, 'response', e)) raise e policy = { 'Version': '2012-10-17', 'Statement': [ { "Sid": "WriteLogs", "Effect": "Allow", "Action": [ "logs:CreateLogGroup", "logs:CreateLogStream", "logs:PutLogEvents" ], "Resource": "arn:aws:logs:*:*:*" } ] } for resource in res['StackResources']: statement = _make_resource_statement(cf, stack_arn, function_name, resource['LogicalResourceId']) if statement is not None: policy['Statement'].append(statement) print 'generated policy: {}'.format(policy) return json.dumps(policy, indent=4)
def _create_role_policy(stack_arn, policy_name, default_statements, policy_metadata_filter): if not isinstance(default_statements, list): raise ValidationError('The default_statements value is not a list.') cf = boto3.client( 'cloudformation', region_name=discovery_utils.get_region_from_stack_arn(stack_arn)) try: res = discovery_utils.try_with_backoff( lambda: cf.describe_stack_resources(StackName=stack_arn)) print 'describe_stack_resource(StackName="{}") result: {}'.format( stack_arn, res) except Exception as e: print 'describe_stack_resource(StackName="{}") error: {}'.format( stack_arn, getattr(e, 'response', e)) raise e policy = { 'Version': '2012-10-17', 'Statement': copy.deepcopy(default_statements) } for resource in res['StackResources']: statement = _make_resource_statement(cf, stack_arn, policy_name, resource['LogicalResourceId'], policy_metadata_filter) if statement is not None: policy['Statement'].append(statement) print 'generated policy: {}'.format(policy) return json.dumps(policy, indent=4)
def _make_resource_statement(resource_group_info, logical_resource_name, metadata_key): try: response = discovery_utils.try_with_backoff( lambda: resource_group_info.get_client().describe_stack_resource( StackName=resource_group_info.stack_arn, LogicalResourceId=logical_resource_name)) print 'describe_stack_resource(LogicalResourceId="{}", StackName="{}") response: {}'.format( logical_resource_name, resource_group_info.stack_arn, response) except Exception as e: print 'describe_stack_resource(LogicalResourceId="{}", StackName="{}") error: {}'.format( logical_resource_name, resource_group_info.stack_arn, getattr(e, 'response', e)) raise e resource = response['StackResourceDetail'] metadata = discovery_utils.get_cloud_canvas_metadata( resource, metadata_key) if metadata is None: return None metadata_actions = metadata.get('Action', None) if metadata_actions is None: raise ValidationError( 'No Action was specified for CloudCanvas Access metdata on the {} resource in stack {}.' .format(logical_resource_name, resource_group_info.stack_arn)) if not isinstance(metadata_actions, list): metadata_actions = [metadata_actions] for action in metadata_actions: if not isinstance(action, basestring): raise ValidationError( 'Non-string Action specified for CloudCanvas Access metadata on the {} resource in stack {}.' .format(logical_resource_name, resource_group_info.stack_arn)) if 'PhysicalResourceId' not in resource: return None if 'ResourceType' not in resource: return None resource = discovery_utils.get_resource_arn(resource_group_info.stack_arn, resource['ResourceType'], resource['PhysicalResourceId']) resource_suffix = metadata.get('ResourceSuffix', None) if resource_suffix is not None: resource += resource_suffix return { 'Sid': logical_resource_name + 'Access', 'Effect': 'Allow', 'Action': metadata_actions, 'Resource': resource }
def _make_resource_statement(cf, stack_arn, policy_name, logical_resource_name, policy_metadata_filter): print 'describe_stack_resource on resource {} in stack {}.'.format( logical_resource_name, stack_arn) try: res = discovery_utils.try_with_backoff( lambda: cf.describe_stack_resource( StackName=stack_arn, LogicalResourceId=logical_resource_name)) print 'describe_stack_resource {} result: {}'.format( logical_resource_name, res) except Exception as e: print 'describe_stack_resource {} error: {}'.format( logical_resource_name, getattr(e, 'response', e)) raise e resource = res['StackResourceDetail'] metadata = _get_metadata_for_role(resource, policy_name, policy_metadata_filter) if metadata is None: return metadata_actions = metadata.get('Action', None) if metadata_actions is None: raise ValidationError( 'No Action was specified for CloudCanvas {} metdata on the {} resource in stack {}.' .format(policy_name, resource['LogicalResourceId'], stack_arn)) if not isinstance(metadata_actions, list): metadata_actions = [metadata_actions] for action in metadata_actions: if not isinstance(action, basestring): raise ValidationError( 'Non-string Action specified for CloudCanvas {} metadata on the {} resource in stack {}.' .format(policy_name, resource['LogicalResourceId'], stack_arn)) resource = discovery_utils.get_resource_arn(stack_arn, resource['ResourceType'], resource['PhysicalResourceId']) resource_suffix = metadata.get('ResourceSuffix', None) if resource_suffix is not None: resource += resource_suffix return { 'Sid': logical_resource_name + 'Access', 'Effect': 'Allow', 'Action': metadata_actions, 'Resource': resource }
def _make_resource_statement(feature_info, logical_resource_name): try: response = discovery_utils.try_with_backoff(lambda : feature_info.get_client().describe_stack_resource(StackName=feature_info.stack_arn, LogicalResourceId=logical_resource_name)) print 'describe_stack_resource(LogicalResourceId="{}", StackName="{}") response: {}'.format(logical_resource_name, feature_info.stack_arn, response) except Exception as e: print 'describe_stack_resource(LogicalResourceId="{}", StackName="{}") error: {}'.format(logical_resource_name, feature_info.stack_arn, getattr(e, 'response', e)) raise e resource = response['StackResourceDetail'] metadata = discovery_utils.get_cloud_canvas_metadata(resource, 'PlayerAccess') if metadata is None: return None metadata_actions = metadata.get('Action', None) if metadata_actions is None: raise ValidationError('No Action was specified for CloudCanvas PlayerAccess metdata on the {} resource in stack {}.'.format( logical_resource_name, feature_info.stack_arn)) if not isinstance(metadata_actions, list): metadata_actions = [ metadata_actions ] for action in metadata_actions: if not isinstance(action, basestring): raise ValidationError('Non-string Action specified for CloudCanvas PlayerAccess metadata on the {} resource in stack {}.'.format( logical_resource_name, feature_info.stack_arn)) if 'PhysicalResourceId' not in resource: return None if 'ResourceType' not in resource: return None resource = discovery_utils.get_resource_arn(feature_info.stack_arn, resource['ResourceType'], resource['PhysicalResourceId']) resource_suffix = metadata.get('ResourceSuffix', None) if resource_suffix is not None: resource += resource_suffix return { 'Sid': logical_resource_name + 'Access', 'Effect': 'Allow', 'Action': metadata_actions, 'Resource': resource }
def _create_role_policy(stack_arn, function_name): cf = boto3.client( 'cloudformation', region_name=discovery_utils.get_region_from_stack_arn(stack_arn)) try: res = discovery_utils.try_with_backoff( lambda: cf.describe_stack_resources(StackName=stack_arn)) print 'describe_stack_resource(StackName="{}") result: {}'.format( stack_arn, res) except Exception as e: print 'describe_stack_resource(StackName="{}") error: {}'.format( stack_arn, getattr(e, 'response', e)) raise e policy = { 'Version': '2012-10-17', 'Statement': [{ "Sid": "WriteLogs", "Effect": "Allow", "Action": [ "logs:CreateLogGroup", "logs:CreateLogStream", "logs:PutLogEvents" ], "Resource": "arn:aws:logs:*:*:*" }] } for resource in res['StackResources']: statement = _make_resource_statement(cf, stack_arn, function_name, resource['LogicalResourceId']) if statement is not None: policy['Statement'].append(statement) print 'generated policy: {}'.format(policy) return json.dumps(policy, indent=4)
def _make_resource_statement(cf, stack_arn, function_name, logical_resource_name): print 'describe_stack_resource on resource {} in stack {}.'.format(logical_resource_name, stack_arn) try: res = discovery_utils.try_with_backoff(lambda : cf.describe_stack_resource(StackName=stack_arn, LogicalResourceId=logical_resource_name)) print 'describe_stack_resource {} result: {}'.format(logical_resource_name, res) except Exception as e: print 'describe_stack_resource {} error: {}'.format(logical_resource_name, getattr(e, 'response', e)) raise e resource = res['StackResourceDetail'] metadata = _get_metadata_for_function(resource, function_name) if metadata is None: return metadata_actions = metadata.get('Action', None) if metadata_actions is None: raise ValidationError('No Action was specified for CloudCanvas FunctionAccess metdata on the {} resource in stack {}.'.format( resource['LogicalResourceId'], stack_arn)) if not isinstance(metadata_actions, list): metadata_actions = [ metadata_actions ] for action in metadata_actions: if not isinstance(action, basestring): raise ValidationError('Non-string Action specified for CloudCanvas FunctionAccess metadata on the {} resource in stack {}.'.format( resource['LogicalResourceId'], stack_arn)) resource = discovery_utils.get_resource_arn(stack_arn, resource['ResourceType'], resource['PhysicalResourceId']) resource_suffix = metadata.get('ResourceSuffix', None) if resource_suffix is not None: resource += resource_suffix return { 'Sid': logical_resource_name + 'Access', 'Effect': 'Allow', 'Action': metadata_actions, 'Resource': resource }