Manage Unused AWS AMIs

Identify and manage unused Amazon Machine Images (AMIs) in AWS to optimize storage and reduce unnecessary costs.

  1. 1

    Retrieve the AWS account ID by calling the AWS Security Token Service (STS) to ensure secure identification and access management.

    import boto3 creds = _get_creds(cred_label)['creds'] access_key = creds['username'] secret_key = creds['password'] def fetch_account_id(): sts_client = boto3.client('sts',aws_access_key_id=access_key,aws_secret_access_key=secret_key,region_name="us-east-1") account_id = sts_client.get_caller_identity()['Account'] return account_id account_id = fetch_account_id() #print(account_id)
    copied
    1
  2. 2

    Identify and list all Amazon Machine Images (AMIs) within an AWS account that are not currently associated with any running or stopped EC2 instances.

    import boto3 from botocore.exceptions import NoCredentialsError, PartialCredentialsError, ClientError, BotoCoreError creds = _get_creds(cred_label)['creds'] access_key = creds['username'] secret_key = creds['password'] # Function to list all AWS regions def list_all_regions(): ec2 = boto3.client('ec2', aws_access_key_id=access_key, aws_secret_access_key=secret_key, region_name='us-east-1') try: return [region['RegionName'] for region in ec2.describe_regions()['Regions']] except ClientError as e: print(f"Failed to list regions: {e}") return [] # Function to list unused AMIs based on the provided region def list_unused_amis(region_name, owner_id): try: ec2 = boto3.client('ec2', aws_access_key_id=access_key, aws_secret_access_key=secret_key, region_name=region_name) amis = ec2.describe_images(Owners=[owner_id])['Images'] instances = ec2.describe_instances()['Reservations'] used_amis = set(instance['ImageId'] for reservation in instances for instance in reservation['Instances']) unused_amis = [{ 'Region': region_name, 'ImageId': ami['ImageId']} for ami in amis if ami['ImageId'] not in used_amis] return unused_amis except (NoCredentialsError, PartialCredentialsError) as e: print(f"Authentication error in region {region_name}: {e}") except BotoCoreError as e: print(f"BotoCore error in region {region_name}: {e}") except ClientError as e: print(f"Client error in region {region_name}: {e}") except Exception as e: print(f"Unexpected error in region {region_name}: {e}") return [] def display_unused_amis(all_unused_amis): # Initialize table with the desired structure and headers table = context.newtable() table.title = "Unused AMI Details" table.num_cols = 2 # Number of columns for ImageId and Region table.num_rows = 1 table.has_header_row = True # Define header names based on the new structure headers = ["AMI ID", "Region"] # Set headers in the first row for col_num, header in enumerate(headers): table.setval(0, col_num, header) # Populate the table with AMI data for row_num, ami in enumerate(all_unused_amis, start=1): # Starting from the second row table.num_rows += 1 # Add a row for each AMI values = [ ami['ImageId'], ami['Region'] ] for col_num, value in enumerate(values): table.setval(row_num, col_num, value) # Main Execution # Specify 'None' for all regions or a specific region like 'us-east-1' # region_name = None # or 'us-east-1' owner_id = account_id regions = [region_name] if region_name else list_all_regions() all_unused_amis = [] for region in regions: unused_amis = list_unused_amis(region, owner_id) all_unused_amis.extend(unused_amis) if all_unused_amis: display_unused_amis(all_unused_amis) '''for ami in all_unused_amis: print(f"Unused AMI: {ami['ImageId']} in Region: {ami['Region']}")''' else: print("No Unused AMIs found across the specified regions.") context.proceed = False # To stop execution and enable user intervention for the downstream remediation task
    copied
    2