文章介绍:使用 VyOS Stream Q2 版本 部署OpenVPN Web ui 系统。
一、VyOS
1.1、VyOS镜像
官方下载
博主共享盘
1.2、VyOS安装
【Vyos-开源篇-1】- VMware安装VyOS虚拟机
1.3、VyOS配置
【VyOS-开源篇-32】- 家庭软路由 VyOS 完整配置
二、项目链接
GitHub GavinTan/openvpn
Docker GavinTan/openvpn
Blog GavinTan
三、部署指导
3.1、基础配置
如果需要使用mfa功能,一定要配置ntp和time-zone
configure
set container registry d.yydy.link:2023
set interfaces ethernet eth0 address '192.168.1.195/24'
set protocols static route 0.0.0.0/0 next-hop 192.168.1.254
set service ntp server ntp.aliyun.com
set service ntp server ntp.tencent.com
set service ntp server time.hicloud.com
set system name-server '192.168.1.254'
set system time-zone 'Asia/Shanghai'
commit
save
3.2、拉取镜像
add container image yyxx/openvpn:latest

3.3、查看镜像
show container image

3.4、创建持久化文件目录
sudo mkdir -p /config/podman/openvpn/data && cd /config/podman/openvpn/data
3.5、初始化生成证书及配置文件
sudo podman run -v /config/podman/openvpn/data:/data --rm yyxx/openvpn --init
3.6、启动容器
configure
set container name ovpn-web allow-host-networks
set container name ovpn-web capability 'net-raw'
set container name ovpn-web capability 'net-admin'
set container name ovpn-web capability 'sys-admin'
set container name ovpn-web cpu-quota '1'
set container name ovpn-web device tun destination '/dev/net/tun'
set container name ovpn-web device tun source '/dev/net/tun'
set container name ovpn-web environment ADMIN_PASSWORD value 'admin'
set container name ovpn-web environment ADMIN_USERNAME value 'admin'
set container name ovpn-web environment ENV_UPDATE_CONFIG value 'false'
set container name ovpn-web environment OVPN_GATEWAY value 'false'
set container name ovpn-web host-name 'ovpn-web'
set container name ovpn-web image 'd.yydy.link:2023/yyxx/openvpn:latest'
set container name ovpn-web memory '1024'
set container name ovpn-web restart 'always'
set container name ovpn-web shared-memory '128'
set container name ovpn-web volume data destination '/data'
set container name ovpn-web volume data source '/config/podman/openvpn/data'
set container name ovpn-web volume localtim destination '/etc/localtime'
set container name ovpn-web volume localtim mode 'ro'
set container name ovpn-web volume localtim source '/etc/localtime'
commit
save
- 允许容器ovpn-web使用主机网络
- 给容器ovpn-web添加网络原始套接字权限
- 给容器ovpn-web添加网络管理权限
- 给容器ovpn-web添加系统管理权限
- 限制容器ovpn-web使用1个CPU核心
- 将主机的tun设备映射到容器,路径为/dev/net/tun
- 指定tun设备的源路径为/dev/net/tun
- 设容器内管理员密码为admin
- 设容器内管理员用户名为admin
- 禁用容器配置自动更新
- 禁用容器作为OpenVPN网关
- 设容器主机名为ovpn-web
- 指定容器使用的镜像为d.yydy.link:2023/yyxx/openvpn:latest
- 限制容器内存使用为1024MB
- 设容器总是自动重启
- 分配128MB共享内存给容器
- 将主机的/config/podman/openvpn/data目录挂载到容器的/data目录
- 将主机的/etc/localtime文件挂载到容器的/etc/localtime
- 设置localtime挂载为只读模式
- 指定localtime的源路径为/etc/localtime
3.7、查看容器启动是否成功
run show container
3.8、查看端口占用
业务端口:udp1194;管理端口:8833
sudo ss -atunlp |grep openvpn

3.9、查看接口配置
run show interfaces

四、登录管理后台
默认账号密码:admin (可在上面的set中设定,不设定,后台只能改密码,不能改账号名。)


4.1、修改配置文件


