Welcome Traveler..
Welcome back Traveler..
In today’s mission we’ll go over how to “List available AWS services by region”.
Yes, we can get all that info from a console and follow ‘clicky, clicky’ but that’s not how we operate and plus we want speeeed.
Why would you need this, you may ask..
Curiosity, Audit request, Security Review – just to name the few..
This is just one of the ways of how WildcardSlasher gathers information to fulfill incoming requests. You might have other/better way. My way is NOT the only way.
The code we’re going to be working with makes use of the boto3 library, which is the official AWS SDK for Python. It allows us to harness the power of the cloud and interact with a wide range of AWS services, making it a powerful tool for any sorcerer.
import boto3 import configparser import csv from botocore.config import Config from botocore.exceptions import ClientError
Next, we set up our configuration for retries and define the paths for our configuration file
config = Config( retries = dict( max_attempts = 10 ) ) config_file = '/home/user1/.aws/.python-profiles.conf'
We then define a function to read a list of profiles from our configuration file.
def read_profile_list(config_file): config = configparser.ConfigParser() config.read(config_file) profile_list = config.get('testProfile', 'profile_list') profile_list = profile_list.split(' ') return profile_list
Our next function, list_aws_services
, takes a profile name as an argument. It creates a session for the given profile and uses the IAM and EC2 clients to get the account name and list of regions. It then checks for available services in each region and writes this information to a report file.
def list_aws_services(profileName): session = boto3.Session(profile_name=profileName) iam = session.client("iam",region_name='us-east-1', config=config) ec2 = session.client("ec2",region_name='us-east-1', config=config) account_alias = iam.list_account_aliases() accountName = account_alias['AccountAliases'][0] report_file = (f"/tmp/{accountName}.available_services.csv") report_file_log = (f"/tmp/{accountName}.available_services.log") with open(report_file, "w") as file: file.write(f"SERVICE_NAME;REGION;ACCOUNT_NAME\n") regions = [region["RegionName"] for region in ec2.describe_regions()["Regions"]] for region in regions: ssm = session.client("ssm", region_name=region, config=config) path = '/aws/service/global-infrastructure/services/' print(f"Checking for available services in {accountName}, {region} region..") try: paginator = ssm.get_paginator('get_parameters_by_path') page_iterator = paginator.paginate(Path=path, Recursive=False, WithDecryption=False) for page in page_iterator: for param in page['Parameters']: serviceName = param['Name'].split('/')[-1] write_line = (f"{serviceName};{region};{accountName}") with open(report_file, "a") as file: print(write_line, file=file) except Exception as e: write_line = (f"ISSUE getting parameter from {path} in {region} region with ERROR:\n{e}\nDETAILS of page in paginator:\n{page}\nSERVICE-NAME is:\n {serviceName}") with open(report_file, "a") as file: print(write_line, file=file) print(f"Report saved in {report_file}\nReading file..\n")
Finally, we read our profile list and call list_aws_services
for each profile.
profile_list = read_profile_list(config_file) for p in profile_list: profileName = p.replace('"', '') list_aws_services(profileName)
Please note that script is NOT perfect and you may need to adjust it to your needs (as services come and go).
ssm-sap;us-west-2;my-fancy-account-name waf;us-west-2;my-fancy-account-name amplify;us-west-2;my-fancy-account-name braket;us-west-2;my-fancy-account-name chime-sdk-identity;us-west-2;my-fancy-account-name cloudhsmv2;us-west-2;my-fancy-account-name codestar;us-west-2;my-fancy-account-name eks;us-west-2;my-fancy-account-name
Full code available on GITHUB:
https://github.com/wozoopa/python/blob/main/list-aws-service-names-by-region.py
That’s all in this short mission..
Until next time Traveler..