-
-
Save bkozora/d4f1cf0e5cf26acdd377 to your computer and use it in GitHub Desktop.
| # Automated AMI and Snapshot Deletion | |
| # | |
| # @author Bobby Kozora | |
| # | |
| # This script will search for all instances having a tag named "Backup" with a value of "Backup". | |
| # As soon as we have the instances list, we loop through each instance | |
| # and reference the AMIs of that instance. We check that the latest daily backup | |
| # succeeded then we store every image that's reached its DeleteOn tag's date for | |
| # deletion. We then loop through the AMIs, deregister them and remove all the | |
| # snapshots associated with that AMI. | |
| import boto3 | |
| import collections | |
| import datetime | |
| import time | |
| import sys | |
| ec = boto3.client('ec2', 'us-east-1') | |
| ec2 = boto3.resource('ec2', 'us-east-1') | |
| images = ec2.images.filter(Owners=["self"]) | |
| def lambda_handler(event, context): | |
| reservations = ec.describe_instances(Filters=[ | |
| { | |
| 'Name': 'tag-key', | |
| 'Values': ['backup', 'Backup'] | |
| }, | |
| ]).get('Reservations', []) | |
| instances = sum([[i for i in r['Instances']] for r in reservations], []) | |
| print("Found %d instances that need evaluated" % len(instances)) | |
| to_tag = collections.defaultdict(list) | |
| date = datetime.datetime.now() | |
| date_fmt = date.strftime('%Y-%m-%d') | |
| imagesList = [] | |
| # Set to true once we confirm we have a backup taken today | |
| backupSuccess = False | |
| # Loop through all of our instances with a tag named "Backup" | |
| for instance in instances: | |
| imagecount = 0 | |
| # Loop through each image of our current instance | |
| for image in images: | |
| # Our other Lambda Function names its AMIs Lambda - i-instancenumber. | |
| # We now know these images are auto created | |
| if image.name.startswith('Lambda - ' + instance['InstanceId']): | |
| # print "FOUND IMAGE " + image.id + " FOR INSTANCE " + instance['InstanceId'] | |
| # Count this image's occcurance | |
| imagecount = imagecount + 1 | |
| try: | |
| if image.tags is not None: | |
| deletion_date = [ | |
| t.get('Value') for t in image.tags | |
| if t['Key'] == 'DeleteOn' | |
| ][0] | |
| delete_date = time.strptime(deletion_date, "%m-%d-%Y") | |
| except IndexError: | |
| deletion_date = False | |
| delete_date = False | |
| today_time = datetime.datetime.now().strftime('%m-%d-%Y') | |
| # today_fmt = today_time.strftime('%m-%d-%Y') | |
| today_date = time.strptime(today_time, '%m-%d-%Y') | |
| # If image's DeleteOn date is less than or equal to today, | |
| # add this image to our list of images to process later | |
| if delete_date <= today_date: | |
| imagesList.append(image.id) | |
| # Make sure we have an AMI from today and mark backupSuccess as true | |
| if image.name.endswith(date_fmt): | |
| # Our latest backup from our other Lambda Function succeeded | |
| backupSuccess = True | |
| print("Latest backup from " + date_fmt + " was a success") | |
| print("instance " + instance['InstanceId'] + " has " + | |
| str(imagecount) + " AMIs") | |
| print("=============") | |
| print("About to process the following AMIs:") | |
| print(imagesList) | |
| if backupSuccess == True: | |
| myAccount = boto3.client('sts').get_caller_identity()['Account'] | |
| snapshots = ec.describe_snapshots(MaxResults=1000, | |
| OwnerIds=[myAccount])['Snapshots'] | |
| # loop through list of image IDs | |
| for image in imagesList: | |
| print("deregistering image %s" % image) | |
| amiResponse = ec.deregister_image( | |
| DryRun=False, | |
| ImageId=image, | |
| ) | |
| for snapshot in snapshots: | |
| if snapshot['Description'].find(image) > 0: | |
| snap = ec.delete_snapshot( | |
| SnapshotId=snapshot['SnapshotId']) | |
| print("Deleting snapshot " + snapshot['SnapshotId']) | |
| print("-------------") | |
| else: | |
| print("No current backup found. Termination suspended.") |
Here is the cleanup code & the output: It able to detect the instance but not able to delete the ami created today, even I changed backupSuccess = True
Test Event Name
test
Response
null
Function Logs
START RequestId: 3f72e0b7-59bb-433e-a46d-4f097c8acb45 Version: $LATEST
Found 1 instances that need evaluated
instance i-0acbe212ea7c31c7e has 0 AMIs
About to process the following AMIs:
[]
END RequestId: 3f72e0b7-59bb-433e-a46d-4f097c8acb45
import boto3
import collections
import datetime
import time
import sys
ec = boto3.client('ec2', 'ap-south-1')
ec2 = boto3.resource('ec2', 'ap-south-1')
images = ec2.images.filter(Owners=["self"])
def lambda_handler(event, context):
reservations = ec.describe_instances(Filters=[
{
'Name': 'tag-key',
'Values': ['backup', 'Backup']
},
]).get('Reservations', [])
instances = sum([[i for i in r['Instances']] for r in reservations], [])
print("Found %d instances that need evaluated" % len(instances))
to_tag = collections.defaultdict(list)
date = datetime.datetime.now()
date_fmt = date.strftime('%Y-%m-%d')
imagesList = []
# Set to true once we confirm we have a backup taken today
backupSuccess = True
# Loop through all of our instances with a tag named "Backup"
for instance in instances:
imagecount = 0
# Loop through each image of our current instance
for image in images:
# Our other Lambda Function names its AMIs Lambda - i-instancenumber.
# We now know these images are auto created
if image.name.startswith('Lambda - ' + instance['InstanceId']):
# print "FOUND IMAGE " + image.id + " FOR INSTANCE " + instance['InstanceId']
# Count this image's occcurance
imagecount = imagecount + 1
try:
if image.tags is not None:
deletion_date = [
t.get('Value') for t in image.tags
if t['Key'] == 'DeleteOn'
][0]
delete_date = time.strptime(deletion_date, "%m-%d-%Y")
except IndexError:
deletion_date = False
delete_date = False
today_time = datetime.datetime.now().strftime('%m-%d-%Y')
# today_fmt = today_time.strftime('%m-%d-%Y')
today_date = time.strptime(today_time, '%m-%d-%Y')
# If image's DeleteOn date is less than or equal to today,
# add this image to our list of images to process later
if delete_date <= today_date:
imagesList.append(image.id)
# Make sure we have an AMI from today and mark backupSuccess as true
if image.name.endswith(date_fmt):
# Our latest backup from our other Lambda Function succeeded
backupSuccess = True
print("Latest backup from " + date_fmt + " was a success")
print("instance " + instance['InstanceId'] + " has " +
str(imagecount) + " AMIs")
print("=============")
print("About to process the following AMIs:")
print(imagesList)
if backupSuccess == True:
myAccount = boto3.client('sts').get_caller_identity()['Account']
snapshots = ec.describe_snapshots(MaxResults=1000,
OwnerIds=[myAccount])['Snapshots']
# loop through list of image IDs
for image in imagesList:
print("deregistering image %s" % image)
amiResponse = ec.deregister_image(
DryRun=False,
ImageId=image,
)
for snapshot in snapshots:
if snapshot['Description'].find(image) > 0:
snap = ec.delete_snapshot(
SnapshotId=snapshot['SnapshotId'])
print("Deleting snapshot " + snapshot['SnapshotId'])
print("-------------")
else:
print("No current backup found. Termination suspended.")
Hi
I have code to have the retention backup days for 7, however, how to exclude the weekends snapshots for the last 35 days in deletion.
I want to have the snapshots for last 7 days and last 5 weekend Saturdays snapshots without using tags.
Kindly let me know the code if possible
Thank you so much for such solution.