修改以下参数,使得一个用户对应一个客户端证书,这样后期我们可以通过CCD控制客户端接收哪些路由信息(经测试,支持下发3685条明细路由),所以这里要注释掉。
log /data/openvpn.log
ifconfig-pool-persist /data/ipp.txt

修改后需要重启服务


4.2、创建客户端


4.3、CCD其他命令参考
4.3.1、核心基础配置(客户端身份与隧道段)
配置 |
说明 |
ifconfig-push 10.8.0.30 255.255.255.0 |
为客户端分配固定IPv4虚拟IP |
ifconfig-push-remote 10.8.0.1 |
强制指定客户端IPv4虚拟网卡的网关(服务器IP) |
ifconfig-ipv6-push 2001:db8:1::10 2001:db8:1::1 |
为客户端分配固定IPv6虚拟IP |
ifconfig-ipv6-push-remote 2001:db8:1::1 |
强制指定客户端IPv6虚拟网卡的网关(服务器IPv6) |
4.3.2、网络与路由配置(流量转发与访问范围)
4.3.2.1、 路由声明与推送
配置 |
说明 |
iroute 192.168.50.0 255.255.255.0 |
声明客户端身后的分支机构网段(类似full mesh),在指定客户端的CCD中配置,另外还需要在服务器上配置该客户端身后的分支机构网段全局路由下发给其他分支机构 |
push "route 192.168.20.0 255.255.255.0" |
向客户端推送IPv4路由(允许访问指定子网) |
push "route 192.168.20.0 255.255.255.0 net_gateway" |
向客户端推送IPv4路由,指定走本地网关 |
push "route 192.168.20.0 255.255.255.0 vpn_gateway" |
向客户端推送IPv4路由,指定走VPN隧道 |
push "route-ipv6 2001:db8:2::/64" |
向客户端推送IPv6路由(允许访问指定IPv6子网) |
push "allow-pull-fqdn" |
允许客户端接受服务器推送的域名形式路由 |
4.3.2.2、 路由优化与控制
配置 |
说明 |
push "route-delay 2 10" |
延迟路由添加(解决路由生效慢问题) |
push "route-noexec" |
仅推送路由信息,不自动添加到客户端路由表 |
4.3.2.3、隧道与MTU优化
配置 |
说明 |
tun-mtu-push 1400 |
调整TUN设备的MTU值(适配网络路径) |
mssfix-push 1300 |
调整TCP MSS值(减少分片问题) |
push "mtu-disc yes" |
启用客户端启用路径MTU发现(自动适配MTU) |
4.3.3、认证与安全配置(加密与身份验证)
4.3.3.1、加密与算法
配置 |
说明 |
push "cipher AES-256-GCM" |
指定客户端使用的加密算法 |
push "auth SHA512" |
指定客户端使用的认证算法 |
push "tls-version-min 1.2" |
限制客户端最低TLS版本(增强安全性) |
push "key-direction 1" |
指定TLS-auth密钥方向(与服务器匹配) |
4.3.3.2、证书与认证控制
配置 |
说明 |
push "remote-cert-tls client" |
要求客户端验证服务器证书(双向认证) |
push "client-cert-not-required" |
允许客户端无需证书,仅用密码认证 |
push "auth-nocache" |
客户端不缓存证书密码(增强安全性) |
push "password-retry 3" |
密码输入错误时的重试次数 |
4.3.4、连接管理配置(保活、重连与传输优化)
4.3.4.1、连接保活与检测
配置 |
说明 |
push "ping 10" |
客户端与服务器的心跳检测间隔(秒) |
push "ping-restart 60" |
心跳超时后重启连接的时间(秒) |
push "ping-timer-rem" |
由客户端主动发送心跳包(默认服务器主动) |
push "explicit-exit-notify 2" |
客户端断开时向服务器发送退出通知(重试次数) |
4.3.4.2、 连接稳定性优化
配置 |
说明 |
push "persist-tun" |
断开重连时保持TUN/TAP设备不关闭 |
push "persist-key" |
断开重连时保持私钥不重新加载 |
push "fast-io" |
启用快速I/O模式(提升传输性能) |
push "sndbuf 393216" |
调整客户端发送缓冲区大小(字节) |
push "rcvbuf 393216" |
调整客户端接收缓冲区大小(字节) |
4.3.4.3、接行为控制
配置 |
说明 |
push "client" |
显式指定客户端为“客户端模式” |
push "nobind" |
客户端不绑定固定本地端口(随机端口) |
push "bind" |
强制客户端绑定固定本地端口(与nobind互斥) |
push "remote-random" |
客户端随机选择remote列表中的服务器 |
push "remote-random-hostname" |
客户端随机解析remote中的域名(多IP负载均衡) |
push "socks-proxy 192.168.1.100 1080" |
客户端通过Socks代理连接VPN服务器 |
push "socks-proxy-retry" |
Socks代理不可用时自动重试 |
4.3.5、流量与访问控制(权限与转发策略)
配置 |
说明 |
push "redirect-gateway def1 bypass-dhcp" |
强制客户端全局流量走VPN |
push "block-outside-dns" |
禁止客户端使用VPN外的DNS(防止DNS泄露) |
push "client-to-client" |
允许该客户端与其他客户端直接通信 |
push "no-client-to-client" |
禁止该客户端与其他客户端通信(覆盖全局配置) |
4.3.6、DNS与名称解析(域名与地址解析)
配置 |
说明 |
push "dhcp-option DNS 8.8.8.8" |
为客户端指定DNS服务器 |
push "dhcp-option DOMAIN yydy.link" |
为客户端指定DNS搜索域 |
push "dhcp-option WINS 192.168.1.100" |
为Windows客户端指定WINS服务器 |
4.3.7、脚本与扩展配置(自动化与日志)
4.3.7.1、脚本执行控制
配置 |
说明 |
push "script-security 2" |
允许客户端执行用户定义的脚本 |
push "up /etc/openvpn/up.sh" |
客户端连接成功后执行的脚本 |
push "down /etc/openvpn/down.sh" |
客户端断开后执行的脚本 |
push "client-connect /etc/openvpn/connect.sh" |
客户端连接时触发的服务器端脚本 |
4.3.7.2、 日志与调试
配置 |
说明 |
push "verb 4" |
调整客户端日志详细程度(1-9,越大越详细) |
push "mute 10" |
限制重复日志输出次数(超过10次不再显示) |
push "status /var/log/openvpn-client.status" |
客户端将连接状态写入日志文件 |
4.3.8、自定义标识配置(环境变量与描述信息)
配置 |
说明 |
setenv FRIENDLY_NAME "VyOS OpenVPN" |
客户端显示名称(供管理工具识别) |
setenv DEPARTMENT "IT部门" |
客户端所属部门 |
setenv PURPOSE "远程办公-开发测试" |
客户端用途描述 |
setenv LOCATION "北京办公室" |
客户端物理位置 |
setenv CONTACT "张三" |
客户端负责人 |
setenv LANGUAGE "zh-CN" |
客户端UI显示语言 |
4.4、创建用户


