回答:
ブログの投稿と他の回答で既にリンクされている要点から大いに影響を受けましたが、ここで問題に対する私の見解を示します。
いくつかの複雑なJMESpath関数を使用して、スナップショットのリストを取得しましたtr
。
免責事項:自己責任で使用してください。問題を回避し、健全なデフォルトを維持するために最善を尽くしましたが、問題が発生した場合でも責任を負いません。
#!/bin/sh
# remove x if you don't want to see the commands
set -ex
# Some variable initialisation with sane defaults
DRUN='--dry-run'
DO_DELETE=${1:-'no'}
REGION=${2:-'eu-west-1'}
ACCOUNTID=${3:-'self'}
# Get two temporary files
SNAP_FILE=$(mktemp)
IMAGE_FILE=$(mktemp)
# Get the snapshot list and the volume list
aws --region "$REGION" ec2 describe-snapshots --owner-ids "$ACCOUNTID" --query 'Snapshots[*].[SnapshotId]' --output text > "$SNAP_FILE"
aws --region "$REGION" ec2 describe-images --owners "$ACCOUNTID" --filters Name=state,Values=available --query 'Images[*].BlockDeviceMappings[*].Ebs.[SnapshotId]' --output text > "$IMAGE_FILE"
# Check if the outputed command should be dry-run (default) or not
if [ "$DO_DELETE" = "IAMSURE" ]
then
DRUN=''
fi
# count each snapshot id, decrease when a volume reference it, print delete command for those with no volumes
awk -v REGION="$REGION" -v DRUN="$DRUN" '
FNR==NR { snap[$1]++; next } # increment snapshots and get to next line in file immediately
{ snap[$1]-- } # we changed file, decrease the snap counter when a volume reference it
END {
for (s in snap) { # loop over the snapshots
if (snap[s] > 0) { # if we did not decrese under 1 that means there is no volume referencing this snapshot
cmd="aws --region " REGION " " DRUN " ec2 delete-snapshot --snapshot-id " s
print(cmd)
}
}
}
' "$SNAP_FILE" "$IMAGE_FILE"
# Clean up the temp files
rm "$SNAP_FILE" "$IMAGE_FILE"
スクリプト自体が十分にコメントされていることを願っています。
デフォルトの使用法(no-params)は、現在のアカウントとリージョンeu-west-1の孤立したスナップショットの削除コマンドを一覧表示します。
aws --region eu-west-1 --dry-run ec2 delete-snapshot --snapshot-id snap-81e5856a
aws --region eu-west-1 --dry-run ec2 delete-snapshot --snapshot-id snap-95c68c7e
aws --region eu-west-1 --dry-run ec2 delete-snapshot --snapshot-id snap-a3bf50bd
この出力をレビュー用にファイルにリダイレクトしてから、すべてのコマンドを実行するように仕向けることができます。
スクリプトではなく、それらを印刷するコマンドを実行したい場合は、交換してくださいprint(cmd)
によるsystem(cmd)
。
スクリプトの使用方法は次のsnap_cleaner
とおりです。
us-west-1リージョンでの予行演習用
./snap_cleaner no us-west-1
eu-central-1で使用可能なコマンド
./snap_cleaner IAMSURE eu-central-1
3番目のパラメーターを使用して、別のアカウントにアクセスできます(以前に別のアカウントにロールを切り替えることを好みます)。
ワンライナーとしてawkスクリプトを使用したスクリプトのバージョンを削除しました。
#!/bin/sh
set -ex
# Some variable initialisation with sane defaults
DRUN='--dry-run'
DO_DELETE=${1:-'no'}
REGION=${2:-'eu-west-1'}
ACCOUNTID=${3:-'self'}
# Get two temporary files
SNAP_FILE=$(mktemp)
IMAGE_FILE=$(mktemp)
# Get the snapshot list and the volume list
aws --region "$REGION" ec2 describe-snapshots --owner-ids "$ACCOUNTID" --query 'Snapshots[*].[SnapshotId]' --output text > "$SNAP_FILE"
aws --region "$REGION" ec2 describe-images --owners "$ACCOUNTID" --filters Name=state,Values=available --query 'Images[*].BlockDeviceMappings[*].Ebs.[SnapshotId]' --output text > "$IMAGE_FILE"
# Check if the outputed command should be dry-run (default) or not
if [ "$DO_DELETE" = "IAMSURE" ]
then
DRUN=''
fi
# count each snapshot id, decrease when a volume reference it, print delete command for those with no volumes
awk -v REGION="$REGION" -v DRUN="$DRUN" 'FNR==NR { snap[$1]++; next } { snap[$1]-- } END { for (s in snap) { if (snap[s] > 0) { cmd="aws --region " REGION " " DRUN " ec2 delete-snapshot --snapshot-id " s; print(cmd) } } }' "$SNAP_FILE" "$IMAGE_FILE"
# Clean up the temp files
rm "$SNAP_FILE" "$IMAGE_FILE"
Rodrigue Koffi(bonclay7)のGitHubで次のスクリプトを使用しましたが、かなりうまく機能します。
https://github.com/bonclay7/aws-amicleaner
コマンド:
amicleaner --check-orphans
ドキュメントのブログ投稿から、さらにいくつかのことが行われます。
それは実際にはそれ以上のことをします、今日ではそれが可能です:
- イメージと関連するスナップショットのリストを削除する
- AMIのマッピング:
- 名前を使用する
- タグを使用する
- AMIのフィルタリング:
- 実行中のインスタンスが使用
- 必要な容量を0に設定した自動スケーリンググループ(起動構成)から
- 自動スケーリンググループから切り離された起動構成から
- 保持するAMIの数を指定する
- 孤立したスナップショットのクリーニング
- 少しの報告
以下は、孤立したスナップショットを見つけるのに役立つスクリプトです。
comm -23 <(echo $(ec2-describe-snapshots --region eu-west-1 | grep SNAPSHOT | awk '{print $2}' | sort | uniq) | tr ' ' '\n') <(echo $(ec2-describe-images --region eu-west-1 | grep BLOCKDEVICEMAPPING | awk '{print $3}' | sort | uniq) | tr ' ' '\n') | tr '\n' ' '
(ここから)
また、serverfaultからこの記事を確認できます
PSもちろん、あなたの地域を反映するように地域を変更することができます
PPSここに更新されたコードがあります:
comm -23 \
<(echo $(aws ec2 describe-snapshots --region eu-west-1 |awk '/SNAPSHOT/ {print $2}' | sort -u) | tr ' ' '\n') \
<(echo $(aws ec2 describe-images --region eu-west-1 | awk '/BLOCKDEVICEMAPPING/ {print $3}' | sort -u) | tr ' ' '\n') | tr '\n' ' '
コードが実行するサンプルの説明は次のとおりです。
echo $(aws ec2 describe-snapshots --region eu-west-1 | awk '/SNAPSHOT/ {print $2}' | sort -u) | tr ' ' '\n')
スナップショットのリストをSTDOUTに送信します。この構造:
<(...)
仮想一時ファイルハンドラを作成して、comm
コマンドを2つの「ファイル」から読み取って比較します
これは、Daniil Yaroslavtsevがまさに求めているGitHub Gistコードスニペットです。
すべてのイメージとそのスナップショットのリストを使用し、IDをすべてのスナップショットIDのリストと比較します。残っているのは、孤立したものです。コードは上記の答えと同じ原理で機能しますが、より適切にフォーマットされており、少し読みやすくなっています。
コードは--query Snapshots[*].SnapshotId
オプション付きのJMESPathを利用し
ます(すでにディストリビューションにある場合は、jpコマンドラインユーティリティも使用できます。出力をテキストとしてフォーマットします。APIリファレンスへ--output text
のリンクといくつかの例です。 grep / awk / sort / uniq / trパイプの長いチェーンよりもエレガントです。
Todd Waltonによる警告:jsonドキュメントを解析するために異なるクエリ言語を使用する「jq」ユーティリティと間違えないでください。
定義済みのリージョンリスト内のすべてのスナップショットを反復処理して生成するsnapshots.pyスクリプトを記述しましたreport.csv
。このファイルには、すべてのスナップショットによって参照されるインスタンス、AMI、およびボリュームに関する情報が含まれています。
ダングリングスナップショットをインタラクティブに削除するコマンドもあります。