所以我正在编写一个脚本来自动登录 OpenVPN 连接,这需要
username
、password
和 Google Authenticator code
。
这是我到目前为止得到的命令(从我提供的
credential_file.txt
文件中读取的用户名和密码)
sudo openvpn --config /client.ovpn --auth-user-pass /credential_file.txt
内容如下
credential_file.txt
username
password
由于登录凭据也需要一次性 Google Authenticator OTP,因此使用上述命令登录肯定会失败。
连接日志
Fri Jan 14 14:33:20 2022 OpenVPN 2.3.10 x86_64-pc-linux-gnu [SSL (OpenSSL)] [LZO] [EPOLL] [PKCS11] [MH] [IPv6] built on Jan 9 2019
Fri Jan 14 14:33:20 2022 library versions: OpenSSL 1.0.2g 1 Mar 2016, LZO 2.08
Fri Jan 14 14:33:20 2022 WARNING: file '/credential_file.txt' is group or others accessible
Fri Jan 14 14:33:20 2022 Control Channel Authentication: tls-auth using INLINE static key file
Fri Jan 14 14:33:20 2022 Outgoing Control Channel Authentication: Using 160 bit message hash 'SHA1' for HMAC authentication
Fri Jan 14 14:33:20 2022 Incoming Control Channel Authentication: Using 160 bit message hash 'SHA1' for HMAC authentication
Fri Jan 14 14:33:20 2022 Socket Buffers: R=[131072->200000] S=[16384->200000]
Fri Jan 14 14:33:20 2022 Attempting to establish TCP connection with [AF_INET]xx.xxx.xxx.xxx:443 [nonblock]
Fri Jan 14 14:33:21 2022 TCP connection established with [AF_INET]xx.xxx.xxx.xxx:443
Fri Jan 14 14:33:21 2022 TCPv4_CLIENT link local: [undef]
Fri Jan 14 14:33:21 2022 TCPv4_CLIENT link remote: [AF_INET]xx.xxx.xxx.xxx:443
Fri Jan 14 14:33:21 2022 TLS: Initial packet from [AF_INET]xx.xxx.xxx.xxx:443, sid=5c312627 2ca5dddd
Fri Jan 14 14:33:21 2022 WARNING: this configuration may cache passwords in memory -- use the auth-nocache option to prevent this
Fri Jan 14 14:33:21 2022 VERIFY OK: depth=1, CN=OpenVPN CA
Fri Jan 14 14:33:21 2022 VERIFY OK: nsCertType=SERVER
Fri Jan 14 14:33:21 2022 VERIFY OK: depth=0, CN=OpenVPN Server
Fri Jan 14 14:33:22 2022 Data Channel Encrypt: Cipher 'AES-256-CBC' initialized with 256 bit key
Fri Jan 14 14:33:22 2022 Data Channel Encrypt: Using 160 bit message hash 'SHA1' for HMAC authentication
Fri Jan 14 14:33:22 2022 Data Channel Decrypt: Cipher 'AES-256-CBC' initialized with 256 bit key
Fri Jan 14 14:33:22 2022 Data Channel Decrypt: Using 160 bit message hash 'SHA1' for HMAC authentication
Fri Jan 14 14:33:22 2022 Control Channel: TLSv1.2, cipher TLSv1/SSLv3 xxxxx-xxx-xxxxx-xxx-xxxxx, 2048 bit RSA
Fri Jan 14 14:33:22 2022 [OpenVPN Server] Peer Connection Initiated with [AF_INET]xx.xxx.xxx.xxx:443
Fri Jan 14 14:33:24 2022 SENT CONTROL [OpenVPN Server]: 'PUSH_REQUEST' (status=1)
Fri Jan 14 14:33:24 2022 AUTH: Received control message: AUTH_FAILED,CRV1:R,E:nTsBKXl8QotPD+MvqjKoM9f9TII4SF8r:YW5kcm9pZF9jbGllbnQ=:Enter Google Authenticator Code
Fri Jan 14 14:33:24 2022 SIGTERM[soft,auth-failure] received, process exiting
有人可以告诉我如何将我的一次性 OTP(我已经在另一个 Python 脚本中拥有它,并准备好作为变量传递给上面的命令)以某种方式传递给上面的登录命令?
这里有一个类似/未回答的问题:https://security.stackexchange.com/questions/191517/openvpn-use-auth-user-pass-with-a-file-and-authenticator
谢谢
我们需要将
--auth-retry interact
作为附加选项传递给 openvpn
命令,以使其请求 TOTP 代码。
完整的命令如下所示
sudo openvpn \
--config /client.ovpn \
--auth-user-pass /credential_file.txt \
--auth-retry interact
正如 openvpn3-linux 存储库中的此讨论中所建议的,OTP 身份验证可以通过两种方式实现自动化:
expect
(讨论建议将此作为最后的手段)。欲了解更多详情,您可以查看这个答案。try:
r = b''
if input_slot.GetVariableName() == 'username':
r = b'your_username'
elif input_slot.GetVariableName() == 'password':
# call the necessary external-script to generate otp
my_opt_password = 'result_from_ext_script'
r = str.encode(my_opt_password)
else:
# this is the part which waits to get input from the user
r = subprocess.check_output(args)
print(r.decode('utf-8').strip())
input_slot.ProvideInput(r.decode('utf-8').strip())
# remaining code ...
将此脚本另存为
connect-vpn.py
。然后您可以将其运行为 python3 connect-vpn.py --start YOUR_CONFIG_NAME
来启动会话(并使用 --stop
标志来停止会话)。
注意:上面的
CONFIG_NAME
指的是您为配置文件设置的名称。该名称可以设置为 openvpn3 config-import -c /path/to/ovpn/file -n CONFIG_NAME