我试图从AWS帐户生成一个库存,并将其写入一个CSV文件中。
我有5个帐户,如开发,测试,DevOps,准备,和Prod。通常我使用下面的bash脚本生成,这需要一些手动任务;
#!/bin/bash
reg="ap-south-1"
input="profile.txt" ##This file contain all the profile name which configured on ~/.aws/credentials file
while IFS= read -r line
do
aws ec2 describe-instances --profile ${line} --region ${reg} --query "Reservations[*].Instances[*].[Tags[?Key=='Name']|[0].Value,InstanceId,InstanceType,PrivateIpAddress,State.Name,Platform,Placement.AvailabilityZone]" --output text >> ec2_inventory.csv
done < "$input"因此,这里我编写了一个python boto3脚本来生成ec2目录;
它可以像预期的那样工作在一个AWS配置文件上。以下脚本;
import boto3
session = boto3.Session(profile_name='dev')
ec2 = session.client('ec2', region_name='ap-south-1')
response = ec2.describe_instances()
import datetime
import csv
time = datetime.datetime.now().strftime ('%Y-%m-%d-%H-%M-%S')
filename_describe_instances = ('ec2_inventory_me-south-1_' + time + '.csv')
fieldnames = ['Instance_Name','ImageId', 'InstanceId', 'InstanceType', 'Availability_Zone', 'Platform', 'PrivateIpAddress','PublicIpAddress', 'State', 'SubnetId','VpcId', 'Environment', 'AccountId']
with open(filename_describe_instances, 'w', newline='') as csvFile:
writer = csv.writer(csvFile, dialect='excel')
writer.writerow(fieldnames)
for Reserv in response['Reservations']:
for Insta in Reserv['Instances']:
instance_imageid = Insta.get('ImageId', 'NULL')
instance_InstanceId = Insta.get('InstanceId', 'NULL')
instance_InstanceType = Insta.get('InstanceType', 'NULL')
instance_Availability_Zone = Insta['Placement'].get('AvailabilityZone', 'NULL')
instance_Platform = Insta.get('Platform', 'Linux')
instance_Private_IP = Insta.get('PrivateIpAddress', 'NULL')
instance_Public_IP = Insta.get('PublicIpAddress', 'NULL')
instance_State = Insta['State'].get('Name', 'NULL')
instance_Subnet = Insta.get('SubnetId', 'NULL')
instance_VPCID = Insta.get('VpcId', 'NULL')
instance_OwnerId = Reserv.get('OwnerId', 'NULL')
tags_list = []
for n in Insta.get('Tags', 'NULL'):
if n.get('Key', 'NULL') == 'Name':
instance_Name = n.get('Value', 'NULL')
if n.get('Key', 'NULL') == 'Environment':
instance_Environment = n.get('Value', 'NULL')
raw = [instance_Name,
instance_imageid,
instance_InstanceId,
instance_InstanceType,
instance_Availability_Zone,
instance_Platform,
instance_Private_IP,
instance_Public_IP,
instance_State,
instance_Subnet,
instance_VPCID,
instance_Environment,
instance_OwnerId]
writer.writerow(raw)
for o in raw:
o = 'NULL'
raw = []
csvFile.close()那么,有人能帮我用这个脚本从多个AWS帐户生成库存并将其写到一个CSV文件中吗?
发布于 2021-02-08 14:33:25
编辑-修改一些基本细节。
如果您已经配置了配置文件,那么最简单的事情就是对它们进行循环,并使用boto3 Session对象获取循环中的实例详细信息。
# set up your .csv writer, etc outside the loop
# iterate over your profiles
profiles = ['Dev', 'Test', 'DevOps', 'Prepared', 'Prod']
for name in profiles:
session = boto3.Session(profile_name=name)
ec2 = session.client('ec2')
response = ec2.describe_instances()
#format your row and write to the .csv您可以对配置文件列表进行硬编码,或者查看argparse以从命令行获取它们。
profile方法很好,并且是我广泛用于编写跨越帐户的报告和审计工具的工具。然而,对于交叉帐户的设置应该是什么样的,这一点值得深入挖掘。你有两个基本的选择:
通过每个帐户中的IAM用户访问
我强烈推荐后者作为一种更安全、更灵活的选择(除非您的组织已经使用了某种形式的SSO,这在概念上是相似的,但超出了这个答案的范围)。使用角色更安全,因为您只提供/管理单个凭据,并将自己设置为管理中央auth存储库中的所有帐户。
为此,SDK支持通过引用其他配置文件隐式调用sts:AssumeRole的配置文件。例如:
在~/.aws/credentials中
[management]
region=us-west-2
aws_access_key_id=...
aws_secret_access_key=...在~/.aws/config中
[profile foo-account]
source_profile=management
role_arn=arn:aws:iam::[foo-account-id]:role/Inventory(请注意两个文件之间的节头名称的差异-这是有意的)
鉴于以上所述,如果您运行aws --profile foo-account ec2 describe-instances,CLI将使用profile management下的密钥/机密调用sts:AssumeRole,目标是Inventory角色。如果设置AWS_PROFILE env变量,则可以省略--profile标志。在您的Python脚本中,使用profile_name参数对Session进行同样的操作。
该角色在您希望使用的每个帐户中定义(具有相应的配置文件),并具有足够的权限来读取所需的EC2数据,并且必须具有允许您的IAM用户调用库存角色上的sts:AssumeRole的AssumeRolePolicyDocument。
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"AWS": "arn:aws:iam::[foo-account-id]:user/[your-user]"
},
"Action": "sts:AssumeRole"
}
]
}同样,IAM用户需要一个允许它调用sts:AssumeRole的策略。
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": "sts:AssumeRole",
"Resource": "*"
}
]
}可以将"*"资源引用替换为角色ARN的列表。AssumeRolePolicyDocument允许指定的主体承担角色;用户策略允许用户针对指定的资源调用AssumeRole。这似乎有点违背直觉,但请记住,授权需要回答两个问题:用户可以这样做吗?资源允许这样做吗?
最后,随着您变得更高级,一旦您完成了基本的帐户/角色设置,您实际上可以省略配置文件,只需使用一个帐户列表直接调用sts:AssumeRole。
accounts = ['123...789', '234...890',]
sts = boto3.client('sts') #assumes you have a default profile set
for id in accounts:
role_arn = f'arn:aws:iam::{id}:role/Inventory'
creds = sts.assume_role(role_arn=role_arn, role_session_name='some-name')
session = boto3.Session(aws_access_key_id=creds['AccessKeyId'], ...)
ec2 = session.client('ec2')如果你必须做很多跨帐户工作,花时间思考和配置中央帐户绝对是值得的。副作用是,一旦您有了跨帐户角色,您就可以通过在管理帐户中的Lambda函数中运行它,并对该执行角色执行相同的权限设置(而不是将.csv写入S3 )来自动化它。
发布于 2021-05-22 20:18:38
有一个云管理平台可以做到这一点。它使用户能够从一个仪表板管理多个AWS帐户,并提供AWS库存管理和成本优化。它是免费的:https://cloudplexo.com。
https://stackoverflow.com/questions/66085408
复制相似问题