谁用占用了这么多磁盘空间?Docker System命令详解

开发 前端
用了一段时间Docker后,会发现它占用了不少硬盘空间。还好Docker 1.13引入了解决方法,它提供了简单的命令来查看/清理Docker使用的磁盘空间。

用了一段时间Docker后,会发现它占用了不少硬盘空间。还好Docker 1.13引入了解决方法,它提供了简单的命令来查看/清理Docker使用的磁盘空间。

[[216788]]

本文通过一个简单的示例,可以证明Docker能够很快地将磁盘占满。该示例通过play-with-docker.com运行。点击Add new instance即可创建新的实例,该实例安装了***版的Docker 17.03。这篇博客主要讨论磁盘空间,那么不妨使用df命令查看磁盘的初始状态:

 

  1. $ df -h 
  2. Filesystem           Size       Used Available Use% Mounted on 
  3. /dev/mapper/...      10.0G    443.3M      9.6G   4% / 
  4. tmpfs                60.0G         0     60.0G   0% /dev 
  5. tmpfs                60.0G         0     60.0G   0% /sys/fs/cgroup 
  6. /dev/xvda1           49.1G      3.7G     43.3G   8% /etc/resolv.conf 
  7. /dev/xvda1           49.1G      3.7G     43.3G   8% /etc/hostname 
  8. /dev/xvda1           49.1G      3.7G     43.3G   8% /etc/hosts 
  9. shm                  64.0M         0     64.0M   0% /dev/shm 
  10. /dev/mapper/...      10.0G    443.3M      9.6G   4% /graph/overlay2 

可知,在新创建的play-with-docker.com实例,一共有10GB磁盘空间,其中接近500MB已被占用。

接下来编写Dockerfile来创建一个镜像。这个镜像基于Alpine镜像;镜像将写入3个随机的文件,每个文件1GB,文件由dd命令生成;因为这个镜像并没有实际作用,因此CMD设为/bin/true。

 

  1. FROM alpine 
  2. RUN dd if=/dev/zero of=1g1.img bs=1G count=1 
  3. RUN dd if=/dev/zero of=1g2.img bs=1G count=1 
  4. RUN dd if=/dev/zero of=1g3.img bs=1G count=1 
  5. CMD /bin/true 

运行docker build -t test .即可创建镜像,执行完成后将生成一个3GB的镜像。

 

  1. $ docker image ls 
  2. REPOSITORY          TAG                CREATED             SIZE 
  3. test                latest             38 seconds ago      3.23GB 
  4. alpine              latest             5 weeks ago         3.99MB 

不难理解,该镜像占用了相应大小的磁盘空间。

 

  1. $ df -h 
  2. Filesystem        Size       Used Available Use% Mounted on 
  3. /dev/mapper/...   10.0G      3.4G      6.5G  34% / 

若只写入2个随机文件,则需要修改Dockerfile,删掉一行。为了避免构建镜像时使用缓存,我在dd命令之前添加了一行echo命令。

 

  1. FROM alpine 
  2. RUN echo foo 
  3. RUN dd if=/dev/zero of=1g1.img bs=1G count=1 
  4. RUN dd if=/dev/zero of=1g2.img bs=1G count=1 
  5. # RUN dd if=/dev/zero of=1g3.img bs=1G count=1 
  6. CMD /bin/true 

本来以为这样可以节省1GB磁盘空间,然而实际情况更加糟糕!

 

  1. $ df -h 
  2. Filesystem        Size       Used Available Use% Mounted on 
  3. /dev/mapper/...   10.0G      5.4G      4.5G  54% / 

旧的Docker镜像一直存在,最终磁盘空间会很快被用完。Docker 1.13引入了docker system df命令,类似于Linux上的df命令,用于查看Docker的磁盘使用情况。

 

  1. $ docker system df 
  2. TYPE                TOTAL     ACTIVE    SIZE          RECLAIMABLE 
  3. Images              3         0         5.373GB       5.373GB (100%) 
  4. Containers          0         0         0B            0B 
  5. Local Volumes       0         0         0B            0B 

可知,实例上一共有3个Docker镜像: apline镜像,包含3个1GB随机文件的镜像以及包含2个1GB随机文件的镜像。这些镜像占用了超过5GB磁盘空间。由于我们并没有基于这些镜像运行容器,所以它们都可以被删除,所以可回收的(RECLAIMABLE)磁盘空间为100%。使用docker run test运行test镜像再查看:

  1. $ docker system df 
  2. TYPE                TOTAL     ACTIVE    SIZE          RECLAIMABLE 
  3. Images              3         1         5.373GB       3.225GB (60%) 
  4. Containers          1         0         0B            0B 
  5. Local Volumes       0         0         0B            0B 

现在情况就不同了,我运行了一个容器,它执行/bin/true之后就很快退出了。

