朕喜技术(ZhenxiJS)
2026.09.04
1 分钟阅读
Docker 容器 /dev/shm(共享内存 tmpfs) 默认 64M 被写满:No space left on device 解决
标签:Docker / docker compose / /dev/shm / tmpfs / 共享内存 / shm_size / No space left on device / ENOSPC / 容器共享内存太小 / OSError 28
问题背景
后端/数据工程师在容器里跑批处理任务:worker.py 要把 128MB 中间结果分块写入
/dev/shm/payload.dat(Linux 的共享内存 tmpfs,读写走内存、极快,多进程共享暂存常用)。
宿主机上跑得好好的,一进 Docker 容器就报:
OSError(28, 'No space left on device')
shm 64M 64M 0 100% /dev/shm
即写满 64MB 就 ENOSPC,与磁盘 df -h / 是否还有空间无关。
复现步骤
cd scenario/2026-09-04-1600
docker compose up -d --build
docker compose exec app df -h /dev/shm # 默认 64M
docker compose exec app python3 /app/worker.py 128 # 写到 64M 报 No space left on device
根本原因
Docker 容器内 /dev/shm 是独立挂载的 tmpfs,默认容量只有 64MB;
宿主机 /dev/shm 则由系统分配了较大容量(或挂载自 RAM),够用。
数据超过 64MB → tmpfs 被写满 → 返回 ENOSPC(错误码 28)。
常见踩坑服务:Elasticsearch、无头浏览器、PyTorch/多进程 DataLoader、需要大共享临时文件的任务。
解决办法
在 docker-compose.yml 对应 service 下显式调大共享内存容量:
services:
app:
...
shm_size: "1g" # 关键修复
重新构建并重建容器:
docker compose down
docker compose up -d --build
等价命令行(docker run):
docker run --shm-size=1g ...
shm_size 支持 512m、1g、2g 等,按需设置。
验证
修复后:
docker compose exec app df -h /dev/shm # 1.0G
docker compose exec app python3 /app/worker.py 128 # OK: 已成功暂存 128MB 到共享内存
输出不再报错,任务正常完成(退出码 0)。
经验与避坑
- 改了 compose 要 down + up 重建,别只
restart,新挂载/配额才能生效。 /dev/shm满不代表磁盘满:排查必须df -h /dev/shm单独看共享内存。- tmpfs 不持久化:重启后内容清空,只适合做临时/共享暂存。
- 用完记得清理(本案例
worker.py在finally删除payload.dat),避免占用共享内存。 - 若用 Kubernetes:可通过 pod 的
emptyDir+medium: Memory或调sizeLimit对应扩容。
