Azure Container Registryのタグなしマニフェストを一括削除する方法
はじめに
こんにちは或いはこんばんは。Ryuzakiです。
最近個人開発でAzure Container Registry(以下、ACR)を使用していて、思わぬハマり方をしてしまいました。そこで今回は、その問題の背景と解決方法について共有させていただきます。
発生した問題
個人での技術検証を目的とした開発において、ACRを利用していました。開発当初は特にタグを意識せずにコンテナイメージをPushしていたのですが、ある日Azureポータルを確認した際に気がついたことがあります。
それは、タグが紐付いていないマニフェストが大量に存在していたということです。
タグなしマニフェストが生まれる原因
この問題について調査したところ、以下のような仕組みで発生していることが分かりました。
- ACRに対して同じタグでPushを行うと、前回そのタグが紐付けられていたマニフェストからタグが移動してしまう(タグを設定せずにPushした場合は
latest
タグが自動的に移動) - あるマニフェストに紐付けられていたタグがすべて別のマニフェストに移動してしまうと、そのマニフェストのタグは
none
となってしまう(=タグなしマニフェストが生まれてしまう)
特に注意が必要なのは、このタグなしマニフェストはAzureポータル上から確認することができない点です。
確認するためには、以下のAzure CLIコマンドを実行する必要があります。
az acr manifest list-metadata --registry [レジストリ名] --name [リポジトリ名]
タグなしマニフェストも他のマニフェストと同様にACRの容量を使用するため、定期的な削除が必要となります。
削除方法の検討
タグなしマニフェストを削除する方法として、以下の3つを検討しました。
1. ACRのRetentionポリシーを利用する方法
以下のコマンドでRetentionポリシーを設定することで、自動削除が可能です。
az acr config retention update --registry [レジストリ名] --status enabled --days 30 --type UntaggedManifests
ただし、この機能はPremium Tierのコンテナレジストリでのみ利用可能です。個人開発・技術検証目的での利用には費用面でやや厳しいため、今回は採用を見送りました。
acr purge
コマンドを使用する方法
2. 公式ドキュメントでは以下のコマンドが紹介されています。
PURGE_CMD="acr purge --filter '[リポジトリ名]:.*' --untagged --ago 1d"
az acr run --cmd "$PURGE_CMD" --registry [レジストリ名] /dev/null
しかし、--dry-run
オプションを付けて実行してみたところ、すべてのマニフェストが削除対象として表示されたため、こちらも利用を断念しました。
acr manifest list-metadata
とacr repository delete
を組み合わせる方法
3. 最終的に採用したのが、以下のコマンドです。
az acr manifest list-metadata -r [レジストリ名] -n [リポジトリ名] --query "[?tags[0]==null].digest" -o tsv | xargs -I% az acr repository delete -n [レジストリ名] -t [リポジトリ名]@% -y
このコマンドはStackoverflowで紹介されていた方法を元に作成しました。
(show-metadata
は既に廃止されているため、後継のlist-metadata
に変更しています。)
実行時の注意点
このコマンドにはacr purge
コマンドのような--dry-run
オプションが用意されておらず、誤って必要なマニフェストを削除してしまうリスクがあります。
そのため、以下の手順での実行をお勧めします。
- コマンド前半部(
az acr manifest ... -o tsv
まで)のみを実行して削除対象を確認 - 削除対象に問題がないことを確認してから、コマンド全文を実行
おわりに
今回はACRのタグなしマニフェストの削除方法について共有させていただきました。同様の課題に直面している方の参考になれば幸いです。
ここまでお読みいただき、ありがとうございました。
Discussion