企业内网本地部署集成LDAP认证的Open-WebUI+Deepseek-R1 70b
配置思路
使用场景
某研发企业,对保密性要求较高,研发人员在无Internet的内网工作。在本地内网搭建运行一套deekseek-r1:70b的模型, 使用open-webui,配合LDAP认证服务器, 向100多位研发的提供AI问答功能。 因为使用人数不多,所以我们采用Ollama作为运行本地大模型的框架,让此工具快速上线。
最终效果是向用户提供一个https连接的open-webui的入口,公司员工使用AD账户登录, 可以同时有5个用户并发提问。
服务器配置
硬件配置上,我们采用1台8卡4090,配置5用户并发。架构图上的GPU Server 2 是规划中的第二台服务器,实际并未上线,使用云上的一台H800进行过负载模拟。
超微420GP-TNR 4U机头,配合8张24G显存4090显卡,具体配置如下:
- 2 * Intel 6326
- 16 * 32G DDR4
- 2 * 960G SATA SSD
- 4 * 3.84TB U.2
- 8 * 4090
- 2 * 2000W电源
网络架构
在同一台GPU服务器运行nginx, open-webui和ollama三个容器。其中,nginx1把open-webui的接口封装为https, 向用户提供访问;nginx2其实和nginx1是同一个容器
用户验证使用公司环境中已经存在的AD, 配置open-webui的LDAP集成,
架构图如下:
配置Docker环境
#配置国内源
apt install docker.io
echo '{"registry-mirrors": ["https://docker.1ms.run"]}' | sudo tee /etc/docker/daemon.json > /dev/null
systemctl daemon-reload
systemctl restart docker
#安装Cuda Toolkit
apt install nvidia-cuda-toolkit
nvcc -V #验证是否安装成功
#安装Nvidia Container Toolit
# 不装这个Container Toolkit, GPU是无法透传给容器的
# 这一步得配置shell和apt的海外代理
curl -s -L https://nvidia.github.io/nvidia-container-runtime/gpgkey | sudo apt-key add -
distribution=$(. /etc/os-release;echo $ID$VERSION_ID)
curl -s -L https://nvidia.github.io/nvidia-container-runtime/$distribution/nvidia-container-runtime.list | sudo tee /etc/apt/sources.list.d/nvidia-container-runtime.list
apt update
apt install nvidia-container-toolkit
systemctl restart docker
#创建docker network
#为了与open-webui和nginx反向代理联动而设
docker network create ollama-network
配置OLLAMA容器
拉取并运行ollama容器
docker pull ollama/ollama
mkdir -p /mnt/ollama
docker run -d \
-e OLLAMA_NUM_PARALLEL=5 \
--restart always
--gpus=all \
-v /mnt/ollama:/root/.ollama \
-p 11434:11434 \
--name ollama \
--network ollama-network \
ollama/ollama
# 模型的位置存放在本地的/mnt/ollama下
# OLLAMA_NUM_PARALLEL是可以同时向ollama提问的请求数, 超过这个上限的用户会排队。
# --gpus "device=0,2" 可以指定使用几张GPU,例子中的0,2是nvidia-smi中看到的GPU序号
拉取deepseek-r1:70b
docker exec -it ollama ollama pull deekpseek-r1:70b
# 你也可以摘取更多的小尺寸的模型,很多时候我觉得7b的模型也挺聪明的了~
配置nginx
配置nginx代理https
配置nginx 容器所需目录
docker pull nginx
mkdir -p /mnt/nginx
mkdir -p /mnt/nginx/conf.d
mkdir -p /mnt/nginx/log
mkdir -p /mnt/nginx/ssl/private
touch /mnt/nginx.conf
touch /mnt/nginx/conf.d/default.conf
填充nginx.conf初始配置
#/mnt/nginx/nginx.conf,这个配置基本不用改, 实际的配置是放在conf.d目录下面的一个.conf文件
cat > /mnt/nginx/nginx.conf << EOF
user nginx;
worker_processes auto;
error_log /var/log/nginx/error.log notice;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
#tcp_nopush on;
keepalive_timeout 65;
#gzip on;
include /etc/nginx/conf.d/*.conf;
}
EOF
SSL证书
你可以使用openssl生成自签名的证书,如果想使用公网域名和证书也可以获取相应的公网SSL证书。可以参考 使用OpenSSL生成自签名SSL证书
nginx的SSL证书的crt和key文件分别命名为open-webui.crt和open-webui.key,放到/mnt/nginx/ssl/private目录下
配置open-webui.conf
# /mnt/nginx/conf.d/open-webui.conf, 用EOF导入文件时变量符号$需要用\转义一下
cat > /mnt/nginx/conf.d/open-webui.conf << EOF
server {
listen 80;
#域名替换成你自己的,如果不想用ssl,就不用费用配置下方的443端口上的监听了。
server_name open-webui.owl.local;
return 301 https://\$server_name$request_uri;
}
server {
listen 443 ssl;
server_name open-webui.owl.local;
# 此处指定了SSL证书
ssl_certificate /etc/ssl/private/open-webui.crt;
ssl_certificate_key /etc/ssl/private/open-webui.key;
location / {
proxy_pass http://open-webui:8080;
proxy_set_header Upgrade $http_upgrade; #这两行一定要有,以支持websocket
proxy_set_header Connection "upgrade"; #这两行一定要有,以支持websocket
proxy_set_header Host \$host;
proxy_set_header X-Real-IP \$remote_addr;
proxy_set_header X-Forwarded-For \$proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto \$scheme;
}
}
EOF
配置nginx负载均衡ollama
如果你有多台GPU服务器或者多个ollama实例, 可以用nginx提供的负载均衡把这些资源汇集在一个接口对open-webui提供服务。 但是有两点要声明一下:
- ollama在处理并发的时候效率并不高, 如果只有比如说一两百总用户, 数台运行ollama的实例,可以快速的用本案的方法部署。如果规模再大,我们应该用vllm来替换ollama。
- nginx代理ollama后,open-webui(或者别的工具比如chatbox)并不会知道这个负载均衡后面到底有多少ollama以及这些ollama的配置情况, 对于open-webui来说, 它只会读取第一台联系到的ollama实例中托管的模型。 所以,我们应该让所有的ollama实例上托管的模型完全一致。ollama实例的配置也应该尽量保持一致。
# /mnt/nginx/conf.d/ollama.conf, 如果你只有一台GPU服务器或者容器,不用配置这个,直接在open-webui的设置中指向你那唯一的ollama实例即可
cat > /mnt/nginx/conf.d/ollama.conf << EOF
upstream backend_servers {
server 192.168.1.11:11434; #GPU服务器1
server 192.168.1.12:11434; #GPU服务器2
}
server {
listen 8899; #把所有的ollama实例都集合到nginx服务器的8899端口, open-webui配置ollama实例时填写nginx服务器的地址和8899端口
location / {
proxy_pass http://backend_servers;
}
}
启动容器
docker run \
-d -p 80:80 -p 443:443 \
--restart always \
-v /mnt/nginx/conf.d:/etc/nginx/conf.d \
-v /mnt/nginx/nginx.conf:/etc/nginx/nginx.conf \
-v /mnt/nginx/log:/var/log/nginx \
-v /mnt/nginx/ssl/private:/etc/ssl/private \
--name nginx \
--network ollama-network \
nginx
配置Open-webui
拉取open-webui
docker pull ghcr.io/open-webui/open-webui
mkdir /mnt/open-webui
docker run -d \
--restart always \
-p 8080:8080 \
-v /mnt/open-webui:/app/backend/data \
--name open-webui \
--network ollama-network \
ghcr.io/open-webui/open-webui
初次登录
容器宿主机的IP地址为192.168.1.10, http://192.168.1.10:8080 即可访问open-webui的登录界面
创建管理员账户
根据提示输入用户名, 邮箱和密码, 创建一个管理员账户,这个过程不需要验证邮箱,所以可以随便输入。
配置LDAP
在右上角的”设备“下的“通用”页签下
配置身份验证:
- 默认用户角色:启用
- 允许新用户注册:启用
这样用户在用LDAP账户登录后无须管理员批准即可使用。
配置LDAP认证:
- 主机:192.168.30.8 #这里填写LDAP或者域控制器的地址,如果你要使用TLS/LDAPS,这里必须填写域控制器或者LDAP服务器的主机名,比如dc01.owl.local,如果你不想这么麻烦,也不讲究,就用IP地址,但是端口一要用非加密的389端口。
- 端口:389 #如果要使用LDAPS则输入636
- Application DN: CN=DirLookup,OU=ServiceAccounts,OU=Shanghai,DC=owl,DC=local #一个用于查询LDAP的用户的DN名
- Application 密码: ******
- 邮箱属性:mail #用户的邮件地址的字段, LDAP和AD都是mail
- 用户名属性:samaccountname #AD是SamAccountName, LDAP是uid或者cn,根据实际情况来填写,用户登录的时候输入的用户名是哪个字段
- 搜索库:dc=owl, dc=local #在哪一个LDAP层级下开始搜索用户
- 搜索过滤器:(&(objectCategory=Person)(sAMAccountName=*)(memberOf:1.2.840.113556.1.4.1941:=CN=open-webui-users,OU=ApplicationGroups,OU=Groups,OU=Shanghai,DC=owl,DC=local)) #你也可以不填写, 会搜索所有的用户,本例中是指定open-webui-users这个组的成员才能访问
- TLS是否启用 #如果上方的端口选择了636,这里就得启用TLS,并且填写证书路径, 这个证书是从域控制器上导出的域服务器证书, X509 Base64格式,把这个证书拷贝到容器里面,然后在此指定此证书文件的位置
配置LDAP账户为管理员
用一个LDAP账户成功登录后,在管理员”设置“中的“用户”页签下, 找到该用户,点击用户名前的”用户“ 权限组,即可将这个用户转化为”管理员“。
配置普通用户使用模型
在管理员设置菜单,模型页签下,选中某一个模型,修改其可见性为:Public,否则普通用户登录系统后左上角看不到任务模型列表。
配置外部连接
因为是内网环境,所以我们关闭OpenAI API,启用Ollama API, 填写:http://nginx:8899, 这里的nginx是我们创建的nginx容器的名字,因为在同一台物理机下的同一个docker网络,所以可以引用容器名。 如果你不用nginx反向代理,这里也可以直接填写ollama的API接口。
验证与结论
- LDAP普通用户可以成功登录,注意, 本例中需要用户在pen-webui-users组下, 你也可以不做这个限制,那随便一个AD用户都可以登录。
- 用户登录后可以在左上角看到deepseek-r1:70的模型, 我们只下载和开启了这一个模型的public权限,所以只能看到这一个,你也可以下载32b,14b, 7b的模型,并且把这些模型在open-webui的管理员后台设置成public,以让用户可以自由选择这几个模型。
- 多开几个页签模拟同时提问的并发场景,比如“给我讲一个1000字的故事”, 同时监控两台GPU服务器的GPU负载,你会发现第一个提问发起时激活了第一台GPU服务器的资源, 紧接着的第二个提问会让第二台服务器被激活。 nginx会依次把请求丢到两台GPU服务器上。
这已经是一个可用的内网DeepSeek环境了。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· TypeScript + Deepseek 打造卜卦网站:技术与玄学的结合
· Manus的开源复刻OpenManus初探
· 三行代码完成国际化适配,妙~啊~
· .NET Core 中如何实现缓存的预热?
· 如何调用 DeepSeek 的自然语言处理 API 接口并集成到在线客服系统