TinkerLab
跳转可下载配置
01 // HOMELABDocker 容器Apple Silicon MacNVIDIA 独显阅读与复现约 9 分钟

Ollama + Open WebUI:安装、持久化、备份、升级和恢复实战

超越官方 Quick Start 的生产级运维手册:锁定镜像 Tag、显式挂载宿主机持久化目录、升级前 10 秒快照备份,以及跨版本迁移失败后的完整恢复演练。

[核心实测结论 / TL;DR]在 Tinker AI 实测工坊针对「Ollama + Open WebUI:安装、持久化、备份、升级和恢复实战」的复现测试中(实测环境:Linux HomeLab(Ubuntu 24.04 · Docker Compose v2.29)及 macOS 宿主机 + Docker WebUI 双环境实测,软件版本:Ollama 0.5.7 / Open WebUI v0.5.10 / SQLite 3 (webui.db),验证日期:2026-10-23):超越官方 Quick Start 的生产级运维手册:锁定镜像 Tag、显式挂载宿主机持久化目录、升级前 10 秒快照备份,以及跨版本迁移失败后的完整恢复演练。 离线边界为「需显式配置环境变量以阻断启动期外部连接」(“本地部署”不自动等于所有环节离线!必须配置 `SCARF_NO_ANALYTICS=true` 并指定本地 `RAG_EMBEDDING_ENGINE=ollama`,否则容器启动时会尝试连接 HuggingFace。),关键限制包括:Open WebUI 升级启动时会自动对 `webui.db` 执行 Alembic 数据库结构迁移;如果未提前备份数据目录,遇到新版本 Bug 直接改回旧镜像 Tag 会因数据库 Schema 不兼容而崩溃。
REPRODUCIBILITY MANIFEST // 实测环境与边界清单
最后实测验证日期:2026-10-23
实测硬件与操作系统 (Tested Hardware & OS)

Linux HomeLab(Ubuntu 24.04 · Docker Compose v2.29)及 macOS 宿主机 + Docker WebUI 双环境实测

锁定软件与模型版本 (Pinned Stack Versions)
Ollama 0.5.7Open WebUI v0.5.10SQLite 3 (webui.db)
离线与外部连接核查 (Offline & Network Boundary)
需显式配置环境变量以阻断启动期外部连接

“本地部署”不自动等于所有环节离线!必须配置 `SCARF_NO_ANALYTICS=true` 并指定本地 `RAG_EMBEDDING_ENGINE=ollama`,否则容器启动时会尝试连接 HuggingFace。

已知限制与失败案例 (Known Limits)
  • Open WebUI 升级启动时会自动对 `webui.db` 执行 Alembic 数据库结构迁移;如果未提前备份数据目录,遇到新版本 Bug 直接改回旧镜像 Tag 会因数据库 Schema 不兼容而崩溃。
  • 切勿依赖难以定位的匿名卷,一旦误执行 `docker compose down -v` 会导致历史对话与提示词全部丢失;推荐使用显式宿主机目录挂载。
遇到环境异常?打开排障诊断树 →

1. 持久化目录规划与锁定版本的 Compose 部署

官方快速开始文档默认使用 `:main` 标签与内部命名卷。在长期自托管使用中,浮动标签意味着一次常规重启就可能因上游破坏性更新导致服务瘫痪。本方案显式锁定 `ollama:0.5.7` 与 `open-webui:v0.5.10`,并将所有状态数据收敛在 `./tinker-local-ai-data/{ollama,open-webui}` 目录下。
表 1:宿主机持久化挂载路径与备份策略对照表
宿主机挂载路径容器内路径包含核心资产推荐备份策略
./tinker-local-ai-data/open-webui/webui.db/app/backend/data/webui.db用户账号、对话历史、系统提示词、知识库索引元数据每次升级镜像前停机打包备份(必做)
./tinker-local-ai-data/open-webui/vector_db/app/backend/data/vector_dbChromaDB 本地文档向量切片与上传原件随 open-webui 目录一并打包快照
./tinker-local-ai-data/ollama/models/root/.ollama/modelsGGUF 模型权重大文件与自定义 Modelfile 清单日常快照排除数十 GB 的 blobs,仅备份 manifests
Pre-Upgrade Backup & Full Disaster Recovery Drill
# [Step 1] Stop WebUI container cleanly to flush SQLite WAL journal
docker compose stop open-webui

