长时间运行Docker时,系统中有很多图像。如何安全地删除所有未使用的Docker镜像以释放存储空间?
此外,我还要删除几个月前提取的图像,这些图片具有正确的TAG
。
所以,我并不是要求仅删除未标记的图像。我正在寻找一种方法来删除一般未使用的图像,其中包括未标记的图像和其他图像,例如几个月前提取的正确TAG
。
答案 0 :(得分:1223)
2016年9月更新:Docker 1.13:PR 26108和commit 86de7c0引入了一些新命令,以帮助可视化Docker守护程序数据在磁盘上占用多少空间并允许轻松清理&# 34;不需要"过量。
docker system prune
将删除所有悬空数据(即按顺序:容器停止,没有容器的卷和没有容器的图像)。甚至是未使用的数据,false
选项。
您还有:
对于未使用的图像,请使用-a
(用于删除悬空和未图像的图像)。
警告:' 未使用'表示未被任何容器引用的图像":在使用docker image prune -a
之前要小心。
正如A L answer中所示,-a
将删除所有未使用的图像,而不仅仅是悬空图片......可以是太多了。
将docker system prune --all
与--filter
option相结合可能是限制修剪的好方法(docker SDK API 1.28 minimum, so docker 17.04+)
目前支持的过滤器是:
docker xxx prune
- 仅删除在给定时间戳之前创建的容器,图像和网络until (<timestamp>)
(label
,label=<key>
,label=<key>=<value>
或label!=<key>
) - 仅删除容器,图片,网络和卷(或如果使用label!=<key>=<value>
,则不使用指定的标签。参见&#34; Prune images&#34;举个例子。
原始答案(2016年9月)
我通常会这样做:
label!=...
我有alias for removing those [dangling images] 13:docker rmi $(docker images --filter "dangling=true" -q --no-trunc)
drmi
过滤器找到未使用的图片
这样,删除了标记图像不再引用的任何中间图像。
我对exited processes (containers)
执行相同的第一次dangling=true
从技术上讲,在清理图像之前应先清理容器,因为这样可以捕获更多悬空图像并减少错误。
Jess Frazelle (jfrazelle)有bashrc function:
alias drmae='docker rm $(docker ps -qa --no-trunc --filter "status=exited")'
删除旧图像,而不只是&#34;未引用的悬空&#34;图片,您可以考虑docker-gc
:
一个简单的Docker容器和图像垃圾收集脚本。
- 删除超过一小时前退出的容器。
- 删除之后不属于任何剩余容器的图像。
答案 1 :(得分:101)
更新第二个(2017-07-08):
使用更新的system prune
(再次)参考VonC。不耐烦的人可以使用-f, --force
选项跳过提示:
docker system prune -f
不耐烦的鲁莽可以另外删除&#34;未使用的图像,而不仅仅是悬空图像&#34;使用-a, --all
选项:
docker system prune -af
https://docs.docker.com/engine/reference/commandline/system_prune/
更新
请参阅使用最近添加的prune
命令的VonC's answer。这是相应的shell别名方便:
alias docker-clean=' \
docker container prune -f ; \
docker image prune -f ; \
docker network prune -f ; \
docker volume prune -f '
旧答案:
删除已停止(已退出)的容器:
$ docker ps --no-trunc -aqf "status=exited" | xargs docker rm
删除未使用的(悬空)图像:
$ docker images --no-trunc -aqf "dangling=true" | xargs docker rmi
如果您对 不可撤销的数据丢失 已经 极其谨慎 ,那么您可以删除未使用的(卷(v1.9及以上):
$ docker volume ls -qf "dangling=true" | xargs docker volume rm
这里有一个方便的shell别名:
alias docker-clean=' \
docker ps --no-trunc -aqf "status=exited" | xargs docker rm ; \
docker images --no-trunc -aqf "dangling=true" | xargs docker rmi ; \
docker volume ls -qf "dangling=true" | xargs docker volume rm'
参考文献:
答案 2 :(得分:50)
删除超过一个月的旧标记图片:
$ docker images --no-trunc --format '{{.ID}} {{.CreatedSince}}' \
| grep ' months' | awk '{ print $1 }' \
| xargs --no-run-if-empty docker rmi
请注意,它失败删除容器使用的图像,在存储库中引用,具有依赖子图像......这可能是您想要的。否则只需添加-f
标志。
/etc/cron.daily/docker-gc
脚本示例:
#!/bin/sh -e
# Delete all stopped containers (including data-only containers).
docker ps -a -q --no-trunc --filter "status=exited" | xargs --no-run-if-empty docker rm -v
# Delete all tagged images more than a month old
# (will fail to remove images still used).
docker images --no-trunc --format '{{.ID}} {{.CreatedSince}}' | grep ' months' | awk '{ print $1 }' | xargs --no-run-if-empty docker rmi || true
# Delete all 'untagged/dangling' (<none>) images
# Those are used for Docker caching mechanism.
docker images -q --no-trunc --filter dangling=true | xargs --no-run-if-empty docker rmi
# Delete all dangling volumes.
docker volume ls -qf dangling=true | xargs --no-run-if-empty docker volume rm
答案 3 :(得分:20)
其他答案很棒,特别是:
docker system prune # doesn't clean out old images
docker system prune --all # cleans out too much
但我在两个命令的中间需要一些东西,所以我需要filter
选项:
docker image prune --all --filter "until=4320h" # delete images older than 6 months ago; 4320h = 24 hour/day * 30 days/month * 6 months
希望有所帮助:)
答案 4 :(得分:19)
假设你有Docker 1.13或更高,你可以使用prune命令。对于专门用于删除旧图像的问题,您需要第一个。
# Remove unused images
docker image prune
# Remove stopped containers.
docker container prune
# Remove unused volumes
docker volume prune
# Remove unused networks
docker network prune
# Command to run all prunes:
docker system prune
我建议不习惯使用docker system prune
命令。我认为用户会不小心删除他们不想要的东西。就个人而言,我将主要使用docker image prune
和docker container prune
命令。
答案 5 :(得分:12)
这对我有用:
docker rmi $(docker images | grep "^<none>" | awk "{print $3}")
答案 6 :(得分:10)
到目前为止(Docker版本1.12),我们使用以下命令删除所有正在运行的容器。此外,如果我们要删除卷,我们可以使用以下命令中的相应标记-v手动执行该操作。
删除所有已退出的容器
docker rm $(docker ps -q -f status=exited)
删除所有已停止的容器
docker rm $(docker ps -a -q)
删除所有正在运行和已停止的容器
docker stop $(docker ps -a -q)
docker rm $(docker ps -a -q)
删除所有容器,没有任何条件
docker container rm $(docker container ps -aq)
但是,在1.13及更高版本中,对于完整的系统和清理,我们可以直接使用以下命令:
docker system prune
将删除所有未使用的容器,图像,网络和卷。我们也可以使用以下清理单个组件的命令来执行此操作:
docker container prune
docker image prune
docker network prune
docker volume prune
答案 7 :(得分:7)
我最近在我的一台服务器上写了一个脚本来解决这个问题:
#!/bin/bash
# Remove all the dangling images
DANGLING_IMAGES=$(docker images -qf "dangling=true")
if [[ -n $DANGLING_IMAGES ]]; then
docker rmi "$DANGLING_IMAGES"
fi
# Get all the images currently in use
USED_IMAGES=($( \
docker ps -a --format '{{.Image}}' | \
sort -u | \
uniq | \
awk -F ':' '$2{print $1":"$2}!$2{print $1":latest"}' \
))
# Get all the images currently available
ALL_IMAGES=($( \
docker images --format '{{.Repository}}:{{.Tag}}' | \
sort -u \
))
# Remove the unused images
for i in "${ALL_IMAGES[@]}"; do
UNUSED=true
for j in "${USED_IMAGES[@]}"; do
if [[ "$i" == "$j" ]]; then
UNUSED=false
fi
done
if [[ "$UNUSED" == true ]]; then
docker rmi "$i"
fi
done
答案 8 :(得分:5)
以下命令将删除48小时以上的图像。
$docker image prune --all --filter until=48h
答案 9 :(得分:5)
这是一个清理Docker镜像并回收空间的脚本。
#!/bin/bash -x
## Removing stopped container
docker ps -a | grep Exited | awk '{print $1}' | xargs docker rm
## If you do not want to remove all container you can have filter for days and weeks old like below
#docker ps -a | grep Exited | grep "days ago" | awk '{print $1}' | xargs docker rm
#docker ps -a | grep Exited | grep "weeks ago" | awk '{print $1}' | xargs docker rm
## Removing Dangling images
## There are the layers images which are being created during building a Docker image. This is a great way to recover the spaces used by old and unused layers.
docker rmi $(docker images -f "dangling=true" -q)
## Removing images of perticular pattern For example
## Here I am removing images which has a SNAPSHOT with it.
docker rmi $(docker images | grep SNAPSHOT | awk '{print $3}')
## Removing weeks old images
docker images | grep "weeks ago" | awk '{print $3}' | xargs docker rmi
## Similarly you can remove days, months old images too.
原始剧本
https://github.com/vishalvsh1/docker-image-cleanup
通常,Docker会保留所有与图像构建和图层相关的临时文件
<强>的/ var / lib中/搬运工强>
此路径是系统的本地路径,通常位于根分区&#34; /&#34; 。
您可以安装更大的磁盘空间并将/var/lib/docker
的内容移动到新的安装位置并创建符号链接。
这样,即使Docker镜像占用空间,它也不会影响您的系统,因为它将使用其他一些安装位置。
答案 10 :(得分:3)
如果您想删除几个月前拉 X 的图片,可以尝试以下示例删除三个月前创建的图片:
Animation anim1 = AnimationUtils.loadAnimation(getApplicationContext(),R.anim.animationtext);
anim1.setRepeatCount(Animation.INFINITE);
tviPrueba.startAnimation(anim1);
答案 11 :(得分:3)
我正在使用此命令:
export BEFORE_DATETIME=$(date --date='10 weeks ago' +"%Y-%m-%dT%H:%M:%S.%NZ")
docker images -q | while read IMAGE_ID; do
export IMAGE_CTIME=$(docker inspect --format='{{.Created}}' --type=image ${IMAGE_ID})
if [[ "${BEFORE_DATETIME}" > "${IMAGE_CTIME}" ]]; then
echo "Removing ${IMAGE_ID}, ${BEFORE_DATETIME} is earlier then ${IMAGE_CTIME}"
docker rmi -f ${IMAGE_ID};
fi;
done
这将删除创建时间大于10周前的所有图像。
答案 12 :(得分:2)
@VonC已经给出了一个非常好的答案,但是为了完整性,这里有一个我一直在使用的小脚本 - 如果你有一些东西,它还会破坏任何差事Docker进程:
#!/bin/bash
imgs=$(docker images | awk '/<none>/ { print $3 }')
if [ "${imgs}" != "" ]; then
echo docker rmi ${imgs}
docker rmi ${imgs}
else
echo "No images to remove"
fi
procs=$(docker ps -a -q --no-trunc)
if [ "${procs}" != "" ]; then
echo docker rm ${procs}
docker rm ${procs}
else
echo "No processes to purge"
fi
答案 13 :(得分:2)
几周前删除旧容器。
docker rm $(docker ps -a | grep "weeks" | awk '{ print $1; }')
几周前删除旧图片。小心。这将删除几周前创建但您的新图像可能正在使用的基本图像。
docker rmi $(docker images | grep 'weeks' | awk '{ print $3; }')
答案 14 :(得分:2)
如何删除已标记的图片
docker rmi the tag
docker rmi图片。
#可以在一个docker rmi中完成,例如:# docker rmi&lt; repo:tag&gt; &LT;图像标识&GT;
(这适用于2016年11月,Docker版本1.12.2)
e.g。
$ docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
usrxx/the-application 16112805 011fd5bf45a2 12 hours ago 5.753 GB
usryy/the-application vx.xx.xx 5af809583b9c 3 days ago 5.743 GB
usrzz/the-application vx.xx.xx eef00ce9b81f 10 days ago 5.747 GB
usrAA/the-application vx.xx.xx 422ba91c71bb 3 weeks ago 5.722 GB
usrBB/the-application v1.00.18 a877aec95006 3 months ago 5.589 GB
$ docker rmi usrxx/the-application:16112805 && docker rmi 011fd5bf45a2
$ docker rmi usryy/the-application:vx.xx.xx && docker rmi 5af809583b9c
$ docker rmi usrzz/the-application:vx.xx.xx eef00ce9b81f
$ docker rmi usrAA/the-application:vx.xx.xx 422ba91c71bb
$ docker rmi usrBB/the-application:v1.00.18 a877aec95006
e.g。脚本删除超过2周的任何内容。
IMAGESINFO=$(docker images --no-trunc --format '{{.ID}} {{.Repository}} {{.Tag}} {{.CreatedSince}}' |grep -E " (weeks|months|years)")
TAGS=$(echo "$IMAGESINFO" | awk '{ print $2 ":" $3 }' )
IDS=$(echo "$IMAGESINFO" | awk '{ print $1 }' )
echo remove old images TAGS=$TAGS IDS=$IDS
for t in $TAGS; do docker rmi $t; done
for i in $IDS; do docker rmi $i; done
答案 15 :(得分:2)
要删除没有容器运行的标记图像,您必须使用一个小脚本:
#!/bin/bash
# remove not running containers
docker rm $(docker ps -f "status=exited" -q)
declare -A used_images
# collect images which has running container
for image in $(docker ps | awk 'NR>1 {print $2;}'); do
id=$(docker inspect --format="{{.Id}}" $image);
used_images[$id]=$image;
done
# loop over images, delete those without a container
for id in $(docker images --no-trunc -q); do
if [ -z ${used_images[$id]} ]; then
echo "images is NOT in use: $id"
docker rmi $id
else
echo "images is in use: ${used_images[$id]}"
fi
done
答案 16 :(得分:1)
如果您希望自动/定期清理已退出的容器并删除正在运行的容器未使用的图像和卷,则可以下载图像meltwater/docker-cleanup
。
跑步:
docker run -d -v /var/run/docker.sock:/var/run/docker.sock:rw -v /var/lib/docker:/var/lib/docker:rw --restart=unless-stopped meltwater/docker-cleanup:latest
默认情况下每30分钟运行一次。但是,您可以使用此标志以秒为单位设置延迟时间(DELAY_TIME = 1800选项)。
更多详情:https://github.com/meltwater/docker-cleanup/blob/master/README.md
答案 17 :(得分:1)
docker system prune -a
(系统会要求您确认该命令。如果您知道自己在做什么,请使用-f
强行运行。)
答案 18 :(得分:1)
docker rm $(docker ps -faq)
docker rmi $(docker ps -faq)
-f力
-全部
-q在模式下
答案 19 :(得分:1)
docker rm `docker ps -aq`
或
docker rm $(docker ps -q -f status=exited)
答案 20 :(得分:1)
如果您自己(从其他一些较旧的基础映像中)构建这些修剪后的映像,请谨慎使用上述基于docker image prune
的可接受的解决方案,因为该命令比较钝,并且还会尝试删除该命令所需的所有依赖项您最新的图片(该命令可能应该重命名为docker image*s* prune
)。
我为docker映像构建管道(其中有每日构建和标签=日期为YYYYMMDD
格式)提出的解决方案是:
# carefully narrow down the image to be deleted (to avoid removing useful static stuff like base images)
my_deleted_image=mirekphd/ml-cpu-py37-vsc-cust
# define the monitored image (tested for obsolescence), which will be usually the same as deleted one, unless deleting some very infrequently built image which requires a separate "clock"
monitored_image=mirekphd/ml-cache
# calculate the oldest acceptable tag (date)
date_week_ago=$(date -d "last week" '+%Y%m%d')
# get the IDs of obsolete tags of our deleted image
# note we use monitored_image to test for obsolescence
my_deleted_image_obsolete_tag_ids=$(docker images --filter="before=$monitored_image:$date_week_ago" | grep $my_deleted_image | awk '{print $3}')
# remove the obsolete tags of the deleted image
# (note it typically has to be forced using -f switch)
docker rmi -f $my_deleted_image_obsolete_tag_ids
答案 21 :(得分:0)
偶尔我遇到Docker将分配并继续使用磁盘空间的问题,即使空间未分配给任何特定图像或现有容器。我不小心生成这个问题的最新方法是在RHEL 7.1中使用“docker-engine”centos build而不是“docker”。似乎发生的事情有时是容器清理没有成功完成,然后空间永远不会被重复使用。当我分配为/ var / lib / docker文件的80GB驱动器时,我不得不想出一个创造性的方法来解决这个问题。
这是我想出的。首先解决磁盘已满错误:
此时我不再有磁盘已满错误,但我仍然浪费了大量空间。接下来的步骤是照顾它。
启动Docker:systemctl start docker
保存所有图片: docker save $(docker images | sed -e'/ ^ / d'-e'/ ^ REPOSITORY / d'-e's,[] [] ,:,' - e',[]。< / em> ,,')&gt; /root/docker.img
卸载docker。
清除/ var / lib / docker中的所有内容: rm -rf / var / lib / docker / [cdintv] *
重新安装docker
启用docker:systemctl enable docker
启动docker:systemctl start docker
恢复图片: docker load&lt; /root/docker.img
启动您需要运行的所有持久性容器。
这使我的磁盘使用率从docker的67 GB减少到docker的6 GB。
我不建议日常使用。但是,当看起来docker已经丢失了使用过的磁盘空间来处理软件错误或意外重启时运行是很有用的。
答案 22 :(得分:0)
也要修剪所有图像和卷
docker system prune -af --volumes
答案 23 :(得分:0)
首先,运行docker images
以查看图像列表并将IMAGE HASH ID复制到剪贴板。
运行docker rmi -f <Image>
记住选项-f
是强制删除。
答案 24 :(得分:0)
如果有很多的话,删除它们确实很繁琐,但是对我们来说幸运的是Docker有一些命令可以帮助我们消除悬空的图像。在较旧的Docker版本中(今天仍然有效),您可以通过运行docker rmi -f $(docker images -f "dangling=true" -q)
自行删除悬空的镜像。
答案 25 :(得分:0)
我通常使用docker rm -f $(docker ps -a -q)
和docker system prune
来清除所有悬空的容器。