当 LLM 遇上集装箱:我的 Docker 学习笔记与 AI 后端的思考(含反向代理Nginx)

方向:AI 应用开发后端 写作日期:2026-08-18

一、缘起:为什么一个想做 AI 后端的我,要先学 Docker

我给自己定的未来方向是 AI 应用开发后端 。在很多人的想象里,"AI 后端"等于调模型接口、写 prompt、搭 RAG。但真正开始做之后我发现,一个能用的 AI 应用,落到工程层面其实是一堆服务在协作:模型推理服务、向量数据库、对话缓存(Redis)、用户与业务数据(MySQL)、网关与代理......

这些服务各自有严格的环境与版本要求。Python 要 3.10,CUDA 要对应某个版本,Node 要 16,Redis 要 7。装在一个机器上,互相踩版本、互相污染环境,是我最先撞上的墙。

于是我问了自己一个问题:那些大规模生产环境里的 AI 应用,基础设施到底是怎么搭的? 顺着这个问题,我走到了 Docker 面前。

二、第一课:集装箱思维 ------ Docker 到底是什么

学习 Docker 时,最先让我"开窍"的是这个类比:

Docker 就像海运里的万吨巨轮和集装箱。

一艘万吨巨轮,可以同时运送成千上万个集装箱。每个集装箱里装着完全不同的货物------有的装着汽车,有的装着服装,有的装着水果。它们互不干扰,装进船里就能漂洋过海,到达任何一个港口,卸下来就能用。

我们的应用也是这样。过去交付一个软件,是"交一堆代码 + 一堆环境要求文档"。到部署方手里,还要现场配环境、对版本、踩坑。而 Docker 把代码和运行环境一起打包成一个标准化的容器,任何一台装了 Docker 的机器,拉下来就能跑,就像集装箱在任何港口都能吊装一样。

我用一句话把 Docker 的本质记了下来:

ini 复制代码
Agent  = LLM + Harness(tool + mcp + rag + skill + ...)
Docker = 应用 + 运行环境

这行对照是我自己的一个小心得。我在做 AI Agent 时理解了"一个 Agent 不是只有模型,而是模型加上一整套工具、上下文、技能的装载"。同样的思维模型,放在 Docker 身上就通了------一个应用不是只有代码,而是代码加上它依赖的一整套运行环境。打包这个"整体",正是容器化干的事情。

三、我踩过的坑:为什么需要"隔离"

道理是空的,坑是实的。让我真正想做这件事的,是一个身边真实的场景:

你到公司接手一个 n 年前写的 Vue2 项目,要求 Node16 + npm 8。而你的电脑装的是 Node 22,代码一跑就报错,跑不起来。

这不是罕见情况,而是后端日常。Java 有 JDK 版本之争,Python 有 2/3 之争,Node 有版本飞速迭代,更别提 C 系的依赖地狱。每一个版本差异,都是一次环境冲突;每一次环境冲突,都是一次无效加班。

容器化技术把各个依赖隔离化安装:每个项目一个容器,各装各的 Node 版本、各装各的依赖,互不打扰。你不需要在自己的机器上为了一个老项目把 Node 卸了重装------就像一辆万吨巨轮不会因为其中一个集装箱里的水果需要冷藏,就把整艘船都改造成冷库。

这个"隔离"的思想,对我后面理解 AI 后端的服务治理特别重要:模型服务、向量库、业务库,本质上是各自独立的集装箱,跑在各自的容器里,通过端口和网络互相协作。

四、核心概念:镜像与容器

理解了"集装箱"这个心智模型,Docker 里最重要的两个概念就顺了:

  • 镜像(Image) :一个打包好的、只读的模板 ,包含应用和环境。我把它类比成 git pull------从远程仓库拉一份代码。Docker 则是从镜像仓库 pull 一个镜像。
  • 容器(Container) :镜像运行起来的实例 。我把它类比成一张 DVD------镜像像母盘,可以复制出很多张,每一张运行起来就是一个独立的容器;或者说,镜像像一张光盘模板,run 一次就烧录出一个能播放的"播放器"。
bash 复制代码
# 拉取镜像(类比:git pull)
docker pull nginx

# 运行镜像,成为可运行的容器
docker run --name my-nginx-demo -d nginx

