Welcome to Day 44 of the “100 Days of DevOps with PowerShell”! For background on our goals in this series, see Announcing the “100 Days of Devops with PowerShell” Series here at SCC.
In my last post for Day 39 we looked at how you can use the user data feature of Amazon Web Services (AWS) to inject bootstrap scripts into AWS instances as they are provisioned. If you have not read that post, I would suggest you have a quick read and then come back. In this post we’re going to dig deeper into user data and look at troubleshooting user data scripts and some additional ways you can run scripts on your instances.
Troubleshooting AWS User Data Scripts
A key requirement to deploying user data scripts with the AWS cmdlets is that the PowerShell code needs to be converted to a single string and then base 64 encoded. An example of which is shown below:
$userDataString = Get-Content -Path 'C:\scripts\post-deployment.ps1' | Out-String
$userDataString = @"
In the first line we read the contents of the script into a variable using Get-Content, which actually reads the content into an array of strings. Remember, we need the script in a single string and that is achieved with Out-String and this is important because if this does not happen the script will not be decoded correctly at runtime.
So if you have deployed your instances and your script is not running correctly, there’s a quick way to check how EC2 has decoded the script and that is to use the AWS console. Right-clicking on the instance gives the option to View/Change User Data:
Once you view the user data here you can see the content of the script that is going to be run, as well the script tags enclosing the script:
The second way you view the contents of user data is to use the user-data URL, which is a URL (http://169.254.169.254/latest/user-data) only accessible while logged on locally to the instance. Therefore to access this via PowerShell we can use the Invoke-RestMethod cmdlet:
As a side note the metadata URL, similar to the user-data URL, is also worth exploring as that contains specific information about the instance itself. Often useful if you are scripting something within the instance and you wish to find the instanceID of the instance you are on. Explore the URL for more details: http://169.254.169.254/latest/meta-data
If you wish to rerun the script on the instance, it has actually been copied to a file and is located at C:\Program Files\Amazon\Ec2ConfigService\Scripts\UserScript.ps1. There are also additional scripts in this folder that are also worth exploring i.e. downloading or uploading files from S3, automatically installing additional updates and running commands before and after sysprep:
Assuming the script is decoded correctly and it still does not perform the function you were anticipating or it does not appear to be completing successfully there is an Ec2ConfigLog.txt file you can view. This file is located in C:\Program Files\Amazon\Ec2ConfigService\Logs and gives a detailed log of the start-up steps:
By default scripts specified in the <powershell> and <script> (used for batch scripting and command-line) tags are only executed at the initial launch. If you wish to enable the scripts so they run on each boot you can configure this within the properties of the EC2 Service properties:
Also worth noting is that scripts that are run on initial launch are run under the context of the local administrator, but scripts set to run via the checkbox above will run under the context of the account running the EC2 Config service
As you can see user data scripts are extremely powerful and if they are not working, hopefully the information in this post will be somewhat helpful. Of course the most successful scripts are those that have been thoroughly tested and contain robust error handling and logging.
To see the previous installments in this series, visit “100 Days of DevOps with PowerShell”.