Cloud-init runcmd not working in CloudFormation UserData.

0

I have the following UserData in my CloudFormation template:

            "UserData": {
                    "Fn::Base64": {
                        "Fn::Join": [
                            "",
                            [
                                "#cloud-config\nruncmd:\n- sudo wget --directory-prefix -O prep_unused_disk.sh /opt/ABCops/sbin https://xxxxxxyyyyyyy-public.s3.amazonaws.com/scripts/common/prep_unused_disk.sh\n- sudo chmod 755 /opt/ABCops/sbin/prep_unused_disk2.sh\n- sudo /opt/ABCops/sbin/prep_unused_disk2.sh\n",
                                "output: { all : '| tee -a /var/log/cloud-init-output.log'}\n",
                                {
                                    "Fn::Join": [ " ",
                                        [
                                            "hostname:",
                                            { "Fn::Join": [ "", [ { "Ref": "AWS::StackName" }, "-HOST01\n" ] ] }
                                        ]
                                    ]
                                },
                                {
                                    "Fn::Join": [ " ",
                                        [
                                            "fqdn:",
                                            { "Fn::Join": [ "", [ { "Ref": "AWS::StackName" }, "-HOST01.tm.ABCops.net\n" ] ] }
                                        ]
                                    ]
                                },
                                { "Fn::Join": [ " ", [ "rh_subscription:\n" ] ] },
                                {
                                    "Fn::Join": [ "",
                                        [
                                            "    activation-key: ",
                                            {
                                                "Fn::FindInMap": [
                                                    "PatchManagementPatchGroup",
                                                    { "Ref": "PatchManagementWave" },
                                                    {
                                                        "Fn::FindInMap": [
                                                            "PatchManagementLifecycle",
                                                            { "Ref": "ABCEnvironment" },
                                                            { "Ref": "AWS::AccountId" }
                                                        ]
                                                    }
                                                ]
                                            },
                                            "_", { "Ref": "OSDistro" }, "_",
                                            {
                                                "Fn::FindInMap": [
                                                    "PatchManagementLifecycle",
                                                    { "Ref": "ABCEnvironment" },
                                                    { "Ref": "AWS::AccountId" }
                                                ]
                                            }, "-AK"
                                        ]
                                    ]
                                },
                                { "Fn::Sub": "\n    org: ABC-TM\n" }
                            ]
                        ]
                    }
                },

What I am finding is that the first part of that UserData where it download a script from S3 then tries to run it does not work. The second part of that UserData where it registers the host to Foreman/Katello DOES work. I also have console=tty1 in my grub line. Regardless of any of this I am seeing NOTHING in /var/log/cloud-init.log or /var/log/cloud-init-output.log. Its as if this section of code has not run at all. I only know the host is registered to Foreman/Katello by logging in there and looking.

Previously, I had the runcmd calling a local script in the AMI but that too gave me no indication that it was running and if it was if it worked. So I changed it to a wget so at least I could validate that the script was being downloaded.

What am I doing wrong? Why is it not logging anything? If I remove one of the hyphens I will get in the logs that a yaml error happened so cloud-init is reading it.

asked 10 months ago212 views
1 Answer
0

Hello,

I tested a sample CloudFormation Template using the syntax above and was seeing the same behaviour. The commands under runcmd were not running. Then I noticed that the syntax used in Fn::Join for commands is a bit incorrect.

For example consider the following sample template, with commands that create a prep_unused_disk.sh script file and executes it. In the below example you will see that each command is separated and is a string in list of Fn::Join.

"UserData": {
    "Fn::Base64": {
        "Fn::Join": [
            "",
            [
                "#cloud-config\n",
                "runcmd:\n",
                "- sudo echo '#!/bin/bash' > prep_unused_disk.sh && echo 'echo \"Hello, World!\"' >> prep_unused_disk.sh\n",
                "- sudo chmod 755 prep_unused_disk.sh\n",
                "- sudo sh prep_unused_disk.sh\n",
                "output: { all : '| tee -a /var/log/cloud-init-output.log'}\n",
                {
                    "Fn::Join": [ " ",
                        [
                            "hostname:",
                            { "Fn::Join": [ "", [ { "Ref": "AWS::StackName" }, "-HOST01\n" ] ] }
                        ]
                    ]
                },
                {
                    "Fn::Join": [ " ",
                        [
                            "fqdn:",
                            { "Fn::Join": [ "", [ { "Ref": "AWS::StackName" }, "-HOST01.tm.ABCops.net\n" ] ] }
                        ]
                    ]
                },
                { "Fn::Join": [ " ", [ "rh_subscription:\n" ] ] },
                {
                    "Fn::Join": [ "",
                        [
                            "    activation-key: ",
                            {
                                "Fn::FindInMap": [
                                    "PatchManagementPatchGroup",
                                    { "Ref": "PatchManagementWave" },
                                    {
                                        "Fn::FindInMap": [
                                            "PatchManagementLifecycle",
                                            { "Ref": "ABCEnvironment" },
                                            { "Ref": "AWS::AccountId" }
                                        ]
                                    }
                                ]
                            },
                            "_", { "Ref": "OSDistro" }, "_",
                            {
                                "Fn::FindInMap": [
                                    "PatchManagementLifecycle",
                                    { "Ref": "ABCEnvironment" },
                                    { "Ref": "AWS::AccountId" }
                                ]
                            }, "-AK"
                        ]
                    ]
                },
                { "Fn::Sub": "\n    org: ABC-TM\n" }
            ]
        ]
    }
}

After running the template with above UserData, I was able to view the log "Hello, World!" in "/var/log/cloud-init-output.log".

Hope this helps.

AWS
SUPPORT ENGINEER
answered 9 months ago
  • I am sure this worked for you but when I cut and pasted the new userdata section above into my template I see the new data in /var/lib/cloud/instance/user-data.txt but there is nothing in /var/log/cloud-init-output.log. I do not find the file name prep_unused_disk.sh. I see cc_rh_subscription.py run in /var/log/cloud-init-output.log so I know some of the user-data.txt was used.

    I am suspecting there is something else wrong in the template thats not being caught by my IDE and not caught by Cloudformation.

    Since I cannot make this work I guess my next place to look is at AWS::CloudFormation::Init. Maybe I can make that work????

You are not logged in. Log in to post an answer.

A good answer clearly answers the question and provides constructive feedback and encourages professional growth in the question asker.

Guidelines for Answering Questions