# 停掉所有容器 / 删除所有容器 / 删除镜像
docker stop $(docker ps -q)
docker rm   $(docker ps -aq)
docker rmi  <镜像名>

还有一个一开始困扰我的点:端口

我们访问网站时输入 www.juejin.cn:3000,域名后跟的 :3000 就是端口。默认的 :80 是 HTTP 的默认端口,所以访问 www.example.com 其实访问的是 www.example.com:80,只是浏览器帮我们隐藏了。

Docker 里容器是隔离的,外部访问不进来,所以要端口映射:把宿主机(我们这台机器)的一个端口,映射到容器内部的端口。比如:

bash 复制代码
docker run --name my-nginx-demo -p 80:80 -d nginx
#          ↑ 容器的名字     ↑ 本机80端口:容器80端口

-p 80:80 表示"本机的 80 端口 对应 容器内部的 80 端口"。用户浏览器输入 http://localhost:80,请求被转发映射进容器的 80。

五、动手实践:用 nginx 反向代理部署一个 Node 服务

理论讲再多,不如跑一遍。我照着笔记做了一个最简单但完整的实践:一个 Node 服务 + nginx 反向代理

先写一个最朴素的 Node 服务,监听 1314 端口,返回 "hello world":

js 复制代码
// demo/index.js
const http = require('http');
const server = http.createServer((req, res) => {
  res.end("hello world");
});
server.listen(1314, '0.0.0.0', () => {
  console.log('node server run on 1314');
});

demo/conf.d/nginx.conf 里配置 nginx 反向代理,把 80 端口的请求转发给 1314 端口的 Node 服务:

nginx 复制代码
# demo/conf.d/nginx.conf
server {
    listen 80;
    location / {
        proxy_pass http://host.docker.internal:1314;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
    }
}

然后启动 nginx 容器,把本机配置挂载进去:

powershell 复制代码
docker run `
 --name my-nginx-demo `
 -p 80:80 `
 -v D:\workspace\sw_ai\backend\docker\demo\conf.d:/etc/nginx/conf.d `
 -d nginx

这条命令拆开看:

参数 作用
--name my-nginx-demo 给容器起名
-p 80:80 本机 80 端口 映射 容器 80 端口
-v 本机目录:容器目录 把本机的 nginx 配置文件挂载进容器,改配置不用重新打包镜像
-d nginx 以后台方式运行 nginx 镜像

跑起来后,完整的请求链路是:

csharp 复制代码
用户浏览器(chrome)
   → localhost:80(正向代理出网)
   → docker -p 端口映射 → 容器内部 :80
   → nginx 收到 80 端口的访问
   → 按配置文件反代到 :1314(host.docker.internal 指向宿主机)
   → Node 服务返回 "hello world"

六、反身思考:反向代理到底意味着什么

这个 demo 看起来简单,但它让我想明白了一件后端的关键事:反向代理。

用户访问 localhost:80,浏览器(正向代理)帮我们出网;而 nginx 在 80 端口"替后端服务器接收请求"------用户根本不知道后端真正跑在哪个端口、哪台机器上。这个动作叫反向代理。

它的意义远不止"转发":

  1. 隐藏后端集群:真实的后端服务躲在内网,外面只看到一个 80 端口,安全得多。
  2. 高并发承接 :nginx 能扛很高的并发,把请求按规则分摊给后面多个后端实例,这就是负载均衡的雏形。
  3. 可扩展:后端想加一台、减一台机器,前端完全无感。

运维知识:服务器软件把所有在 80 端口的请求,代理给 3000(或 1314)端口。

这个"外面一个口,里面一群服务"的形态,正是所有现代后端(包括 AI 后端)的标准姿势。

七、Docker 在我 AI 后端路线图里的位置

这是这篇博客我最想讲的部分。学 Docker 不是单纯补一门运维知识,而是我发现 AI 应用后端的整个基础设施,几乎都能用这套"集装箱"思维来理解

1. 模型服务化:LLM 本身就是一个容器

生产环境里,你几乎不会在代码里直接 import 一个千亿参数模型。通常是把模型推理封装成一个独立的模型服务(比如一个跑着 vLLM / Ollama 的容器),对外暴露 HTTP 接口,业务后端去调用它。这跟上面 Node 服务 + nginx 的模型一模一样------模型服务就是一个躲在代理后面的 1314。

