Cloudformation:输出 - 你能 return 一个文件中的值吗

Cloudformation: Outputs - Can you return a value from a file

Cloudformation 似乎有一个 "Outputs" 部分,您可以在其中为其他堆栈引用一个值,或者向用户显示等。

The limited doc is here.

是否可以使用它来使文​​件的内容可用?

例如我安装了 Jenkins,其中初始管理员密码存储在:

/var/lib/jenkins/secrets/initialAdminPassword

我希望在部署我们的 Jenkins Cloudformation 堆栈后可以使用该值,而无需通过 SSH 连接到服务器。

输出部分是否可行,或者使用 cloudformation 模板的任何其他方式?

Outputs 部分 Cloud Formation 模板旨在帮助您轻松找到资源。

对于您创建的任何资源,您都可以输出Fb::GetAtt Documentation中定义的属性。

例如,要获取使用 Cloud formation 模板创建的 RDS 实例的连接字符串,您可以使用以下内容

"Outputs" : {
    "JDBCConnectionString": {
        "Description" : "JDBC connection string for the master database",
        "Value" : { "Fn::Join": [ "", 
            [ "jdbc:mysql://",
            { "Fn::GetAtt": [ "MyDatabase", "Endpoint.Address" ] },
            ":",
            { "Fn::GetAtt": [ "MyDatabase", "Endpoint.Port" ] },
            "/",
            { "Ref": "MyDBName" }]
        ]}
    }
}

无法从文件中输出内容。此外,所有有权访问您的 AWS 账户的用户都可以看到输出。因此,不建议将密码作为输出。

我建议您在云形成创建堆栈操作成功后将您的机密上传到私有 S3 存储桶,并在需要时下载机密。

希望这对您有所帮助。

我知道这个问题已经得到解答,但我想提供另一种解决方案。

我发现自己想做您(OP)想做的事情:使用 Cloudformation 在 EC2 实例上安装 Jenkins,然后将初始管理员密码打印到 Cloudformation 输出。

我最终尝试使用密码读取文件,而是使用 UserData 部分中的 Jenkins CLI 使用我指定的密码更新管理员用户。

这是我所做的(显示 YAML 模板中的片段):

向模板输入添加了一个参数以获取密码:

Parameters:
  KeyName:
    ConstraintDescription: Must be the name of an existing EC2 KeyPair.
    Description: Name of an existing EC2 KeyPair for SSH access
    Type: AWS::EC2::KeyPair::KeyName
  PassWord:
    AllowedPattern: '[-_a-zA-Z0-9]*'
    ConstraintDescription: A complex password at least eight chars long with alphanumeric characters, dashes and underscores.
    Description: Password for the admin account
    MaxLength: 64
    MinLength: 8
    NoEcho: true
    Type: String

在 UserData 部分,我在调用 jenkins-cli 时使用了 PassWord 参数来更新管理员帐户:

  UserData: !Base64
    Fn::Join:
      - ''
      - - "#!/bin/bash -x\n"
        - "exec > /tmp/user-data.log 2>&1\nunset UCF_FORCE_CONFFOLD\n"
        - "export UCF_FORCE_CONFFNEW=YES\n"
        - "ucf --purge /boot/grub/menu.lst\n"
        - "export DEBIAN_FRONTEND=noninteractive\n"
        - "echo \"deb http://pkg.jenkins-ci.org/debian binary/\" > /etc/apt/sources.list.d/jenkins.list\n"
        - "wget -q -O jenkins-ci.org.key http://pkg.jenkins-ci.org/debian-stable/jenkins-ci.org.key\n\
          apt-key add jenkins-ci.org.key\n"
        - "apt-get update\n"
        - "apt-get -o Dpkg::Options::=\"--force-confnew\" --force-yes -fuy upgrade\n"
        - "apt-get install -y python-pip\n"
        - "pip install https://s3.amazonaws.com/cloudformation-examples/aws-cfn-bootstrap-latest.tar.gz\n"
        - "apt-get install -y nginx\n"
        - "apt-get install -y openjdk-8-jdk\n"
        - "apt-get install -y jenkins\n"
        - "# Wait for Jenkins to Set Up\n
        - until [ $(curl -o /dev/null --silent\
          \ --head --write-out '%{http_code}\n' http://localhost:8080) -eq 403\
          \ ]; do sleep 1; done\nsleep 10\n# Change the password for the admin\
          \ account\necho 'jenkins.model.Jenkins.instance.securityRealm.createAccount(\"\
          admin\", \""
        - !Ref 'PassWord'
        - "\")' | java -jar /var/cache/jenkins/war/WEB-INF/jenkins-cli.jar -s\
          \ \"http://localhost:8080/\" -auth \"admin:$(cat /var/lib/jenkins/secrets/initialAdminPassword)\"\
          \ groovy =\n/usr/local/bin/cfn-init --resource=Instance --region="
        - !Ref 'AWS::Region'
        - ' --stack='
        - !Ref 'AWS::StackName'
        - "\n"
        - "unlink /etc/nginx/sites-enabled/default\nsystemctl reload nginx\n"
        - /usr/local/bin/cfn-signal -e $? --resource=Instance --region=
        - !Ref 'AWS::Region'
        - ' --stack='
        - !Ref 'AWS::StackName'
        - "\n"

使用这种方法,当 Jenkins 启动时,我没有看到“输入初始管理员密码”屏幕,而是看到一个屏幕,我可以在其中使用参数中使用的密码以管理员身份登录。

就向系统文件的输出添加内容而言,我认为一种使用 WaitCondition 并使用 cfn- 传回数据的方法信号命令。但是一旦我发现我需要做的就是设置我没有追求WaitCondition方法的密码。

同样,我知道您已经有了答案,但我想分享一下,以防其他人碰巧正在寻找一种方法来做到这一点。这种方式对我有用! :D