OpenWebUI(1)源码学习构建
本文介绍了基于Docker源码构建的Web应用开发环境配置。项目采用Python≥3.11后端和Svelte前端框架(Node.js≥20.10),包含完整目录结构说明:后端API服务、数据库操作位于backend目录;前端组件在src目录采用Svelte开发;另有Cypress测试框架、K8s部署配置及各类自动化脚本。文档详细描述了dev.sh等环境启动脚本的使用方法,以及前后端代码的组织架构,
1. 前言
通过docker镜像拉取安装就不介绍了,官方的命令很多。本节主要撸一撸源码,所以,本地构建。
当前项目基于main分钟2025-5-30日的最新提交进行分析。随着后续的升级过程中,可能会出现差异。
2. 技术框架和启动环境
后端python,前端svelte
环境要求:python > = 3.11 ,Node.js > = 20.10
3. 源码目录
3.1 根目录

目录说明
- backend目录:后端代码目录,包含API服务、数据库操作等
- cypress 目录:包含Cypress测试框架的配置和测试脚本,用于端到端测试
- docs 目录:文档目录,包含项目说明、安全指南等。
- kubernetes : 包含Kubernetes部署配置文件。
- scripts : 包含各种脚本文件,用于自动化部署、测试或其他任务的脚本。
- src :前端代码目录,存放Svelte组件和相关资源的地方。
- static : 静态文件目录,如图片、CSS、客户端JavaScript等。
- test/test_files/image_gen : 测试目录下的子目录,包含用于测试的图像生成器。
3.2. 后端目录

- data文件夹:用于存储后端服务需要的数据文件,如数据库、文档等
- open-webui文件夹:包含后端服务的主要代码和配置文件
- dev.sh:用于本地开发环境的启动脚本
- start.sh 和 start_windows.bat - 用于启动后端服务的脚本,分别适用于类Unix系统和Windows系统。
3.2.1 data目录

3.2.1.1 cache - 用于存储应用程序的缓存数据。
(1)audio
(2)functions 包含一些后端服务使用的函数或脚本

(3)image
(4)tools包含一些用于后端服务的工具或脚本

3.2.1.2 uploads - 用于存储用户上传的文件
知识库上传的文件在此处

3.2.1.3 vector_db - 用于存储向量数据库或类似的数据结构
sqlite数据库

3.2.1.4 webui.db后端服务使用的数据库文件

3.2.1.5 readme.txt - 包含文件夹的说明或使用指南
3.2.2 dev.sh文件
用于本地开发环境的启动脚本
PORT="${PORT:-8080}"
uvicorn open_webui.main:app --port $PORT --host 0.0.0.0 --forwarded-allow-ips '*' --reload
uvicorn是web服务器,可以理解为javaweb中Tomcat
如果你用了conda来创建的虚拟环境。虚拟环境指定了python版本,就可以通过pip安装uvicorn。其中requirements.txt文件中指定了uvicorn包版本。国内pip源可以指定华为的,清华源感觉总是出错,不知是本人配置问题还是怎样。

如何启动后端服务?
(1)通过命令行启动。conda创建虚拟环境后,激活虚拟环境。然后进入到项目backend目录喜下,运行命令:
D:\GiteeDownloadProject\AIStudyProject\open-webui\backend>uvicorn open_webui.main:app --port 8080 --host 0.0.0.0 --forwarded-allow-ips '*' --reload
(2)如果使用PyCharm软件,配置如下