# [Step 2] Create timestamped backup of chats, users, prompts & vector DB
tar -czf openwebui-state-$(date +%F-%H%M).tar.gz ./tinker-local-ai-data/open-webui

# [Step 3] Upgrade image tag in docker-compose.yml and start
docker compose up -d

# [Step 4] Emergency Rollback if the new version fails:
docker compose stop open-webui
rm -rf ./tinker-local-ai-data/open-webui
tar -xzf openwebui-state-2026-10-23-0900.tar.gz
# Revert image tag in docker-compose.yml, then:
docker compose up -d

2. 核查云模型与外部连接:实现真正的离线可控

即便部署在本地机器上,Open WebUI 在默认配置下仍可能产生两类外部网络请求:(1)后台「外部连接」默认开启了 OpenAI API 探测;(2)默认 Embedding 引擎首次触发文档解析时会向 `huggingface.co` 下载 `all-MiniLM-L6-v2`。实测离线前请务必在管理员设置中关闭未使用的云端接口,并将 Embedding 引擎切换为本地 Ollama。

3. SQLite WAL 事务一致性校验与在线热备方案

Open WebUI 底层使用 SQLite 存储状态,运行期会产生 `webui.db-wal` 与 `webui.db-shm` 预写日志。如果在用户正在流式对话时直接用 `cp` 或 `tar` 强行拷贝运行中的目录,极易因 WAL 页未刷盘导致恢复后报 `database disk image is malformed` 损坏。最稳妥的方式是在每日凌晨低峰期先 `docker compose stop open-webui` 停机 5 秒再打包,或使用 `sqlite3` 原生 `.backup` 指令执行原子热备。
FIELD Q&A // 常见实测疑问与边界解答

复现常见疑问与深层原理解答

Q: 为什么拔掉网线离线启动时,Open WebUI 会卡住 60 秒才显示登录页?

默认情况下 Open WebUI 启动时会尝试请求 `https://api.openai.com/v1/models` 拉取模型列表。在环境变量中添加 `ENABLE_OPENAI_API=false` 与 `OFFLINE_MODE=true` 即可实现断网秒开。

Q: 如果重建容器时没有固定 `WEBUI_SECRET_KEY` 会发生什么?

`WEBUI_SECRET_KEY` 用于签名所有用户的登录会话 JWT。如果未在 `docker-compose.yml` 中显式固定该密钥,每次重建容器都会随机生成新密钥,导致所有已登录终端全部掉线报 `401`。

REPRODUCIBLE ARTIFACT // 配套可参数化附件

Ollama + Open WebUI 持久化、备份与安全回滚栈 (Docker Compose)

锁定镜像版本、显式挂载宿主机持久化目录(支持 30 秒快照备份与跨版本回滚)、关闭遥测及 KV Cache 优化。

docker-compose.ollama-webui.yml ↗
修改上方参数将实时更新下方配置内容
# Tinker AI Verified Stack — Ollama + Open WebUI (Guide #3)
# Pre-upgrade backup: tar -czf backup-$(date +%F).tar.gz ./tinker-local-ai-data

services:
  ollama:
    image: ollama/ollama:0.5.7
    container_name: tinker-ollama
    restart: unless-stopped
    ports:
      - "127.0.0.1:11434:11434"
    environment:
      - OLLAMA_HOST=0.0.0.0:11434
      - OLLAMA_FLASH_ATTENTION=1
      - OLLAMA_KV_CACHE_TYPE=q8_0
      - OLLAMA_NUM_PARALLEL=2
      - OLLAMA_KEEP_ALIVE=15m
    volumes:
      - ./tinker-local-ai-data/ollama:/root/.ollama

  open-webui:
    image: ghcr.io/open-webui/open-webui:v0.5.10
    container_name: tinker-open-webui
    restart: unless-stopped
    depends_on:
      - ollama
    ports:
      - "127.0.0.1:3000:8080"
    environment:
      - OLLAMA_BASE_URL=http://ollama:11434
      - RAG_EMBEDDING_ENGINE=ollama
      - RAG_EMBEDDING_MODEL=bge-m3:latest
      - ENABLE_RAG_HYBRID_SEARCH=true
      - RAG_TOP_K=5
      - SCARF_NO_ANALYTICS=true
      - DO_NOT_TRACK=true
    extra_hosts:
      - "host.docker.internal:host-gateway"
    volumes:
      - ./tinker-local-ai-data/open-webui:/app/backend/data

更多可复现工程指南

查看全部 42 篇指南 →