I want to reduce my Amazon EC2 usage by stopping and starting instances at predefined times or utilization thresholds. Can I configure AWS Lambda and AWS CloudWatch to help me do that automatically?

You can use a CloudWatch Event to trigger a Lambda function to start and stop your EC2 instances at scheduled intervals.

CloudWatch Events allows you to create an event that is triggered at a specified time or interval in response to events that take place in your account. For example, you can create a CloudWatch alarm that triggers at a predetermined time of day, or when CPU utilization for an instance reaches certain levels (10% or more, for example).

You can configure a Lambda function to start and stop instances when triggered by this CloudWatch event.

For this example, you’ll create Lambda functions to start and stop EC2 instances and then create CloudWatch Events that trigger your instances to start in the morning and stop at night.

1.    Open the AWS Lambda console and select Create a Lambda function (First time Lambda users may need to choose “Get Started Now,” which will direct you to the “function create” screen). When prompted to select a blueprint, choose Blank Function.

2.    Choose Configure triggers if it is not already selected, and then choose Next. You will configure a Lambda trigger later.

3.    Enter the following information to configure your Lambda function:
            For Name, enter "StopEC2Instances" or another name that’s meaningful for you.
            For Description, add a meaningful description; for example, “stops EC2 instances every day at night”.
            For Runtime, select Python 2.7.

4.    To stop your instances, enter the following sample code:

import boto3

# Enter the region your instances are in, e.g. 'us-east-1'

region = 'XX-XXXXX-X'

# Enter your instances here: ex. ['X-XXXXXXXX', 'X-XXXXXXXX']

instances = ['X-XXXXXXXX']

 

def lambda_handler(event, context):

    ec2 = boto3.client('ec2', region_name=region)

    ec2.stop_instances(InstanceIds=instances)

    print 'stopped your instances: ' + str(instances)

 

5.    Expand the Role drop-down menu and choose Create a custom role. This should open a new tab or window in your browser.

6.    Enter the following information to create a role for Lambda to use:
            Under IAM Role, choose Create a new IAM Role.
            For Role Name, enter “lambda_start_stop_ec2” or another name that’s meaningful for you.

7.    Choose View Policy Document, Edit, and then edit the policy as follows:

{

  "Version": "2012-10-17",

  "Statement": [

    {

      "Effect": "Allow",

      "Action": [

        "logs:CreateLogGroup",

        "logs:CreateLogStream",

        "logs:PutLogEvents"

      ],

      "Resource": "arn:aws:logs:*:*:*"

    },

    {

      "Effect": "Allow",

      "Action": [

        "ec2:Start*",

        "ec2:Stop*"

      ],

      "Resource": "*"

    }

  ]

}

8.    Choose Allow.

9.    From Advanced settings, input 10 seconds for the function timeout.
Note: Environment variables, dead letter queues, and VPC are not necessary for this example; however, if you wish to use these features, you will need to add additional permissions. See the AWS Lambda documentation for more details.

10. Choose Next to review your function configuration, and then choose Create function.

11. Repeat steps 1-4 and 9 to create another function that will start your instances again, using code similar to the following:

import boto3

# Enter the region your instances are in, e.g. 'us-east-1'

region = 'XX-XXXXX-X'

# Enter your instances here: ex. ['X-XXXXXXXX', 'X-XXXXXXXX']

instances = ['X-XXXXXXXX']

 

def lambda_handler(event, context):

    ec2 = boto3.client('ec2', region_name=region)

    ec2.start_instances(InstanceIds=instances)

    print 'started your instances: ' + str(instances)

Note: Use a Name and Description that show this function will be used to start instances. You can use the previously created role.

To test your newly created functions:

1.    From the Lambda console, choose Functions, select your function, and then choose Test.

2.    Your function doesn’t use the test event, so from the Input test event editor just choose Save and test.

Create a CloudWatch event that will trigger your Lambda function at night:

1.    Open the CloudWatch console.

2.    Choose Events, and then choose Create rule.

3.    Select Schedule under Event Selector.

4.    Enter an interval of time or cron expression that will tell Lambda when to stop your instances; for more information on the correct syntax, see Schedule Expression Syntax for Rules.
Note: Cron expressions are evaluated in UTC. Make sure to adjust for your preferred time zone.

5.    Choose Add target.

6.    Under Targets, choose Lambda function.

7.    For Function, choose the Lambda function that stops your instances.

8.    Choose Configure details.

9.    Enter the following information in the provided fields:
            For Name, enter "StopEC2Instances", or another name that’s meaningful for you.
            For Description, add a meaningful description; for example, “stops EC2 instances every day at night”.
            For State, check Enabled.

10.    Choose Create rule.

To restart your instances in the morning, repeat these steps using your preferred time.

Lambda, CloudWatch, EC2, event, custom role


Did this page help you? Yes | No

Back to the AWS Support Knowledge Center

Need help? Visit the AWS Support Center.

Published: 2016-07-07

Updated: 2016-01-10