3.2.3 requirements.txt文件
python依赖包
3.2.4 start.sh文件
启动后端服务的window脚本。
相较于开发环境dev.sh 多了一些配置项,最终都是通过uvicorn命令启动,来运行 open-webui/backend/open_webui/main.py 文件中的FastAPI的 app 应用对象,监听在指定的主机和端口上,并允许所有的转发 IP 地址。
流程:
(1)识别当前脚本所在目录为项目的工作目录
(2)设置访问地址和端口,访问地址允许全部IP
(3)webui_secret_key配置,用于系统session和token访问鉴权,如果负载多节点部署,同一个key能够保证用户访问的时候,会话一致性,否则可能造成认证失败,重新登录。如果不做配置,在系统env.py文件中会默认一个key值
(4)是否安装ollama配置(这个是linux启动命令中配置,window启动命令start_windows.bat没有),linux环境下open-webui的启动命令支持,直接命令方式安装ollama
(5)是否配置huggingFace的space_id,如果设置了HuggingFace的space id,则进行web应用配置,以适应 HuggingFace space 的部署要求。
(6)通过uvicorn启动python服务
#!/usr/bin/env bash
# 这行代码的作用是获取当前脚本文件所在的目录路径,并赋值给 SCRIPT_DIR 变量。它常用于确保后续操作是在脚本所在目录下执行的
SCRIPT_DIR=$( cd -- "$( dirname -- "${BASH_SOURCE[0]}" )" &> /dev/null && pwd )
cd "$SCRIPT_DIR" || exit
# Add conditional Playwright browser installation
if [[ "${WEB_LOADER_ENGINE,,}" == "playwright" ]]; then
if [[ -z "${PLAYWRIGHT_WS_URL}" ]]; then
echo "Installing Playwright browsers..."
playwright install chromium
playwright install-deps chromium
fi
python -c "import nltk; nltk.download('punkt_tab')"
fi
KEY_FILE=.webui_secret_key
# 设置主机端口号 和 主机地址
PORT="${PORT:-8080}"
HOST="${HOST:-0.0.0.0}"
# 若秘钥为空 生成新的秘钥 ,如果没有该文件,在程序env.py中默认值=t0p-s3cr3t
if test "$WEBUI_SECRET_KEY $WEBUI_JWT_SECRET_KEY" = " "; then
echo "Loading WEBUI_SECRET_KEY from file, not provided as an environment variable."
if ! [ -e "$KEY_FILE" ]; then
echo "Generating WEBUI_SECRET_KEY"
# Generate a random value to use as a WEBUI_SECRET_KEY in case the user didn't provide one.
echo $(head -c 12 /dev/random | base64) > "$KEY_FILE"
fi
echo "Loading WEBUI_SECRET_KEY from $KEY_FILE"
WEBUI_SECRET_KEY=$(cat "$KEY_FILE")
fi
# 如果当前docker镜像中有ollama镜像,则启动ollama服务 (在此前的dockerfile中如果用户使用docker内ollama,则在镜像制作阶段,已经下载ollama安装)
if [[ "${USE_OLLAMA_DOCKER,,}" == "true" ]]; then
echo "USE_OLLAMA is set to true, starting ollama serve."
ollama serve &
fi
# 如果在docker内安装cuda,则将 PyTorch 和 CUDA 相关的库路径添加到 LD_LIBRARY_PATH,以确保程序能正确加载这些动态库。
if [[ "${USE_CUDA_DOCKER,,}" == "true" ]]; then
echo "CUDA is enabled, appending LD_LIBRARY_PATH to include torch/cudnn & cublas libraries."
export LD_LIBRARY_PATH="$LD_LIBRARY_PATH:/usr/local/lib/python3.11/site-packages/torch/lib:/usr/local/lib/python3.11/site-packages/nvidia/cudnn/lib"
fi
# 如果设置了HuggingFace的space id,则进行web应用配置,以适应 HuggingFace space 的部署要求。
# Check if SPACE_ID is set, if so, configure for space
if [ -n "$SPACE_ID" ]; then
echo "Configuring for HuggingFace Space deployment"
if [ -n "$ADMIN_USER_EMAIL" ] && [ -n "$ADMIN_USER_PASSWORD" ]; then
echo "Admin user configured, creating"
WEBUI_SECRET_KEY="$WEBUI_SECRET_KEY" uvicorn open_webui.main:app --host "$HOST" --port "$PORT" --forwarded-allow-ips '*' &
webui_pid=$!
echo "Waiting for webui to start..."
while ! curl -s http://localhost:8080/health > /dev/null; do
sleep 1
done
echo "Creating admin user..."
curl \
-X POST "http://localhost:8080/api/v1/auths/signup" \
-H "accept: application/json" \
-H "Content-Type: application/json" \
-d "{ \"email\": \"${ADMIN_USER_EMAIL}\", \"password\": \"${ADMIN_USER_PASSWORD}\", \"name\": \"Admin\" }"
echo "Shutting down webui..."
kill $webui_pid
fi
export WEBUI_URL=${SPACE_HOST}
fi
# 查找系统中可用的 Python 3 解释器路径,优先查找 python3,若未找到则尝试查找 python。 最终将查找到的路径赋值给变量 PYTHON_CMD。
PYTHON_CMD=$(command -v python3 || command -v python)
# ##############################################################################################
# 该Shell命令启动了一个Uvicorn Web服务器,用于运行Open WebUI应用。具体功能如下:
# 1. WEBUI_SECRET_KEY="$WEBUI_SECRET_KEY":将环境变量 WEBUI_SECRET_KEY 传递给即将执行的进程。
# 2. exec "$PYTHON_CMD" -m uvicorn:使用指定的Python解释器运行Uvicorn模块。
# 3. open_webui.main:app:指定要运行的应用模块和实例(即 app 对象)。
# 4. --host "$HOST" 和 --port "$PORT":绑定服务器监听的主机和端口。
# 5. --forwarded-allow-ips '*':允许所有IP通过反向代理访问。
# 6. --workers "${UVICORN_WORKERS:-1}":设置工作进程数,默认为1
# #############################################################################################
WEBUI_SECRET_KEY="$WEBUI_SECRET_KEY" exec "$PYTHON_CMD" -m uvicorn open_webui.main:app --host "$HOST" --port "$PORT" --forwarded-allow-ips '*' --workers "${UVICORN_WORKERS:-1}"
3.2.5 start_windows.bat文件
同start.sh。
3.2.6 open_webui目录

