AWS EC2实例每周仅根卷无重启AMI备份及旧镜像清理方案咨询
方案1:修改现有Bash脚本增加自动清理逻辑
核心实现逻辑如下:
- 给生成的AMI统一命名前缀,附加时间戳保证名称唯一
- 新增清理逻辑:每次创建完新AMI后,筛选同前缀的历史AMI,仅保留指定数量的最新镜像,超出部分自动注销AMI并删除关联的根卷快照,避免产生不必要的存储费用
修改后的完整脚本如下:
#!/bin/bash # 可调整配置项 INSTANCE_ID="i-12345" AMI_NAME_PREFIX="ec2-root-only-ami" # 保留最新的AMI数量,可按需调整 KEEP_AMIS_COUNT=4 # AMI和对应快照的标签,方便资源分组管理 AMI_TAGS="Key=Purpose,Value=Backup Key=Type,Value=RootOnlyAMI" # 获取实例根设备名 root_device=$(aws ec2 describe-instances --instance-ids ${INSTANCE_ID} --query 'Reservations[*].Instances[*].RootDeviceName' --output text) echo "根设备为: ${root_device}" # 构造非根卷排除参数 exclude_devices="" for device in $(aws ec2 describe-instances --instance-ids ${INSTANCE_ID} --query 'Reservations[*].Instances[*].BlockDeviceMappings[*].DeviceName' --output text ); do if [ "${device}" != "${root_device}" ]; then exclude_devices="${exclude_devices} DeviceName=${device},NoDevice=" fi; done # 生成带时间戳的唯一AMI名称 ami_name="${AMI_NAME_PREFIX}-$(date +%Y%m%d%H%M)" echo "正在创建AMI: ${ami_name}" # 创建仅根卷的AMI,获取返回的AMI ID new_ami_id=$(aws ec2 create-image --instance-id ${INSTANCE_ID} \ --block-device-mappings ${exclude_devices} \ --name "${ami_name}" \ --description "仅根卷备份,实例ID: ${INSTANCE_ID}" \ --tag-specifications "ResourceType=image,Tags=[{Key=Name,Value=${ami_name}} ${AMI_TAGS}]" "ResourceType=snapshot,Tags=[${AMI_TAGS}]" \ --no-reboot \ --query 'ImageId' --output text) echo "新AMI创建成功,ID: ${new_ami_id}" # 清理旧AMI逻辑 echo "开始清理旧AMI,保留最新${KEEP_AMIS_COUNT}个" # 查询所有符合前缀的可用AMI,按创建时间倒序,跳过保留数量后的所有旧AMI old_ami_ids=$(aws ec2 describe-images --owners self \ --filters "Name=name,Values=${AMI_NAME_PREFIX}*" "Name=state,Values=available" \ --query 'Images | sort_by(@, &CreationDate) | reverse(@) | ['${KEEP_AMIS_COUNT}':].ImageId' \ --output text) if [ -n "${old_ami_ids}" ]; then for ami_id in ${old_ami_ids}; do echo "正在注销旧AMI: ${ami_id}" # 先获取AMI关联的快照ID snapshot_id=$(aws ec2 describe-images --image-ids ${ami_id} \ --query 'Images[*].BlockDeviceMappings[*].Ebs.SnapshotId' \ --output text) # 注销AMI aws ec2 deregister-image --image-id ${ami_id} # 删除关联快照 if [ -n "${snapshot_id}" ]; then echo "正在删除关联快照: ${snapshot_id}" aws ec2 delete-snapshot --snapshot-id ${snapshot_id} fi done else echo "无需要清理的旧AMI" fi echo "任务执行完成"
脚本使用注意事项
- 执行脚本的IAM身份(用户/角色)需要额外新增
ec2:DeregisterImage、ec2:DeleteSnapshot权限 - 可将脚本加入crontab实现每周定时执行,例如下方配置为每周日凌晨2点执行:
0 2 * * 0 /path/to/your/script.sh >> /var/log/ami-backup.log 2>&1
方案2:无服务器替代方案
如果不想维护本地脚本和运行环境,可以使用AWS原生服务实现:
- 用EventBridge设置每周定时触发规则
- 关联Lambda函数执行和上述脚本完全一致的逻辑,Python/Node.js均可实现
- 可额外配置SNS主题,任务成功/失败时推送告警通知
内容的提问来源于stack exchange,提问作者Ravi Rathnam
相关产品推荐
相关产品推荐

