摘要:用了 Docker,好处挺多的,可是有一个不大不小的问题,它会一不当心占用太多磁盘,这就意味着咱们必须及时清理。nginx
做为一个有信仰的技术公司,咱们Fundebug的后台采用了酷炫的全 Docker 化架构,全部服务,包括数据库都运行在 Docker 里面。这样作固然不是为了炫技,看得清楚的好处仍是很多的:git
至少,上线这一年多来,Docker 一直很是稳定,没有出什么问题。可是,它有一个不大不小的问题,会比较消耗磁盘空间。github
若是 Docker 一不当心把磁盘空间全占满了,你的服务也就算玩完了,所以全部 Docker 用户都须要对此保持警戒。固然,你们也没关系张,这个问题仍是挺好解决的。docker
在谁用光了磁盘?Docker System 命令详解中,咱们详细介绍了docker system命令,它能够用于管理磁盘空间。数据库
docker system df命令,相似于 Linux 上的df命令,用于查看 Docker 的磁盘使用状况:json
docker system df TYPE TOTAL ACTIVE SIZE RECLAIMABLE Images 147 36 7.204GB 3.887GB (53%) Containers 37 10 104.8MB 102.6MB (97%) Local Volumes 3 3 1.421GB 0B (0%) Build Cache 0B 0B
可知,Docker 镜像占用了7.2GB磁盘,Docker 容器占用了104.8MB磁盘,Docker 数据卷占用了1.4GB磁盘。小程序
docker system prune命令能够用于清理磁盘,删除关闭的容器、无用的数据卷和网络,以及 dangling 镜像(即无 tag 的镜像)。docker system prune -a命令清理得更加完全,能够将没有容器使用 Docker 镜像都删掉。注意,这两个命令会把你暂时关闭的容器,以及暂时没有用到的 Docker 镜像都删掉了...因此使用以前必定要想清楚吶。微信小程序
执行docker system prune -a命令以后,Docker 占用的磁盘空间减小了不少:bash
docker system df TYPE TOTAL ACTIVE SIZE RECLAIMABLE Images 10 10 2.271GB 630.7MB (27%) Containers 10 10 2.211MB 0B (0%) Local Volumes 3 3 1.421GB 0B (0%) Build Cache 0B 0B
对于旧版的 Docker(版本 1.13 以前),是没有 docker system 命令的,所以须要进行手动清理。这里给出几个经常使用的命 删除全部关闭的容器服务器
docker ps -a | grep Exit | cut -d ' ' -f 1 | xargs docker rm
删除全部 dangling 镜像(即无 tag 的镜像):
docker rmi $(docker images | grep "^<none>" | awk "{print $3}")
删除全部 dangling 数据卷(即无用的 volume):
docker volume rm $(docker volume ls -qf dangling=true)
Fundebug提供实时、专业的错误监控服务,为您的线上代码保驾护航,欢迎你们无偿使用!
有一次,当我使用 1 与 2 提到的方法清理磁盘以后,发现并无什么做用,因而,我进行了一系列分析。
在 Ubuntu 上,Docker 的全部相关文件,包括镜像、容器等都保存在**/var/lib/docker/**目录中:
du -hs /var/lib/docker/ 97G /var/lib/docker/
Docker 居然使用了将近100GB磁盘,这也是够了。使用du命令继续查看,能够定位到真正占用这么多磁盘的目录:
92G /var/lib/docker/containers/a376aa694b22ee497f6fc9f7d15d943de91c853284f8f105ff5ad6c7ddae7a53
由docker ps可知,nginx 容器的 ID 刚好为a376aa694b22,与上面的目录**/var/lib/docker/containers/a376aa694b22**的前缀一致:
docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES a376aa694b22 192.168.59.224:5000/nginx:1.12.1 "nginx -g 'daemon off" 9 weeks ago Up 10 minutes nginx
所以,nginx 容器居然占用了92GB的磁盘。进一步分析可知,真正占用磁盘空间的是 nginx 的日志文件。那么这就不难理解了。咱们Fundebug天天的数据请求为百万级别,那么日志数据天然很是大。
使用truncate命令,能够将 nginx 容器的日志文件“清零”:
truncate -s 0 /var/lib/docker/containers/a376aa694b22ee497f6fc9f7d15d943de91c853284f8f105ff5ad6c7ddae7a53/*-json.log
固然,这个命令只是临时有做用,日志文件早晚又会涨回来。要从根本上解决问题,须要限制 nginx 容器的日志文件大小。这个能够经过配置日志的max-size来实现,下面是 nginx 容器的 docker-compose 配置文件:
nginx: image: nginx:1.12.1 restart: always logging: driver: "json-file" options: max-size: "5g"
重启 nginx 容器以后,其日志文件的大小就被限制在5GB,不再用担忧了~
还有一次,当我清理了镜像、容器以及数据卷以后,发现磁盘空间并无减小。根据Docker disk usage提到过的建议,我重启了 Docker,发现磁盘使用率从 83%降到了 19%。根据高手指点,这应该是与内核 3.13 相关的 BUG,致使 Docker 没法清理一些无用目录:
it's quite likely that for some reason when those container shutdown, docker couldn't remove the directory because the shm device was busy. This tends to happen often on 3.13 kernel. You may want to update it to the 4.4 version supported on trusty 14.04.5 LTS.
The reason it disappeared after a restart, is that daemon probably tried and succeeded to clean up left over data from stopped containers.
我查看了一下内核版本,发现真的是 3.13:
uname -r 3.13.0-86-generic
若是你的内核版本也是 3.13,并且清理磁盘没能成功,不妨重启一下 Docker。固然,这个晚上操做比较靠谱。
Fundebug专一于JavaScript、微信小程序、微信小游戏、支付宝小程序、React Native、Node.js和Java线上应用实时BUG监控。 自从2016年双十一正式上线,Fundebug累计处理了10亿+错误事件,付费客户有Google、360、金山软件、百姓网等众多品牌企业。欢迎你们免费试用!
转载时请注明做者Fundebug以及本文地址: https://blog.fundebug.com/2018/01/10/how-to-clean-docker-disk/