3.2.6.1 data目录
用于存储后端服务需要的数据文件。
3.2.6.2 internal目录
针对项目早期或部分模块中仍在使用 Peewee ORM 的数据库模型。
是项目早期使用的 Peewee 数据库迁移机制,主要用于用户、聊天、标签等功能模块。
这部分是原来旧的迁移方式,具体对比如下一节说明
3.2.6.3 migrations目录
数据库迁移脚本,用于数据库结构的版本控制

在 FastAPI 项目中集成 Alembic 和 SQLAlchemy 的迁移机制
FastAPI 中集成 Alembic 和 SQLAlchemy 的核心原理是通过 env.py 配置文件来协调数据库连接、模型元数据以及迁移脚本的执行方式。Alembic 利用 SQLAlchemy 提供的引擎和连接能力,确保数据库结构能够与模型定义保持同步。
当前迁移脚本使用的技术和internal目录下使用数据库迁移技术对比

从目录结构和内容来看:
- internal/migrations 是项目早期使用的 Peewee 数据库迁移机制,主要用于用户、聊天、标签等功能模块。
- migrations 是后来引入的 Alembic + SQLAlchemy 的迁移机制,用于更现代的数据库模式管理和自动化迁移。
这表明项目正在逐步从 Peewee 向 SQLAlchemy 过渡,两个迁移系统并存是过渡阶段的一种合理设计。未来可能会逐渐淘汰 internal/migrations,完全转向 migrations。
3.2.6.4 models目录
详细介绍如下文章
3.2.6.5 retrieval目录(检索模块)
详细介绍如下文章
3.2.6.6 routers目录
详解介绍如下文章
3.2.6.7 socket目录
详细介绍如下文章
3.2.6.8 static目录
3.2.6.9 storage目录
详细介绍如下文章
3.2.6.10 test目录
Open WebUI 项目的 测试目录,它包含用于验证系统关键模块功能的集成测试和单元测试。该目录结构清晰、模块化良好,便于开发者进行自动化测试与持续集成。
test/
├── apps
│ └── webui
│ ├── routers
│ │ ├── test_auths.py → 测试认证相关接口
│ │ ├── test_chats.py → 测试聊天记录管理接口
│ │ ├── test_models.py → 测试模型管理接口
│ │ ├── test_prompts.py → 测试提示词模板接口
│ │ └── test_users.py → 测试用户管理接口
│ └── storage
│ └── test_provider.py → 测试文件存储抽象层(local, s3, gcs, azure)
├── util
│ ├── abstract_integration_test.py → 提供通用测试基类与 Postgres 测试容器管理
│ └── mock_user.py → 提供模拟用户上下文工具函数
└── __init__.py
3.2.6.11 utils目录
(1)images/comfyui.py文生图模块
(2)utils/telemetry追踪遥测模块
(3)utils常用特定功能模块
3.2.6.12 __init__.py文件
python生命文件
3.2.6.13 alembic.ini文件
3.2.6.14 config.py文件
后端服务的配置文件。对于标记为PersistentConfig的环境变量,它们的值被持久化并存储在内部。下次启动后,他会去数据库寻找,而不会因为你重启时修改环境变量而改变。没有被PersistentConfig标记的配置项可以修改更新
官方对此文件中相关配置项说明:
3.2.6.15 constants.py文件
3.2.6.16 env.py文件
包含环境变量的配置,此文件中变量值,可以通过docker-compose.*.yaml中进行覆盖
官方文档变量解释如下:
3.2.6.17 functions.py文件
3.2.6.18 main.py文件
3.2.6.19 tasks.py文件
3.3 前端目录

- lib:包含可重用的JavaScript或Svelte组件、工具函数、实用程序等
- routes:包含Svelte路由文件,用于定义应用程序的页面路由。
- app.css:包含全局样式表,定义了样式重置、通用样式或主题。
- app.d.ts:TypeScript的声明文件,用于为项目提供类型定义。
- app.html:项目的HTML模板文件,通常是应用程序的入口点。
- tailwind.css:使用Tailwind CSS时的全局样式文件
待续:
Open WebUI项目源码学习记录(从0开始基于纯CPU环境部署一个网页Chat服务)_openwebui二次开发-CSDN博客
更多推荐





所有评论(0)