Menu
Amazon EC2 Systems Manager
User Guide

Simplify AMI Patching Using Automation, Lambda, and Parameter Store

The following example expands on how to update a Windows AMI, as described in Creating an Automation Document. This example uses the model where an organization maintains and periodically patches their own, proprietary AMIs rather than building from Amazon EC2 AMIs.

The following procedure shows how to automatically apply operating system (OS) patches to a Windows AMI that is already considered to be the most up-to-date or latest AMI. In the example, the default value of the parameter SourceAmiId is defined by a Systems Manager Parameter Store parameter called latestAmi. The value of latestAmi is updated by an AWS Lambda function invoked at the end of the Automation workflow. As a result of this Automation process, the time and effort spent patching AMIs is minimized because patching is always applied to the most up-to-date AMI.

Before You Begin

Configure Automation roles and, optionally, CloudWatch Events for Automation. For more information, see Setting Up Automation.

Task 1: Create a Parameter in Systems Manager Parameter Store

Use the following procedure to create a parameter in Systems Manager Parameter Store. Parameter Store lets you reference parameters (called Systems Manager parameters) across Systems Manager features, including Run Command, State Manager, and Automation.

To create a parameter using Parameter Store

  1. Open the Amazon EC2 console, expand Systems Manager Shared Resources in the navigation pane, and then choose Parameter Store.

  2. Choose Create Parameter.

  3. For Name, type latestAmi.

  4. In the Description field, type a description that identifies this parameter's use.

  5. For Type, choose String.

  6. In the Value field, enter a Windows AMI ID. For example: ami-188d6e0e.

  7. Choose Create Parameter, and then choose OK.

Task 2: Create an IAM Role for AWS Lambda

Use the following procedure to create an IAM service role for AWS Lambda. This role includes the AWSLambdaExecute and AmazonSSMFullAccess managed policies. These policies give Lambda permission to update the value of the latestAmi parameter using a Lambda function and Systems Manager.

To create an IAM service role for Lambda

  1. Open the IAM console at https://console.aws.amazon.com/iam/.

  2. In the navigation pane, choose Roles, and then choose Create New Role.

  3. For Role name, type a role name that can help you identify the purpose of this role, for example, lambda-ssm-role. Role names must be unique within your AWS account. After you type the name, choose Next Step at the bottom of the page.

    Note

    Because various entities might reference the role, you cannot change the name of the role after it has been created.

  4. On the Select Role Type page, choose the AWS Service Roles section, and then choose AWS Lambda.

  5. On the Attach Policy page, choose AWSLambdaExecute and AmazonSSMFullAccess, and then choose Next Step.

  6. Choose Create Role.

Task 3: Create an AWS Lambda Function

Use the following procedure to create a Lambda function that automatically updates the value of the latestAmi parameter.

To create a Lambda function

  1. Sign in to the AWS Management Console and open the AWS Lambda console at https://console.aws.amazon.com/lambda/.

  2. Choose Create a Lambda function.

  3. On the Select blueprint page, choose Blank Function.

  4. On the Configure triggers page, choose Next.

  5. On the Configure function page, type Automation-UpdateSsmParam in the Name field, and enter a description, if you want.

  6. In the Runtime list, choose Python 2.7.

  7. In the Lambda function code section, delete the pre-populated code in the field, and then paste the following code sample.

    Copy
    from __future__ import print_function import json import boto3 print('Loading function') #Updates an SSM parameter #Expects parameterName, parameterValue def lambda_handler(event, context): print("Received event: " + json.dumps(event, indent=2)) # get SSM client client = boto3.client('ssm') #confirm parameter exists before updating it response = client.describe_parameters( Filters=[ { 'Key': 'Name', 'Values': [ event['parameterName'] ] }, ] ) if not response['Parameters']: print('No such parameter') return 'SSM parameter not found.' #if parameter has a Descrition field, update it PLUS the Value if 'Description' in response['Parameters'][0]: description = response['Parameters'][0]['Description'] response = client.put_parameter( Name=event['parameterName'], Value=event['parameterValue'], Description=description, Type='String', Overwrite=True ) #otherwise just update Value else: response = client.put_parameter( Name=event['parameterName'], Value=event['parameterValue'], Type='String', Overwrite=True ) reponseString = 'Updated parameter %s with value %s.' % (event['parameterName'], event['parameterValue']) return reponseString
  8. In the Lambda function handler and role section, in the Role list, choose the service role for Lambda that you created in Task 2.

  9. Choose Next, and then choose Create function.

  10. To test the Lambda function, from the Actions menu, choose Configure Test Event.

  11. Replace the existing text with the following JSON.

    Copy
    { "parameterName":"latestAmi", "parameterValue":"your AMI ID" }
  12. Choose Save and test. The output should state that the parameter was successfully updated and include details about the update. For example, “Updated parameter latestAmi with value ami-123456”.

