#!/bin/sh # cleanup_old_images.sh # 清理构建服务器上的旧 Docker 镜像和 Registry 旧版本 # 保留最近 KEEP_VERSIONS 个版本(默认 2) # 在 CI 构建完成后调用,防止磁盘空间耗尽 set -eu KEEP_VERSIONS="${KEEP_VERSIONS:-2}" REGISTRY_HOST="${REGISTRY_HOST:-172.30.18.198:5000}" SERVICES="xiaoxia-saas-api xiaoxia-saas-worker xiaoxia-saas-web" ACCEPT="application/vnd.docker.distribution.manifest.v2+json, application/vnd.oci.image.manifest.v1+json" echo "=== Docker Image Cleanup ===" echo "Keeping last ${KEEP_VERSIONS} versions per service" echo "" for svc in $SERVICES; do # 收集所有 v0.N.N 格式的版本号(去重,按版本号排序) versions=$(docker images --format "{{.Repository}}:{{.Tag}}" | \ grep "${svc}" | \ grep -E "v[0-9]+\.[0-9]+\.[0-9]+" | \ sed -E "s/.*:v([0-9]+\.[0-9]+\.[0-9]+).*/v\1/" | \ sort -t. -k1,1V -k2,2n -k3,3n | \ uniq) total=$(echo "$versions" | grep -c "^v" || true) if [ "$total" -gt "$KEEP_VERSIONS" ]; then remove_count=$((total - KEEP_VERSIONS)) to_remove=$(echo "$versions" | head -n "$remove_count") echo "[Registry] Cleaning old blobs for ${svc}..." for ver in $to_remove; do # 仓库名与服务名一致(如 xiaoxia-saas-api),不再裁剪前缀 manifest_url="http://admin:Xiaoxia2026@localhost:5000/v2/${svc}/manifests/${ver}" digest=$(curl -s -D- -H "Accept: ${ACCEPT}" "$manifest_url" | grep -i "^docker-content-digest:" | tr -d "\r" | awk "{print \$2}") if [ -n "$digest" ]; then curl -s -X DELETE -H "Accept: ${ACCEPT}" "http://admin:Xiaoxia2026@localhost:5000/v2/${svc}/manifests/${digest}" > /dev/null 2>&1 || true echo " Deleted registry tag: ${svc}:${ver}" fi done echo "[Local] Removing old local images for ${svc}..." for ver in $to_remove; do docker rmi "${svc}:${ver}" 2>/dev/null && echo " Removed local: ${svc}:${ver}" || true docker rmi "${REGISTRY_HOST}/${svc}:${ver}" 2>/dev/null && echo " Removed registry-ref: ${REGISTRY_HOST}/${svc}:${ver}" || true done else echo "[${svc}] ${total} version(s) found, within keep limit (${KEEP_VERSIONS})" fi echo "" done # 清理悬空镜像(构建中间层) echo "=== Pruning dangling images ===" pruned=$(docker image prune -f 2>&1) echo "$pruned" | tail -1 echo "" echo "=== Cleanup complete ===" echo "Current images:" docker images --format "table {{.Repository}}\t{{.Tag}}\t{{.Size}}" | grep -E "(xiaoxia|REPOSITORY)" || true