手动删除Docker镜像

8

我在本地Ubuntu上有大约50K张图片:

$ docker info
Containers: 3
Images: 49708
Storage Driver: aufs
 Root Dir: /var/lib/docker/aufs
 Backing Filesystem: extfs
 Dirs: 49714

docker rmi -f $(docker images | grep "something" | awk "{print \$3}")

这个命令会占用100%的CPU,而且速度很慢。有没有更快的方法来批量删除镜像呢?


可能是如何删除旧的和未使用的Docker镜像的重复问题。 - kenorb
2个回答

11

2

看起来你需要清理 /var/lib/docker/aufs。我没有这样做,这可能是不安全的。

但首先尝试使用由ndk编写的这些别名:

# Kill all running containers.
alias dockerkillall='docker kill $(docker ps -q)'

# Delete all stopped containers.
alias dockercleanc='printf "\n>>> Deleting stopped containers\n\n" && docker rm $(docker ps -a -q)'

# Delete all untagged images.
alias dockercleani='printf "\n>>> Deleting untagged images\n\n" && docker rmi $(docker images -q -f dangling=true)'

# Delete all stopped containers and untagged images.
alias dockerclean='dockercleanc || true && dockercleani'

# Delete all
alias dockercleanup='dockerkillall || true && dockercleanc || true && dockercleani'

更新:自本答案发布以来,已经引入了几种新的手动清理方法。我将引用GitHub用户adamhadani的代码(需要docker-py):

#!/usr/bin/env python
"""
Check all existing Docker containers for their mapped paths, and then purge any
zombie directories in docker's volumes directory which don't correspond to an
existing container.
"""
import logging
import os
import sys
from shutil import rmtree

import docker


DOCKER_VOLUMES_DIR = "/var/lib/docker/vfs/dir"


def get_immediate_subdirectories(a_dir):
    return [os.path.join(a_dir, name) for name in os.listdir(a_dir)
            if os.path.isdir(os.path.join(a_dir, name))]


def main():
    logging.basicConfig(level=logging.INFO)

client = docker.Client()

valid_dirs = []
for container in client.containers(all=True):
    volumes = client.inspect_container(container['Id'])['Volumes']
    if not volumes:
        continue

    for _, real_path in volumes.iteritems():
        if real_path.startswith(DOCKER_VOLUMES_DIR):
            valid_dirs.append(real_path)

all_dirs = get_immediate_subdirectories(DOCKER_VOLUMES_DIR)
invalid_dirs = set(all_dirs).difference(valid_dirs)

logging.info("Purging %s dangling Docker volumes out of %s total volumes found.",
             len(invalid_dirs), len(all_dirs))
for invalid_dir in invalid_dirs:
    logging.info("Purging directory: %s", invalid_dir)
    rmtree(invalid_dir)

logging.info("All done.")


if __name__ == "__main__":
    sys.exit(main())

1
RMI与悬空也需要很长时间。我不想删除所有的图像,这就是为什么要使用grep“something”的原因。在文件系统中胡乱操作是不可行的,因为我需要保留一些图像,而不仅仅是执行rm -rf.. - shayy

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接