Task 4: Create an Automation Document and Patch the AMI

Use the following procedure to create and run an Automation document that patches the AMI you specified for the latestAmi parameter. After the Automation workflow completes, the value of latestAmi is updated with the ID of the newly-patched AMI. Subsequent executions use the AMI created by the previous execution.

  1. Open the Amazon EC2 console at https://console.aws.amazon.com/ec2/.

  2. In the navigation pane, choose Documents.

  3. Choose Create Document.

  4. In the Name field, type UpdateMyLatestWindowsAmi.

  5. In the Document Type list, choose Automation.

  6. Delete the brackets in the Content field, and then paste the following JSON sample document.

    Note

    You must change the values of assumeRole and IamInstanceProfileName in this sample with the service role ARN and instance profile role you created when Setting Up Automation.

    Copy
    { "description":"Systems Manager Automation Demo – Patch AMI and Update SSM Param", "schemaVersion":"0.3", "assumeRole":"the role ARN you created", "parameters":{ "sourceAMIid":{ "type":"String", "description":"AMI to patch", "default":"{{ssm:latestAmi}}" }, "targetAMIname":{ "type":"String", "description":"Name of new AMI", "default":"patchedAMI-{{global:DATE_TIME}}" } }, "mainSteps":[ { "name":"startInstances", "action":"aws:runInstances", "timeoutSeconds":1200, "maxAttempts":1, "onFailure":"Abort", "inputs":{ "ImageId":"{{ sourceAMIid }}", "InstanceType":"m3.large", "MinInstanceCount":1, "MaxInstanceCount":1, "IamInstanceProfileName":"the name of the IAM role you created" } }, { "name":"installMissingWindowsUpdates", "action":"aws:runCommand", "maxAttempts":1, "onFailure":"Continue", "inputs":{ "DocumentName":"AWS-InstallMissingWindowsUpdates", "InstanceIds":[ "{{ startInstances.InstanceIds }}" ], "Parameters":{ "UpdateLevel":"Important" } } }, { "name":"stopInstance", "action":"aws:changeInstanceState", "maxAttempts":1, "onFailure":"Continue", "inputs":{ "InstanceIds":[ "{{ startInstances.InstanceIds }}" ], "DesiredState":"stopped" } }, { "name":"createImage", "action":"aws:createImage", "maxAttempts":1, "onFailure":"Continue", "inputs":{ "InstanceId":"{{ startInstances.InstanceIds }}", "ImageName":"{{ targetAMIname }}", "NoReboot":true, "ImageDescription":"AMI created by EC2 Automation" } }, { "name":"terminateInstance", "action":"aws:changeInstanceState", "maxAttempts":1, "onFailure":"Continue", "inputs":{ "InstanceIds":[ "{{ startInstances.InstanceIds }}" ], "DesiredState":"terminated" } }, { "name":"updateSsmParam", "action":"aws:invokeLambdaFunction", "timeoutSeconds":1200, "maxAttempts":1, "onFailure":"Abort", "inputs":{ "FunctionName":"Automation-UpdateSsmParam", "Payload":"{\"parameterName\":\"latestAmi\", \"parameterValue\":\"{{createImage.ImageId}}\"}" } } ], "outputs":[ "createImage.ImageId" ] }
  7. Choose Create Document to save the document.

  8. Expand Systems Manager Services in the navigation pane, choose Automations, and then choose Run automation.

  9. In the Document name list, choose UpdateMyLatestWindowsAmi.

  10. In the Version list, choose 1, and then choose Run automation.

  11. After execution completes, in the Amazon EC2 console, choose Parameter Store and confirm that the new value for latestAmi matches the value returned by the Automation workflow. You can also verify the new AMI ID matches the Automation output in the AMIs section of the EC2 console.