这个容器绑定了test镜像,test镜像被标记为活跃(active)因而不能被删除,这导致可回收的磁盘空间变少了。

现在来清理一下磁盘空间。

Docker提供了docker system prune,可以用于清理dangling镜像(参考What are Docker : images?)和容器,以及失效的数据卷和网络。

 

  1. $ docker system prune 
  2. WARNING! This will remove: 
  3.         - all stopped containers 
  4.         - all volumes not used by at least one container 
  5.         - all networks not used by at least one container 
  6.         - all dangling images 
  7. Are you sure you want to continue? [y/N] y 
  8. Deleted Containers: 
  9. 1cdf866157b4a97e151125af3c2a7f186a59b6f63807e2014ce1a00d68f44e1d 
  10. Deleted Images: 
  11. deleted: sha256:f59bb277... 
  12. deleted: sha256:695b8e70... 
  13. deleted: sha256:93b1cceb... 
  14. deleted: sha256:c74d6bcd... 
  15. deleted: sha256:df8b9bb1... 
  16. deleted: sha256:dfe8340f... 
  17. deleted: sha256:ce1ee654... 
  18. Total reclaimed space: 3.221GB 

根据警告信息可知,这个命令会删除所有关闭的容器以及dangling镜像。示例中,含有3个1GB随机文件的镜像的名称被占用了,名称为:,为dangling镜像,因此会被删除。同时,所有的中间镜像也会被删除。这样的话,一共3GB的磁盘空间被回收了!

更进一步,使用-a选项可以做深度清理。这时我们会看到更加严重的WARNING信息:

 

  1. $ docker system prune -a 
  2. WARNING! This will remove: 
  3.         - all stopped containers 
  4.         - all volumes not used by at least one container 
  5.         - all networks not used by at least one container 
  6.         - all images without at least one container associated to them 
  7. Are you sure you want to continue? [y/N] y 
  8. Deleted Images: 
  9. untagged: test:latest 
  10. deleted: sha256:c515ebfa2... 
  11. deleted: sha256:07302c011... 
  12. deleted: sha256:37c0c6474... 
  13. deleted: sha256:5cc2b6bc4... 
  14. deleted: sha256:b283b9c35... 
  15. deleted: sha256:8a8b9bd8b... 
  16. untagged: alpine:latest 
  17. untagged: alpine@sha256:58e1a1bb75db1... 
  18. deleted: sha256:4a415e366... 
  19. deleted: sha256:23b9c7b43... 
  20. Total reclaimed space: 2.151GB 

这个命令将清理整个系统,并且只会保留真正在使用的镜像,容器,数据卷以及网络,因此需要格外谨慎。比如,我们不能在生产环境中运行prune -a命令,因为一些备用镜像(用于备份,回滚等)有时候需要用到,如果这些镜像被删除了,则运行容器时需要重新下载。

此时,所有未绑定容器的镜像将会被删除。由于***次prune命令删除了所有容器,因此所有镜像(它们没有绑定任何容器)都会被删除。

 

  1. $ df -h 
  2. Filesystem          Size      Used Available Use% Mounted on 
  3. /dev/mapper/...    10.0G    442.5M      9.6G   4% / 

现在,已使用的磁盘空间又变成了4%。本文的示例只是冰山一角,因为一旦我们运行了真正的容器,并且使用了Docker数据卷和Docker网络,则磁盘空间将会更快用完。感兴趣的话,可以查看博客***的视频(不要忘了订阅!)。在视频中,我介绍一个简单的WordPress应用,它由数个容器,数据卷以及网络构成。这个应用可以很快地消耗掉磁盘空间,我将介绍如何处理这个问题。

责任编辑:未丽燕 来源: 代码湾
相关推荐

2023-11-13 08:49:54

2021-07-30 16:28:42

磁盘微信工具

2010-05-27 17:51:55

Linux查看磁盘空间

2018-06-26 15:00:24

Docker安全风险

2021-02-11 08:11:50

Window10Docker容器

2015-11-25 13:37:52

磁盘空间LinuxUbuntu

2021-03-05 08:29:20

DeleteMysql数据结构

2024-06-04 09:36:37

2021-08-30 07:53:54

Linuxncdu磁盘

2010-04-08 15:24:36

Windows磁盘空间

2009-11-30 17:20:32

LINUX虚拟机磁盘

2011-01-18 10:25:19

Linux磁盘分区

2022-06-28 07:14:23

WizTree磁盘文件清理

2021-08-04 12:09:04

Linuxdf命令

2020-12-03 06:18:04

磁盘Docker容器

2023-04-18 23:31:59

Linux磁盘系统

2017-08-11 14:21:33

软件开发前端框架

2024-04-02 08:41:10

ArrayListSubList场景

2023-07-17 08:21:52

漏洞版本项目

2024-10-31 16:46:36

点赞
收藏

51CTO技术栈公众号