Crawl4AI Docker 部署实战:镜像拉取、源码构建、Compose 编排与 Dockerfile 实现解析
本文基于仓库中 docs/deprecated/docker-deployment.md 这篇 Docker 部署文档展开:它完整继承了原文档的三种部署方式(Docker Hub 镜像、仓库源码构建、Docker Compose 编排)与一键部署说明,并结合当前仓库的 Dockerfile、docker-compose.yml、deploy/docker/supervisord.conf 与 deploy/docker/server.py 等文件,深入讲解容器内部的工作机制(supervisor 双进程、/health 健康检查、内存与共享内存约束、构建参数分支),帮助你既会"照抄命令",也懂"为什么这样配"。
需要说明适用前提:该文档位于 docs/deprecated/ 目录下,标题标注为 "Legacy",其中记录的 basic-amd64、all-amd64、gpu-arm64 等镜像标签与 compose profile 属于早期版本约定。当前仓库的构建参数已演进(见后文"新旧差异"一节),但文档中的核心思路——按平台选镜像、--shm-size 调参、/health 验收——依然完全适用。
一、部署方式总览
Crawl4AI 以 Docker 镜像形式分发,容器内预装 Python、Playwright Chromium、Redis 与 FastAPI 服务(server:app),启动后在 11235 端口对外提供 HTTP API。原文档给出四条路径:
| 方式 | 适用场景 | 核心命令 |
|---|---|---|
| Option 1:Docker Hub 镜像 | 生产快速上线,无需构建环境 | docker pull + docker run -p 11235:11235 |
| Option 2:从仓库构建 | 需要定制安装类型或调试构建过程 | docker build --build-arg INSTALL_TYPE=... |
| Option 3:Docker Compose | 需要管理环境变量、多配置项的结构化编排 | docker-compose --profile ... up |
| One-Click Deployment | 云端一键托管 | 原文档提供云厂商部署徽章 |
所有方式最终都要通过同一个验收动作确认服务就绪:
curl http://localhost:11235/health
1.1 为什么是 11235 端口
从源码结构看,11235 是容器内 Gunicorn 的监听端口。deploy/docker/supervisord.conf 中以 uvicorn worker 启动 FastAPI 应用:
[program:gunicorn]
command=/usr/local/bin/gunicorn --bind "%(ENV_GUNICORN_BIND)s" \
--workers 1 --threads 4 --timeout 1800 --graceful-timeout 30 \
--keep-alive 300 --log-level info \
--limit-request-line 8190 --limit-request-fields 100 \
--worker-class uvicorn.workers.UvicornWorker server:app
容器内还有第二个由 supervisor 托管的进程——Redis,仅绑定回环地址且带密码([program:redis] 中 --bind 127.0.0.1 ::1 --requirepass),用于缓存与会话支持。这也解释了 Dockerfile 中默认设置的 REDIS_HOST=localhost 环境变量(L22-L23)。因此 -p 11235:11235 只需暴露 API 端口,Redis 端口从不出容器。
1.2 /health 端点返回什么
curl http://localhost:11235/health 之所以是官方验收手段,是因为它在服务端有明确的实现。deploy/docker/server.py:
@app.get(config["observability"]["health_check"]["endpoint"])
async def health():
return {"status": "ok", "timestamp": time.time(), "version": __version__}
端点路径 /health 本身由 deploy/docker/config.yml 的 observability.health_check.endpoint 配置项决定(该文件 L120 即 endpoint: "/health"),而非硬编码路由,运维上可以改配置换端点路径。
二、Option 1:从 Docker Hub 拉取镜像(推荐)
这是原文档标注 "Recommended" 的路径,无需本地构建。选镜像遵循"平台 × 功能档位"两个维度:平台有 amd64 / arm64 / armv7 三类,档位有 basic / all / gpu 三档。
2.1 AMD64(常规 Linux / Windows)
# Basic version (recommended)
docker pull unclecode/crawl4ai:basic-amd64
docker run -p 11235:11235 unclecode/crawl4ai:basic-amd64
# Full ML/LLM support
docker pull unclecode/crawl4ai:all-amd64
docker run -p 11235:11235 unclecode/crawl4ai:all-amd64
# With GPU support
docker pull unclecode/crawl4ai:gpu-amd64
docker run -p 11235:11235 unclecode/crawl4ai:gpu-amd64
三档含义:basic 仅包含基础爬虫能力;all 额外安装完整 ML/LLM 依赖(torch、transformers 等,见 3.2 节构建分支);gpu 在 all 基础上启用 NVIDIA CUDA 工具链。
2.2 ARM64(M1/M2 Mac、ARM 服务器)
# Basic version (recommended)
docker pull unclecode/crawl4ai:basic-arm64
docker run -p 11235:11235 unclecode/crawl4ai:basic-arm64
# Full ML/LLM support
docker pull unclecode/crawl4ai:all-arm64
docker run -p 11235:11235 unclecode/crawl4ai:all-arm64
# With GPU support
docker pull unclecode/crawl4ai:gpu-arm64
docker run -p 11235:11235 unclecode/crawl4ai:gpu-arm64
2.3 共享内存调参:--shm-size
Chromium 内核的无头浏览器依赖 /dev/shm 共享内存,Docker 默认只给 64MB,并发爬取或大页面截图时极易崩溃。原文档给出的调参方式:
docker run --shm-size=2gb -p 11235:11235 unclecode/crawl4ai:basic-amd64
这一点与仓库实践相互印证:deploy/docker/README.md 中所有示例运行命令都带 --shm-size=1g,而 docker-compose.yml 则用 shm_size: "1gb" 声明等价能力(L21)。经验上 1GB 起步、重负载页面提升到 2GB 是稳妥的取值。
2.4 Raspberry Pi(32 位)
# Pull and run basic version (recommended for Raspberry Pi)
docker pull unclecode/crawl4ai:basic-armv7
docker run -p 11235:11235 unclecode/crawl4ai:basic-armv7
# With increased shared memory if needed
docker run --shm-size=2gb -p 11235:11235 unclecode/crawl4ai:basic-armv7
原文档注明该档位标注为 "coming soon",并明确硬件限制下仅推荐 basic 版本。
2.5 验收
curl http://localhost:11235/health
预期返回 {"status": "ok", "timestamp": ..., "version": ...}。
三、Option 2:从仓库构建镜像
需要定制依赖组合或验证本地改动时使用。
3.1 构建命令
# Clone the repository
git clone https://github.com/unclecode/crawl4ai.git
cd crawl4ai
# For AMD64 (Regular Linux/Windows)
docker build --platform linux/amd64 \
--tag crawl4ai:local \
--build-arg INSTALL_TYPE=basic \
.
# For ARM64 (M1/M2 Macs, ARM servers)
docker build --platform linux/arm64 \
--tag crawl4ai:local \
--build-arg INSTALL_TYPE=basic \
.
构建参数(原文档 Build options):
INSTALL_TYPE=basic(默认):基础爬虫功能;INSTALL_TYPE=all:完整 ML/LLM 支持;ENABLE_GPU=true:启用 GPU 支持。
组合示例:
docker build --platform linux/amd64 \
--tag crawl4ai:local \
--build-arg INSTALL_TYPE=all \
--build-arg ENABLE_GPU=true \
.
3.2 构建参数在 Dockerfile 中的真实分支逻辑
对照当前 Dockerfile 源码,可以看到这些 ARG 的实际消费方式(L26-L27 定义 INSTALL_TYPE 与 ENABLE_GPU,默认值分别是 default 与 false):
- GPU 分支(L92-L99):仅当
ENABLE_GPU=true且TARGETARCH=amd64时才安装nvidia-cuda-toolkit,其他平台直接跳过并打印提示。也就是说gpu档位在 ARM 上不会真正装入 CUDA 工具链; - 平台优化(L101-L115):
arm64安装libopenblas-dev,amd64安装libomp-dev,对应不同架构的数值计算后端; - 安装类型分支(L146-L168):
INSTALL_TYPE=all时先装 torch/torchvision/torchaudio/scikit-learn/nltk/transformers/tokenizers 并下载 NLTK 语料,再pip install "/tmp/project/[all]"触发模型加载器python -m crawl4ai.model_loader;torch与transformer两个中间档位分别装对应的 extras;否则只装基础包。
此外 Dockerfile 还完成了几件对容器可用性至关重要的事:
- L175
crawl4ai-setup与 L177playwright install --with-deps:预装浏览器及系统依赖,并把 Chromium 拷贝到非 root 用户appuser的~/.cache/ms-playwright下(L179-L181),避免运行时权限问题; - L198
chown -R root:root ${APP_HOME} && chmod -R a-w ${APP_HOME}:应用目录对运行用户只读,防止写入型漏洞在/app持久化; - L203-L206 创建 0700 权限的沙箱化产物目录
/var/lib/crawl4ai/outputs(截图/PDF 输出); - L221
USER appuser:进程以非 root 用户运行。
3.3 容器级 HEALTHCHECK 比 API 更严格
除了 /health HTTP 端点,Dockerfile 还内置了容器级健康检查,它比"端点返回 200"多两道闸门:
HEALTHCHECK --interval=30s --timeout=10s --start-period=5s --retries=3 \
CMD bash -c '\
MEM=$(free -m | awk "/^Mem:/{print \$2}"); \
if [ $MEM -lt 2048 ]; then \
echo "Warning: Less than 2GB RAM available! ..."; \
exit 1; \
fi && \
redis-cli ping > /dev/null && \
curl -f http://localhost:11235/health || exit 1'
即依次校验:可用内存不低于 2GB、Redis 可 ping 通、/health 返回成功。三者任一失败容器即标记 unhealthy——这也是后文"4GB 内存推荐"的直接来源。
3.4 运行本地构建
# Regular run
docker run -p 11235:11235 crawl4ai:local
# With increased shared memory
docker run --shm-size=2gb -p 11235:11235 crawl4ai:local
验收同样用 curl http://localhost:11235/health。
四、Option 3:Docker Compose 编排
Compose 适合需要管理环境变量与持久配置的场景。原文档的用法(基于当时版本的多 profile 设计):
# Clone the repository
git clone https://github.com/unclecode/crawl4ai.git
cd crawl4ai
# AMD64: 本地构建运行
docker-compose --profile local-amd64 up
# AMD64: 从 Docker Hub 运行
VERSION=basic docker-compose --profile hub-amd64 up # Basic
VERSION=all docker-compose --profile hub-amd64 up # Full ML/LLM
VERSION=gpu docker-compose --profile hub-amd64 up # GPU
# ARM64 同理,使用 local-arm64 / hub-arm64 profile
docker-compose --profile local-arm64 up
VERSION=basic docker-compose --profile hub-arm64 up
VERSION=all docker-compose --profile hub-arm64 up
VERSION=gpu docker-compose --profile hub-arm64 up
环境变量(可选,写入 .env 文件):
# Create a .env file
CRAWL4AI_API_TOKEN=your_token
OPENAI_API_KEY=your_openai_key
CLAUDE_API_KEY=your_claude_key
原文档列出 compose 文件包含的能力:内存管理(4GB 上限 / 1GB 预留)、浏览器用共享内存卷、健康检查、自动重启策略、完整端口映射。
4.1 当前仓库 compose 文件的对应实现
当前 docker-compose.yml 已演进为单服务结构(IMAGE/TAG 环境变量选镜像,替代了 profile 切换),但原文档描述的每一项能力都能在文件中找到对应配置:
x-base-config: &base-config
ports:
- "11235:11235" # Gunicorn 端口
env_file:
- .llm.env # API 密钥文件(由 .llm.env.example 创建)
shm_size: "1gb" # 浏览器共享内存(私有 tmpfs)
cap_drop: [ALL] # 丢弃所有 capabilities
security_opt:
- no-new-privileges:true
pids_limit: 512 # PID 上限
read_only: true # 根文件系统只读
tmpfs: # 仅这些路径可写
- /tmp
- /var/lib/redis
- /var/lib/crawl4ai/outputs:mode=0700
- /home/appuser/.cache
deploy:
resources:
limits: { memory: 4G } # 原文档"4GB limit"
reservations: { memory: 1G } # 原文档"1GB reserved"
restart: unless-stopped
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:11235/health"]
interval: 30s
timeout: 10s
retries: 3
start_period: 40s
user: "appuser"
对比原文档有三处值得注意的演进:
- API 密钥文件由
.env改为.llm.env:L8 的env_file指向.llm.env,并支持OPENAI_API_KEY、ANTHROPIC_API_KEY、GEMINI_API_KEY、LLM_PROVIDER等可选变量(L9-L18 注释块); - 共享内存从"卷挂载"改为"私有 tmpfs":L19-L20 注释明确说明,原先对宿主机
/dev/shm的绑定挂载是"共享且可写"的隐患,现改用shm_size提供的隔离 tmpfs; - 安全加固:
read_only根文件系统、cap_drop: ALL、no-new-privileges、pids_limit等最小权限设置是原文档时代没有的。
build 段(L57-L62)则直接消费 INSTALL_TYPE 与 ENABLE_GPU 两个构建参数,与 Option 2 的 docker build --build-arg 完全同源,可用 IMAGE=local-test docker compose up 覆盖为本地镜像(L53 注释)。
五、One-Click Deployment 与规格建议
原文档最后一节提供云厂商一键部署入口(DigitalOcean 部署徽章),部署过程自动完成:搭建包含 Crawl4AI 的容器、配置 Playwright 及全部依赖、在 11235 端口启动 FastAPI 服务、设置健康检查与自动部署。
原文档给出的规格建议:
最低 4GB 内存,部署时选择 "professional-xs" 或更高规格以保证稳定运行。
该建议与仓库内证据一致:Dockerfile 的 HEALTHCHECK 在可用内存低于 2GB 时直接判不健康(4GB 机器扣除系统开销后恰好满足),compose 文件也把内存上限设为 4G。低于此规格部署,容器会频繁进入 unhealthy 状态。
六、新旧差异与兼容性速查
把原文档与当前仓库状态并置,有几处需要在实操时留意(基于当前仓库源码确认):
| 项目 | 原文档(Legacy) | 当前仓库实际 |
|---|---|---|
| 镜像标签 | basic-amd64、all-arm64、gpu-… 等标签 |
deploy/docker/README.md 建议按版本号拉取(如 unclecode/crawl4ai:0.8.6 或 :latest),多架构由 manifest 自动选择 |
INSTALL_TYPE 取值 |
basic(默认)/ all |
Dockerfile 分支为 default(默认)/ all / torch / transformer,basic 对应现语义的默认档 |
| GPU 前提 | ENABLE_GPU=true |
额外要求 TARGETARCH=amd64,ARM 平台构建会跳过 CUDA 安装 |
| Compose 结构 | local-* / hub-* 多 profile + VERSION 变量 |
单服务 + IMAGE/TAG 变量,构建参数走 build.args |
| 密钥文件 | .env(CRAWL4AI_API_TOKEN 等) |
.llm.env(LLM 密钥为主),CRAWL4AI_API_TOKEN 仍用于 socket 级鉴权绑定 |
| 共享内存 | 宿主机 /dev/shm 挂载 |
shm_size: 1gb 私有 tmpfs |
这些差异不改变操作流程的骨架——仍是"选镜像 → 加 shm → 跑 → curl 验收",只是标签名与参数默认值随版本演进。
七、部署后验证清单
容器启动后,按以下顺序验证(依据均可在仓库中复核):
- API 存活:
curl http://localhost:11235/health,应返回status: ok与版本号(deploy/docker/server.py); - 内存门槛:容器
docker ps状态非 unhealthy,意味着 2GB 内存闸、Redis ping、HTTP 健康检查三者均通过(Dockerfile); - 进程拓扑:容器内 supervisord 同时托管
redis(priority 10)与gunicorn(priority 20)两个 program,任一挂掉都会自动重启(deploy/docker/supervisord.conf); - 端口面:仅
11235对外;Redis 只监听回环地址(supervisord.conf L9 的--bind 127.0.0.1 ::1),Dockerfile 注释(L218-L219)也明确"Redis is in-container only; never expose its port"。
完成以上四步,即等同于原文档三种方式共同的验收标准,且能解释容器内部每一项配置的来源。
atomcodeClaude Code 的开源替代方案。连接任意大模型,编辑代码,运行命令,自动验证 — 全自动执行。用 Rust 构建,极致性能。 | An open-source alternative to Claude Code. Connect any LLM, edit code, run commands, and verify changes — autonomously. Built in Rust for speed. Get StartedRust0623
Hy4-previewHy4 preview 是由腾讯混元团队研发的新一代混合专家(MoE)旗舰模型。模型总参数量 770B,每个 token 激活 49B,主干共包含78层,第一层采用标准 FFN,其余 77 层均为 MoE 结构,每层包含 256 个路由专家与 1 个共享专家,每个 token 激活 top-8 路由专家及共享专家。主干之外原生内置 1 层 MTP(总参数量 10B,激活 0.7B)以支持投机解码。Python00
GLM-5.3GLM-5.3 与 GLM-5.2 使用相同的基座模型——所有提升均来自后训练。与 GLM-5.2 相比,它在复杂编程和长程任务上的表现显著提升。Jinja00
GLM-5.3-FlashGLM-5.3-Flash (320B-A18B),是GLM-5系列的首个原生多模态模型。320B总参数,能力超过GLM-5.2Jinja00
Spark-X2.5-4BSpark-X2.5-4B 旨在让强大的 AI 更实用、更高效、更易获得。在广泛日常任务中表现强劲,涵盖对话、写作、翻译、推理、编码、工具调用以及智能体工作流,并在同等规模的开源模型中取得领先成绩。Spark-X2.5 将面向效率的架构与最高 1M tokens 的原生上下文窗口相结合,并支持 200 多种语言。Python00
Spark-X2.5-1.7BSpark-X2.5-1.7B 旨在让强大的 AI 更加实用、高效且易于获取。这些模型在广泛的日常任务中表现出色,涵盖对话、写作、翻译、推理、编程、工具调用和智能体工作流,并在同等规模的开源模型中取得领先结果。Spark-X2.5 将面向效率的架构与最高 1M tokens 的原生上下文窗口相结合,并支持 200 多种语言。Python00