五、用户首次使用
5.1、用户自主获取ovpn配置文件
用户如果在内网,通过浏览器打开http://192.168.1.195:8833,用户如果在外网,建议配置nginx发布https加密访问,其次在加一层访问过滤。


5.2、扫码获取动态TOTP令牌数字


5.3、连接登录

5.4、管理后台首页

5.5、历史记录

六、已知问题解决方案
6.1、mfa验证码错误

许多 MFA 系统使用基于时间的一次性密码(TOTP)协议,该协议依赖于客户端与服务器之间的时间同步。如果设备时间与服务器时间相差超过一定阈值,通常为 1 分钟,生成的验证码将被视为无效。
配置完成后,需要重启openvpn服务。
6.1.1、VyOS解决方案
set service ntp server ntp.aliyun.com
set service ntp server ntp.tencent.com
set service ntp server time.hicloud.com
set system time-zone 'Asia/Shanghai'
6.1.2、传统Linux解决方案
sudo apt update
sudo apt install ntpdate
sudo timedatectl set-timezone Asia/Shanghai
sudo timedatectl set-ntp true
sudo systemctl stop systemd-timesyncd.service
sudo ntpdate ntp.aliyun.com
sudo ntpdate ntp.tencent.com
sudo ntpdate time.hicloud.com
sudo systemctl start systemd-timesyncd.service
sudo systemctl enable systemd-timesyncd.service
timedatectl status
date