<返回目录 Powered by claude/xia兄
第12课: 资源限制
为什么需要资源限制?
- 防止单个容器占用过多资源影响其他容器
- 提高系统稳定性和可预测性
- 合理分配资源,提高资源利用率
- 防止内存泄漏导致系统崩溃
内存限制
# 限制容器最大内存为512MB
docker run -d --memory="512m" nginx
# 限制内存和swap总量
docker run -d --memory="512m" --memory-swap="1g" nginx
# 禁用swap
docker run -d --memory="512m" --memory-swap="512m" nginx
# 内存预留(软限制)
docker run -d --memory="1g" --memory-reservation="512m" nginx
# OOM时不杀死容器(不推荐)
docker run -d --memory="512m" --oom-kill-disable nginx
内存单位:
- b, k, m, g:字节、KB、MB、GB
- 示例:512m = 512MB,2g = 2GB
CPU限制
# 限制CPU份额(相对权重,默认1024)
docker run -d --cpu-shares=512 nginx
# 限制使用的CPU核心数
docker run -d --cpus="1.5" nginx
# 指定使用哪些CPU核心
docker run -d --cpuset-cpus="0,1" nginx
docker run -d --cpuset-cpus="0-3" nginx
# CPU配额(100000为100%)
docker run -d --cpu-period=100000 --cpu-quota=50000 nginx # 限制50% CPU
磁盘IO限制
# 限制读写速率(字节/秒)
docker run -d \
--device-read-bps /dev/sda:10mb \
--device-write-bps /dev/sda:10mb \
nginx
# 限制读写IOPS
docker run -d \
--device-read-iops /dev/sda:1000 \
--device-write-iops /dev/sda:1000 \
nginx
# 限制块IO权重(10-1000,默认500)
docker run -d --blkio-weight 300 nginx
查看资源使用情况
# 实时查看所有容器资源使用
docker stats
# 查看特定容器
docker stats mycontainer
# 不持续刷新,只显示一次
docker stats --no-stream
# 格式化输出
docker stats --format "table {{.Container}}\t{{.CPUPerc}}\t{{.MemUsage}}"
# 查看容器详细信息
docker inspect mycontainer | grep -A 10 "Memory"
Docker Compose资源限制
version: '3.8'
services:
web:
image: nginx
deploy:
resources:
limits:
cpus: '0.5'
memory: 512M
reservations:
cpus: '0.25'
memory: 256M
db:
image: mysql
deploy:
resources:
limits:
cpus: '2'
memory: 2G
reservations:
cpus: '1'
memory: 1G
environment:
MYSQL_ROOT_PASSWORD: secret
实战示例 - Web应用资源配置
# Nginx前端服务器(轻量级)
docker run -d \
--name nginx \
--memory="256m" \
--memory-reservation="128m" \
--cpus="0.5" \
-p 80:80 \
nginx:alpine
# Python应用服务器(中等)
docker run -d \
--name webapp \
--memory="1g" \
--memory-reservation="512m" \
--cpus="1" \
myapp:latest
# MySQL数据库(重量级)
docker run -d \
--name mysql \
--memory="2g" \
--memory-reservation="1g" \
--cpus="2" \
-e MYSQL_ROOT_PASSWORD=secret \
mysql:8.0
# Redis缓存(轻量级)
docker run -d \
--name redis \
--memory="512m" \
--cpus="0.5" \
redis:alpine
PID限制
# 限制容器可创建的进程数
docker run -d --pids-limit=100 nginx
# 查看容器进程数
docker exec mycontainer ps aux | wc -l
网络带宽限制
# Docker本身不直接支持网络带宽限制
# 需要使用tc(traffic control)工具
# 在主机上限制容器网络
# 获取容器网络接口
docker exec mycontainer cat /sys/class/net/eth0/iflink
# 使用tc限制带宽
tc qdisc add dev veth123456 root tbf rate 1mbit burst 32kbit latency 400ms
资源监控和告警
# 使用cAdvisor监控容器
docker run -d \
--name=cadvisor \
--volume=/:/rootfs:ro \
--volume=/var/run:/var/run:ro \
--volume=/sys:/sys:ro \
--volume=/var/lib/docker/:/var/lib/docker:ro \
--publish=8080:8080 \
google/cadvisor:latest
# 访问 http://localhost:8080 查看监控数据
完整监控方案
version: '3.8'
services:
# 应用容器
app:
image: myapp
deploy:
resources:
limits:
cpus: '1'
memory: 1G
# Prometheus监控
prometheus:
image: prom/prometheus
volumes:
- ./prometheus.yml:/etc/prometheus/prometheus.yml
ports:
- "9090:9090"
# cAdvisor收集容器指标
cadvisor:
image: google/cadvisor
volumes:
- /:/rootfs:ro
- /var/run:/var/run:ro
- /sys:/sys:ro
- /var/lib/docker/:/var/lib/docker:ro
ports:
- "8080:8080"
# Grafana可视化
grafana:
image: grafana/grafana
ports:
- "3000:3000"
environment:
- GF_SECURITY_ADMIN_PASSWORD=admin
压力测试
# 使用stress工具测试资源限制
docker run -it --rm \
--memory="512m" \
--cpus="1" \
progrium/stress \
--cpu 2 --io 1 --vm 2 --vm-bytes 256M --timeout 30s
# 观察容器被OOM杀死
docker run -it --rm \
--memory="100m" \
progrium/stress \
--vm 1 --vm-bytes 200M
动态调整资源限制
# 更新运行中容器的资源限制
docker update --memory="1g" --cpus="2" mycontainer
# 批量更新
docker update --memory="512m" $(docker ps -q)
# 查看更新后的配置
docker inspect mycontainer | grep -A 5 "Memory"
资源配额最佳实践
- 根据应用实际需求设置资源限制
- 设置memory-reservation作为软限制
- 为关键服务预留足够资源
- 使用监控工具观察资源使用趋势
- 定期压力测试验证资源配置
- 为数据库等有状态服务分配更多资源
- 使用CPU shares而不是硬限制提高灵活性
常见问题排查
# 容器被OOM杀死
docker inspect mycontainer | grep OOMKilled
# 查看容器退出原因
docker inspect mycontainer | grep -A 5 "State"
# 查看系统日志
dmesg | grep -i oom
journalctl -u docker | grep -i oom
# 查看容器资源限制
docker inspect mycontainer | grep -A 20 "HostConfig"
推荐资源配置
# 小型Web应用
--memory="256m" --cpus="0.5"
# 中型应用服务器
--memory="1g" --cpus="1"
# 数据库服务
--memory="2g" --cpus="2"
# 大数据处理
--memory="4g" --cpus="4"
# 开发环境
--memory="512m" --cpus="1"
实践练习
- 启动一个限制512MB内存的容器,观察资源使用
- 使用stress工具测试内存限制,观察OOM行为
- 配置Docker Compose为不同服务设置资源限制
- 使用docker stats实时监控容器资源使用
- 搭建Prometheus+Grafana监控系统
- 动态调整运行中容器的资源限制