LingBot-Vision 用 Docker 封装推理环境的配置方法

文章导读
LingBot-Vision 的推理环境通常依赖特定版本的 CUDA、Python 包和模型文件,直接在不同机器上部署时容易因为基础环境不一致而失败。用 Docker 封装推理环境,可以先把代码和依赖固定在镜像里,把模型文件放在宿主机的目录通过挂载方式暴露给容器,这样镜像本身不携带模型,也能在不同机器上复用。
📋 目录
  1. 确定基础镜像与依赖拷贝清单
  2. 编写Dockerfile并安装Python依赖
  3. 模型文件挂载与动态加载方式
  4. 启动容器并测试推理接口
  5. 容器显存限制与多用户隔离
A A

LingBot-Vision 的推理环境通常依赖特定版本的 CUDA、Python 包和模型文件,直接在不同机器上部署时容易因为基础环境不一致而失败。用 Docker 封装推理环境,可以先把代码和依赖固定在镜像里,把模型文件放在宿主机的目录通过挂载方式暴露给容器,这样镜像本身不携带模型,也能在不同机器上复用。

适合用 CUDA 基础镜像搭配 Python3-pip 安装依赖;Dockerfile 只包含代码和依赖清单,模型文件通过 -v 挂载并用 MODEL_PATH 环境变量读取;启动时需指定 GPU 和端口,用 NVIDIA_VISIBLE_DEVICES 限制可见 GPU,用 `--shm-size` 调整共享内存。验证方式是执行 curl 请求并查看容器日志。

确定基础镜像与依赖拷贝清单

基础镜像决定了容器内的 CUDA 驱动兼容层和运行库,最好直接使用 NVIDIA 官方提供的 CUDA 运行基础镜像,避免自己装配出缺东少西的环境。例如:

FROM nvidia/cuda:12.2.0-base-classic

这个标签 12.2.0 可以按宿主机 NVIDIA 驱动支持的版本替换为 11.8.0 等;如果宿主机驱动较老,就需要选择对应的 CUDA 版本镜像,否则容器内推理时会报 CUDA driver 版本不匹配。

确定基础镜像后,要把 LingBot-Vision 推理项目中的代码、依赖清单和运行配置拷贝进镜像,但不要把模型文件拷贝进来。通常需要 COPY 的文件有:

  • 推理入口脚本,例如 inference.py
  • 依赖清单 requirements.txt
  • 模型加载逻辑或配置文件 config.yaml

这些文件缺省情况下不会被包含进镜像,需要在 Dockerfile 里逐一 COPY 到工作目录。

LingBot-Vision 用 Docker 封装推理环境的配置方法

编写Dockerfile并安装Python依赖

Dockerfile 的写法并不复杂,关键是把 Python 运行环境和依赖一次性安装好。因为基础镜像不包含 pip,所以要先用 apt-get 安装 python3-pip,再拷贝 requirements.txt 并执行 pip install。以下是一个可用的 Dockerfile 示例:

FROM nvidia/cuda:12.2.0-base-classic

RUN apt-get update && apt-get install -y `--no-install-recommends` python3 python3-pip curl

WORKDIR /app

COPY requirements.txt .

RUN pip install `--no-cache-dir` -r requirements.txt

COPY inference.py .
COPY config.yaml .

CMD ["python3", "inference.py"]

这里的 `--no-cache-dir` 让 pip 不保留缓存,镜像体积更小。curl 不是必须的,但后续测试接口时会在容器内用到,也可以先不装。

requirements.txt 中需要包含 LingBot-Vision 推理时实际用到的 Python 包,比如 torch、torchvision、Pillow、fastapi 等,具体内容根据项目需求维护。如果还有系统级依赖,比如 libgl1,也要在 apt-get 阶段补充。

模型文件挂载与动态加载方式

模型文件通常比较大,如果打进镜像会导致镜像臃肿且每次模型更新都得重新构建。更合理的做法是在启动容器时通过 -v 参数把宿主机里的模型目录挂载到容器内的固定路径,然后在代码中通过环境变量获取这个路径。例如:

docker run -v /host/model:/models -e MODEL_PATH=/models ...

在 inference.py 里,可以用 os.environ.get("MODEL_PATH") 读取模型路径,再传入模型加载函数。这样镜像本身不依赖模型文件,任何机器上只要有这份镜像和模型目录就能运行。

LingBot-Vision 用 Docker 封装推理环境的配置方法
import os
model_path = os.environ.get('MODEL_PATH', '/models')
model = load_lingbot_model(model_path)

这样做的边界是:宿主机上的模型目录必须真实存在且包含所需的权重文件;同时容器内需要能读取该目录的权限,否则启动时会因找不到模型而异常退出。

启动容器并测试推理接口

启动容器时需要显式指定 GPU 资源,并把模型目录和端口映射进去。假设推理服务在容器内监听 8000 端口,用如下命令启动:

docker run -d `--gpus` all -p 8000:8000 \
  -v /host/model:/models \
  -e MODEL_PATH=/models \
  lingbot-vision

启动后,首先要确认容器日志中没有 CUDA 初始化或模型加载的报错,可以用 docker logs <container_id> 观察。

随后调用推理接口,假设服务暴露了 /predict 端点,可以这样测试:

LingBot-Vision 用 Docker 封装推理环境的配置方法
curl -X POST http://localhost:8000/predict \
  -H 'Content-Type: application/json' \
  -d '{"image_url": "http://example.com/test.jpg"}'

如果返回结果中包含识别结果,说明接口正常;如果长时间无响应,需要结合日志判断是模型未加载还是网络超时。

容器显存限制与多用户隔离

当多个用户或任务共用同一台宿主机的 GPU 时,需要明确限制每个容器可用的 GPU 设备,避免一个容器抢占全部显存。可以通过环境变量 NVIDIA_VISIBLE_DEVICES 指定容器只能看到某一张卡,例如:

docker run `--gpus` all -e NVIDIA_VISIBLE_DEVICES=0 ...

在共享一个 GPU 的情况下,也可以用 `--shm-size` 调整共享内存大小,防止 PyTorch 等框架因共享内存不足而崩溃。比如分配 8GB 共享内存:

docker run `--shm-size`=8g ...

调度多个容器共用一个 GPU 时,建议先用 nvidia-smi 查看当前显存占用,再决定是否增加新的容器。如果显存已经接近上限,就不要再启动新的推理容器,否则会因显存不足触发 OOM。所有容器的 GPU 编号通过 NVIDIA_VISIBLE_DEVICES 显式指定,不指定的话所有容器都会看到全部 GPU,容易互相干扰。