2. MCP / Agent 工具链:每个工具都可以容器化

我理解的 Agent 是 LLM + Harness(tool + mcp + rag + skill...)。这些 tool、MCP server,本质上是独立的服务。把它们各自容器化,就能独立升级、独立扩容、独立部署------今天升级某个工具,不影响主服务,就像船上一个集装箱的货物损坏,不影响其他集装箱。

3. RAG 基础设施:Redis + MySQL + 向量库

一个 RAG 应用背后挂着缓存(Redis)、业务数据(MySQL)、向量数据库。我在笔记里用 Docker 装 mysql 时第一次体会到:

bash 复制代码
docker exec -it mysql-demo /bin/bash   # 进入容器
mysql -uroot -p123456                   # 连上 mysql
create database blog;                    # 建库

这些"数据库服务"完全不需要在我自己的电脑上装任何东西------拉个镜像、起个容器就完事。我笔记本上干干净净,却能同时跑 MySQL、Redis、Postgres 好多个版本。这就是隔离的价值。

4. 环境一致性的终极方案

AI 领域的环境地狱比普通后端更夸张:CUDA 版本、Python 版本、推理框架(PyTorch / vLLM / llama.cpp)......每个人的机器都不一样,同一个 prompt 在不同环境可能跑出不同结果。Docker 把整个运行环境(包括 GPU 驱动依赖、CUDA 版本)锁进镜像,开发和生产的每一步都在同一个"集装箱"里,从根上消灭"在我电脑上是好的"。

八、下一步计划

学完 Docker 基础,我的路线图是这样的:

  1. 补全 Docker 实践 :用 docker-compose.yml 一次性编排 Node + Redis + MySQL + 一个模型服务,搭出"类生产"的本地 AI 后端。
  2. 写一个真正的 AI 应用后端:基于 NodeJS(我的主力后端框架)实现一个带 RAG 的服务,把模型服务、向量库、Redis 缓存都容器化跑起来。
  3. 深入 MCP 与 Agent 服务化:把自研的工具封装成 MCP server,用 Docker 部署,体验"可插拔工具链"的后端形态。
  4. 理解 GPU 容器与生产部署:研究模型服务在带 GPU 的容器里怎么跑、怎么扩容,为将来上生产做准备。

九、结语

回过头看,Docker 教给我的第一课不是某个命令,而是一种思维:把一个复杂系统拆成一堆互不干扰、又能协作的"集装箱"。

这个思维模型,恰好和我做 AI Agent 时理解的东西同构------Agent 是 LLM + Harness,Docker 是 应用 + 环境,都是"核心 + 配套装载"的整体打包。而 AI 应用后端,说到底就是把这些集装箱合理编排、让它们协作运转。

从一杯咖啡的功夫写下一个返回 hello world 的 Node 服务,到把 nginx 反代、mysql、redis 一个个容器化跑起来------路还很长,但方向越来越清晰了。

我们搬进集装箱的,不只是代码,还有未来每一个 AI 应用赖以生存的基础设施。

相关推荐
ZzzZZzzzZZZzzzz…5 分钟前
K8s---网络:从 Pod 网络模型到 Calico 三种模式
运维·网络·云原生·容器·kubernetes·calico·pod网络模型
mldong2 小时前
Go 开发者也有自己的轻量工作流引擎了:go get 一行,5 分钟跑通一条审批流
后端·go
BingoGo8 小时前
PHP clone 之后,为什么改副本会影响原对象?
后端·php
JaguarJack8 小时前
PHP clone 之后,为什么改副本会影响原对象?
后端·php·服务端
小灰灰搞电子9 小时前
Rust+Slint 实现动态消息提示框源码分享
开发语言·后端·rust
小奏技术9 小时前
10 MB 的 Postman 替代品,启动不到 1 秒
后端
东风破_9 小时前
Text2SQL :用自然语言操作 SQLite 数据库
人工智能·后端
xhaxy10 小时前
docker
docker·容器·eureka
一技安身12 小时前
【信创】Docker‑Compose V2 两种离线部署(独立模式、插件模式)简易教程
java·docker·eureka
IT_陈寒13 小时前
Python的多线程就是个假把式,我算是体验到了
前端·人工智能·后端