OpenConnect
OpenConnect 是一款免费开源的客户端到站点 VPN 软件。它允许您连接到各种商业的所谓 SSL VPN 服务器/网关/集中器,即
- Cisco AnyConnect anyconnect
- Palo Alto Networks (PAN) GlobalProtect gp
- Junos/Ivanti Pulse Secure pulse,另请参阅 Pulse Connect Secure
- Juniper Network Connect nc
- Fortinet fortinet
- F5 f5
- Array Networks array
安装
为了与 NetworkManager 集成,如果您使用像 GNOME 或 KDE 这样的 桌面环境,您可能需要 安装 networkmanager-openconnect 软件包。它将拉取 openconnect 软件包作为依赖项。如果您不需要集成,只需 安装 openconnect 软件包即可。
某些 VPN 被设置为拆分路由,因此也拆分 DNS。为了满足这一点,并且一般来说,建议使用 systemd-resolved 和 resolv.conf stub 模式。要验证是否是这种情况,请运行 resolvectl
并查找全局部分中 "resolv.conf mode: stub" 这一行。理解完整的输出可能非常有用,因此最好 研究 它。连接到 VPN 后,输出将大致如下所示
$ resolvectl
Global Protocols: -LLMNR -mDNS -DNSOverTLS DNSSEC=no/unsupported resolv.conf mode: stub Link 2 (enp1s0) Current Scopes: DNS Protocols: +DefaultRoute +LLMNR -mDNS -DNSOverTLS DNSSEC=no/unsupported Current DNS Server: 192.168.0.1 DNS Servers: 192.168.0.1 DNS Domain: ~home.box Link 3 (tun0) Current Scopes: DNS Protocols: -DefaultRoute +LLMNR -mDNS -DNSOverTLS DNSSEC=no/unsupported Current DNS Server: 10.10.10.10 DNS Servers: 10.10.10.10 DNS Domain: ~example.org ~int.example.net
用法
纯 OpenConnect
OpenConnect 有许多选项,请参阅 openconnect(8)。在最简单的情况下,您正在使用 Cisco AnyConnect VPN,因此您只需提供地址,然后在提示时输入您的用户名和密码。
$ sudo openconnect vpnserviceaddr
如果您使用 Cisco AnyConnect 以外的 VPN 类型,请添加 "--protocol" 选项,指定 nc、gp、pulse、f5、fortinet 或 array 之一
$ sudo openconnect --protocol=vpntype vpnserviceaddr
也可以提供用户名
$ sudo openconnect --protocol=vpntype -u user vpnserviceaddr
某些 VPN 为不同的访问配置提供不同的身份验证组,例如用于完整隧道或拆分隧道连接。要显示不同的提供的身份验证组并获取有关该服务的一般信息,请使用
$ sudo openconnect --protocol=vpntype --authenticate vpnserviceaddr
某些 VPN 在连接时需要收集有关您计算机的信息。在这种情况下,"--csd-wrapper" 选项可能会有所帮助。要使用和调整的脚本可以在 "/usr/lib/openconnect/" 下找到。
$ sudo openconnect --protocol=vpntype --csd-wrapper=script vpnserviceaddr
某些 VPN 将身份验证委派给身份提供商 (IdP),例如 Google、Microsoft AzureActiveDirectory 或 Okta。这种情况通常称为单点登录 (SSO),通常采用 SAML 2.0 标准或 OIDC 标准。过程如下:在浏览器或 webview 中,您打开 VPN 的 SSO 地址,该地址重定向到 IdP,IdP 将您发送回 VPN 页面,您最终会得到一个 cookie。cookie 必须使用 "-C,--cookie" 或 "--cookie-on-stdin" 选项传递给 openconnect。要从浏览器复制 cookie,请使用其开发者工具。
$ sudo openconnect --protocol=vpntype --cookie-on-stdin vpnserviceaddr
对于 Fortinet SSO VPN,您可以使用 openfortivpn-webview-qtAUR 来获取 cookie,而无需摆弄浏览器的开发者工具
$ sudo openconnect --protocol=fortinet -C "$(openfortivpn-webview vpnserviceaddr)" vpnserviceaddr
OpenConnect 将几个环境变量传递给脚本,以配置 IP 路由和 DNS 路由。默认情况下,它是 "/etc/vpnc/vpnc-script"。它支持一些您可以在需要时设置的环境变量,例如 "CISCO_SPLIT_DNS" 以将额外的 DNS 域添加到网络接口,除了 VPN 推送的域之外。
$ sudo CISCO_SPLIT_DNS=~internal.example.com,~10.in-addr.arpa openconnect --protocol=vpntype vpnserviceaddr
您可以使用您自己的脚本来代替默认脚本,使用 "-s,--script" 选项
$ sudo openconnect --protocol=vpntype -s script vpnserviceaddr
您还可以将 OpenConnect 与像 ocproxy-gitAUR 这样的代理结合使用,以进行 SSH 风格的端口转发。例如,如果您运行以下命令,则使用 rdesktop 连接到 localhost:13389 的连接将通过 VPN 转发到 RDS 服务 rds.int.example.net:3389
$ openconnect --protocol=vpntype --script-tun -s "ocproxy -L 13389:rds.int.example.net:3389" vpnserviceaddr $ rdesktop localhost:13389
使用 NetworkManager
NetworkManager 可以通过命令行界面 nmcli
、通过终端用户界面 nmtui
以及通过许多桌面环境进行控制,这要归功于其 D-Bus API。对于 NetworkManager 来说,VPN 只是另一种类型为 "vpn" 的连接。要使用 CLI 创建一个基于 OpenConnect 且名为 "MyOrgVPN" 的连接,请运行
$ nmcli connection add \ connection.id MyOrgVPN \ connection.type vpn \ vpn.service-type openconnect \ vpn.data cookie-flags=2,gateway=vpnserviceaddr,protocol=vpntype vpn.secrets gateway=vpnserviceaddr,gwcert=
在大多数情况下,使用 nmcli connection up MyOrgVPN
(即不带 --ask
)或 GNOME 右上角的菜单或 GNOME 设置(也称为控制中心)激活连接会按预期工作:会打开一个窗口并要求输入用户名、密码,以及可能的 2FA/MFA;即使 VPN 类型为 anyconnect 或 gp,SSO 场景通常也有效。对于其他桌面环境,您可能需要安装 network-manager-applet、nm-connection-editor 或其他一些软件包,以便控制 NetworkManager 连接。
然而,使用 nmcli --ask connection up MyOrgVPN
或 nmtui
或 nmtui connect MyOrgVPN
激活连接并不能像人们期望的那样工作:不是要求输入用户名等,而是要求输入 "Cookie (vpn.secrets.cookie)"。要提供它,您可以使用像这样的 Bash 脚本
~/vpn-up.bash
#!/usr/bin/bash connection_name=$(nmcli -t -g type,name connection \ | grep -Po '^vpn:\K.*' \ | sed 's/\\:/:/g' | fzf ) eval "$(nmcli -t -g vpn.data connection show "$connection_name" \ | grep -Po '(^|[ ,])(protocol|gateway)\ =\ [^,]*' \ | sed 's/ //g')" eval "$(openconnect --authenticate --protocol="$protocol" "$gateway")" nmcli connection up "$connection_name" \ passwd-file <(echo "vpn.secrets.cookie:$COOKIE")
要停用连接,请使用 nmcli connection down MyOrgVPN
或 nmtui
或 GNOME 右上角的菜单或 GNOME 设置(也称为控制中心)。
使用 WebAuth 和 Anyconnect 的单点登录 (SSO)
networkmanager-openconnect 支持使用 WebAuth 为 Cisco Anyconnect 进行单点登录 (SSO)。要使用 WebAuth
- 不要忘记为 networkmanager-openconnect 安装可选依赖项,例如 webkit2gtk-*
- 对于此连接,在 VPN 选项卡上的 “User Agent” 字段中添加类似 “AnyConnect Linux_64 4.10.07061” 的内容
激活连接。它应该为您弹出一个带有浏览器的窗口,用于完成 WebAuth。如果成功,networkmanager-openconnect 将启动 openconnect 并传递 “webvpn” cookie 以进行连接。
使用 netctl
一个简单的 tuntap
netctl.profile(5) 可以用于将 OpenConnect 集成到正常的 netctl 工作流程中。例如
/etc/netctl/vpn
Description='VPN' Interface=vpn Connection=tuntap Mode=tun #User=root #Group=root BindsToInterfaces=(enp0s25 wlp2s0) IP=no PIDFILE=/run/openconnect_${Interface}.pid SERVER=vpn.example.net AUTHGROUP='<AUTHGROUP>' LOCAL_USERNAME=<USERNAME> REMOTE_USERNAME=<VPN_USERNAME> # Assuming the use of pass(1): PASSWORD_CMD="su ${LOCAL_USERNAME} -c \"pass ${REMOTE_USERNAME} | head -n 1\"" ExecUpPost="${PASSWORD_CMD} | /usr/bin/openconnect --background --pid-file=${PIDFILE} --interface='${Interface}' --authgroup='${AUTHGROUP}' --user='${REMOTE_USERNAME}' --passwd-on-stdin ${SERVER}" ExecDownPre="kill -INT $(cat ${PIDFILE}) ; resolvconf -d ${Interface} ; ip link delete ${Interface}"
这允许像这样的执行
$ netctl start vpn $ netctl restart vpn $ netctl stop vpn
请注意,这依赖于 LOCAL_USERNAME
运行 gpg-agent,并且 PGP 密钥的密码已缓存。
如果需要 pass 的交互式查询,请为 PASSWORD_CMD
使用以下行
DISPLAY=":0" PASSWORD_CMD="su ${LOCAL_USERNAME} -c \"DISPLAY=${DISPLAY} pass ${REMOTE_USERNAME} | head -n 1\""
根据需要调整 DISPLAY
变量。
故障排除
Cisco AnyConnect
对于 Cisco AnyConnect VPN,如果您尝试使用 2FA/MFA,但它没有提示您输入密码,则需要将 useragent 设置为 AnyConnect ...
。这是 Cisco 的一个问题,这是 OpenConnect 项目中的 相关问题。