docker水位过高,清理怕出问题?,不知道清理什么?怕删错了?进入实践
第一步准备测试数据
- 创建 悬空的镜像(即REPOSITORY和TAG均为的镜像)
docker pull busybox:musl
docker tag busybox:musl busybox:stable
mkdir -p /tmp/busybox
cd /tmp/busybox
echo 'FROM busybox:stable' > /tmp/busybox/Dockerfile
echo 'RUN touch /tmp/test' >> /tmp/busybox/Dockerfile
docker build -t busybox:test /tmp/busybox
docker pull busybox:stable
docker build -t busybox:test /tmp/busybox
docker images -f "dangling=true"
- 创建 正常的容器 并写入1G文件
docker run -d --rm --name busybox busybox:test /bin/sh -c "/bin/sleep 3600"
docker exec -it busybox /bin/sh -c 'dd if=/dev/zero of=./test.zip count=1024 bs=1M'
docker system df | grep Containers
- 创建 已停止 的容器(即docker ps -a中STATUS为Exited的容器)
docker run -d --name busybox2 busybox:test /bin/sh -c "/bin/sleep 1"
docker ps -a | grep Exited
- 创建 已暂停 的容器(即docker ps -a中STATUS为Paused的容器
docker run -d --rm --name busybox3 busybox:test /bin/sh -c "/bin/sleep 3600"
docker pause busybox3
docker ps -a | grep Paused
- 创建 孤儿卷(即未被使用的卷)
docker volume create volume-test1
docker volume ls -f dangling=true
确认过程
1.docker info 确认 docker root 路径
- docker info 查看 docker root 路径
docker info | grep Root
2.docker system df 分析资源使用
- docker system df:查看所有镜像/容器/数据卷等资源使用的统计信息
docker system df 列出了 docker 使用磁盘的 4 种类型:
类型 | 描述 |
---|---|
Images | 所有镜像占用的空间(包括拉取的镜像、本地构建的镜像) |
Containers | 运行中的容器所占用的空间(没运行就不占空间) |
Local Volumes | 本地数据卷的空间 |
Build Cache | 镜像构建过程产生的缓存数据 |
- docker system df -v:查看所有镜像/容器/数据卷等资源使用的详细信息
docker system df -v
注:docker system df -v 看到的容器大小,有可能比实际的小很多。比如 df -v 看到某容器大小43G,但该容器对应的 overlay2/xxx/diff 和 merge 加一起却有82G。
docker inspect 分析 overlay2 使用
- 查看指定容器(比如 busybox)的 overlay2 目录
docker inspect busybox | grep overlay2
docker volume 查看 volume 使用
- 查看volume
查看容器日志的大小
- 查看docker所有容器日志(*-json.log)
find /var/lib/docker/containers/ -name *-json.log
- 查看超过100MB的文件
find /var/lib/docker -type f -size +100M -print0 | xargs -0 du -h | sort -nr
查看 /var/lib/docker/overlay2
- 查询 overlay2 占用磁盘空间较多(比如达到G或T以上)的目录
du -sh /var/lib/docker/overlay2/* | grep [GT] | sort -nr
- 找到使用较多的 overlay2 子目录,结合 docker inspect 反向定位到哪个容器在用
docker ps -q | xargs docker inspect --format '{{.State.Pid}}, {{.Name}}, {{.GraphDriver.Data.WorkDir}}' | grep xxx
- 进入容器(比如 busybox),找到占用磁盘较多的目录,清理就完了。
手动清理环节
清理容器日志
- 重置较大的容器日志(*-json.log)
1.find /var/lib/docker/containers/ -name *-json.log
2.# bash -c "echo > /var/lib/docker/containers/xxx-json.log"
- 删除较大(超过100MB)的容器日志
find /var/lib/docker -type f -size +100M -print0 | xargs -0 du -h | sort -nr
# rm -f xxx
停止 container
- 停止 已暂停 的容器(注:请确认已暂停的容器不在使用,否则后面会误删)
- 停止 特定|所有 的容器
docker stop $(docker ps -a | egrep "(mysql|zabbix)" | awk '{print $1}')
#docker stop $(docker ps -a -q)
删除 container
- 删除 已停止 的容器
删除 特定|所有 的容器
# docker rm $(docker ps -a | egrep "(mysql|zabbix)" | awk '{print $1}')
# docker rm $(docker ps -a -q)
删除 images
- 删除 悬空 的镜像(即REPOSITORY和TAG 均为的镜像)
注1:若REPOSITORY正常、TAG为,只是说明该镜像没有正常打标签,不可轻易删除。
注2:如果正在运行的容器使用了悬空镜像 ,那么删除此镜像就会报错:Error response from daemon: conflict: unable to delete 77bb919cd617 (cannot be forced) - image is being used by running container 48c2f4b4f4af。 若确认依赖的容器已不在使用,停掉此容器再次删除悬空镜像就不会报错了。
docker rmi $(docker images | grep "^<none>" | awk '{print $3}')
docker rmi $(docker images -qf dangling=true)
- 删除 特定 的容器
删除 volume
- 删除 孤儿卷(即无用的volume)
- 清理volume
docker volume prune
删除 network
- 删除网络,网络一般不占用磁盘空间,可以不用删除
推荐 docker system prune
- docker system prune:会删除已停止的容器、无用的网络、悬空镜像、悬空镜像的构建缓存
注1:不会删除已暂停的容器、没有关联容器的镜像等
docker images -qf dangling=true #.悬空的镜像
docker ps -a | grep Exited #.已关闭的容器
docker system prune
- docker system prune -a:清理的更加彻底,会删除没有容器使用的镜像
docker system prune -a
最佳实践
使用参数限制容器大小
- 比如,在创建容器的时候使用参数 –storage-opt size=100G 来设定容器的硬盘大小为100G
docker pull nginx:latest
docker run -itd --name nginx1 -p 8001:80 nginx:latest /bin/bash
docker exec -it nginx1 /bin/bash -c 'df -Th | grep overlay'
docker run -itd --name nginx2 -p 8002:80 --memory=2G --storage-opt size=100G nginx:latest /bin/bash
docker exec -it nginx2 /bin/bash -c 'df -Th | grep overlay'
修改默认的docker路径
- 修改docker默认存放镜像/容器/数据卷的路径,比如:/data/docker
mkdir -p /data/docker
systemctl stop docker
rsync -avz /var/lib/docker/ /data/docker
mv /var/lib/docker /var/lib/docker.bak
echo '{"data-root":"/data/docker"}' > /etc/docker/daemon.json
systemctl restart docker
docker info | grep Root
#.执行 docker info 若返回 Docker Root Dir: /data/docker 则表示docker根目录修改成功
创建自动清理任务
- 容器日志随时间推移会继续积累,可以创建一个定期清理的任务,脚本参考如下:clean_docker_log.sh
#!/bin/bash
logs=$(find /var/lib/docker/containers/ -name *-json.log)
for log in $logs
do
cat /dev/null > $log
done