动态引用以在AWS Cloudformation中指定Secret Manager值

问题描述 投票:2回答:3

无论如何我们可以将dynamic references传递给Secret Manager到AWS Launch Config用户数据吗?

这是我试过的代码片段:

"SampleLaunchConfig": {
            "Type": "AWS::AutoScaling::LaunchConfiguration",
             "Properties": {
                "ImageId": {
                    "Fn::FindInMap": [
                        "AWSRegionArch2AMI",
                        {
                            "Ref": "AWS::Region"
                        },
                        "AMI"
                    ]
                },
                "UserData": {
                    "Fn::Base64": {
                        "Fn::Join": [
                            "",
                            [
                                "#!/bin/bash -xe\n",
                                "yum update -y\n",
                                "useradd -p <<pwd>>{{resolve:secretsmanager:Credentials:SecretString:userName}}\n",
                                "\n"
                            ]
                        ]
                    }
                }
        }
    }

获取useradd时似乎出错:无效的用户名'{{resolve:secretsmanager:Credentials:SecretString:userName}}'

如何将Secret Manager秘密值传递给cloudformation用户数据?

amazon-web-services amazon-cloudformation aws-secrets-manager
3个回答
4
投票

我不确定为什么这不适合你。但是,您可能不希望CFN扩展您在用户数据中的秘密,因为密码将嵌入在EC2控制台中可见的base64编码用户数据脚本中。

相反,您应该利用以下事实:您有一个在主机上执行的脚本,并在脚本执行时调用机密管理器(警告未经测试):

"SampleLaunchConfig": {
        "Type": "AWS::AutoScaling::LaunchConfiguration",
         "Properties": {
            "ImageId": {
                "Fn::FindInMap": [
                    "AWSRegionArch2AMI",
                    {
                        "Ref": "AWS::Region"
                    },
                    "AMI"
                ]
            },
            "UserData": {
                "Fn::Base64": {
                    "Fn::Join": [
                        "",
                        [
                            "#!/bin/bash -xe\n",
                            "yum update -y\n",
                            "yum install -y jq\n",
                            !Sub "useradd -p `aws --region ${AWS::Region} secretsmanager get-secret-value --secret-id Credentials --query SecretString --output text | jq -r .passwordKey` `aws --region ${AWS::Region} secretsmanager get-secret-value --secret-id Credentials --query SecretString --output text | jq -r .userName`\n",
                            "\n"
                        ]
                    ]
                }
            }
    }
}

这并不理想,因为它在命令行上扩展了密码。通过先将密码放入文件并从那里读取然后粉碎文件,可以使安全性更高。


4
投票

似乎{{resolve:...}}动态引用仅在模板中的某些上下文中展开。

AWS文档中没有关于模板中确切位置可以使用这些引用的确切信息。目前有关{{resolve:secretsmanager:...}}的措辞说:

“secrettsmanager动态引用可用于所有资源属性”

然而,这与您的示例相矛盾,我还观察到动态引用无法解析CloudFormation :: Init数据。

我有一个与AWS开放的活跃支持案例,他们已经同意动态参考的行为没有充分记录。随着我的了解,我会更新这个答案。

https://docs.aws.amazon.com/AWSCloudFormation/latest/UserGuide/dynamic-references.html#dynamic-references-secretsmanager


2
投票

我可以确认@ JoeB的“未经测试的警告”答案是有效的,但需要注意的是,有问题的机器必须有权阅读这个秘密。你需要类似的东西

  MyInstancePolicy:
    Type: AWS::IAM::Policy
    Properties:
      PolicyName: MyPolicy
      PolicyDocument:
        Version: 2012-10-17
        Statement:
          -
            Effect: Allow
            Action:
              - secretsmanager:GetSecretValue
            Resource: !Join
              - ''
              - - !Sub "arn:aws:secretsmanager:${AWS::Region}:"
                - !Sub "${AWS::AccountId}:secret:Credentials-??????"

请注意以下几点:

与S3桶不同,你不能做arn:aws:secretsmanager:::secret...。如果您不想显式声明区域和帐户,则需要使用通配符。埋在Using Identity-based Policies (IAM Policies) for Secrets Manager的底部

如果您不关心拥有机密的区域或帐户,则必须为ARN的区域和帐户ID号字段指定通配符*(不是空字段)。

也许不太重要,不太可能导致意外故障,但仍值得注意:

使用'??????'作为匹配Secrets Manager分配的6个随机字符的通配符,可以避免在使用'*'通配符时出现的问题。如果使用语法“another_secret_name- *”,它不仅匹配6个随机字符的预期秘密,而且还匹配“another_secret_name-a1b2c3”。使用 '??????'语法使您可以安全地授予尚不存在的机密的权限。

© www.soinside.com 2019 - 2024. All rights reserved.