feat(cistech-tunnel): add auto-connect, menu flag, watchdog, fix host routing
- Auto-connect on startup (skip with -m/--menu flag) - Add VPN watchdog for auto-reconnect - Add live TOTP display - Fix host-routing.sh pipefail issue with grep - Better forwarding rules similar to rego-tunnel
This commit is contained in:
@@ -93,8 +93,8 @@ remove_all() {
|
|||||||
done
|
done
|
||||||
|
|
||||||
# Remove masquerade rule (using nft)
|
# Remove masquerade rule (using nft)
|
||||||
local handle
|
local handle=""
|
||||||
handle=$(nft -a list chain ip nat POSTROUTING 2>/dev/null | grep "saddr $LAN_SUBNET.*oifname.*$BRIDGE_NAME.*masquerade" | grep -oP 'handle \K\d+' | head -1)
|
handle=$(nft -a list chain ip nat POSTROUTING 2>/dev/null | grep "saddr $LAN_SUBNET.*oifname.*$BRIDGE_NAME.*masquerade" | grep -oP 'handle \K\d+' | head -1 || true)
|
||||||
if [ -n "$handle" ]; then
|
if [ -n "$handle" ]; then
|
||||||
nft delete rule ip nat POSTROUTING handle "$handle" 2>/dev/null || true
|
nft delete rule ip nat POSTROUTING handle "$handle" 2>/dev/null || true
|
||||||
fi
|
fi
|
||||||
|
|||||||
@@ -1,16 +1,24 @@
|
|||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
|
|
||||||
# OpenConnect-SSO VPN Connection Script
|
# Cistech VPN Connection Script with OpenConnect-SSO
|
||||||
# Usage: ./openconnect-vpn [-c|--connect] [-d|--disconnect] [-s|--status] [--setup-keyring] [--help]
|
# Usage: ./openconnect-vpn [-c|--connect] [-d|--disconnect] [-m|--menu] [-r|--routes] [-s|--status] [--help]
|
||||||
|
#
|
||||||
|
# Options:
|
||||||
|
# -c, --connect Connect to VPN and exit
|
||||||
|
# -d, --disconnect Disconnect VPN and exit
|
||||||
|
# -m, --menu Skip auto-connect, show menu directly
|
||||||
|
# -r, --routes Show routing table and exit
|
||||||
|
# -s, --status Show VPN status and exit
|
||||||
|
# --help Show this help message
|
||||||
|
|
||||||
# Credentials from environment variables (set by runtipi)
|
# Credentials from environment variables (set by runtipi)
|
||||||
VPN_EMAIL="${VPN_EMAIL:-}"
|
VPN_EMAIL="${VPN_EMAIL:-}"
|
||||||
VPN_PASSWORD="${VPN_PASSWORD:-}"
|
VPN_PASSWORD="${VPN_PASSWORD:-}"
|
||||||
VPN_TOTP_SECRET="${VPN_TOTP_SECRET:-}"
|
VPN_TOTP_SECRET="${VPN_TOTP_SECRET:-}"
|
||||||
VPN_HOST="${VPN_HOST:-}"
|
VPN_HOST="${VPN_HOST:-}"
|
||||||
TARGET_IP="${TARGET_IP:-}"
|
TARGET_IP="${TARGET_IP:-10.3.1.0}"
|
||||||
VPN_INTERFACE="${VPN_INTERFACE:-tun0}"
|
VPN_INTERFACE="${VPN_INTERFACE:-tun0}"
|
||||||
IBMI_HOST="10.3.1.201"
|
CONTAINER_NETWORK="172.30.0.0/24"
|
||||||
|
|
||||||
# Log directory
|
# Log directory
|
||||||
LOG_DIR="/var/log/openconnect-vpn"
|
LOG_DIR="/var/log/openconnect-vpn"
|
||||||
@@ -35,15 +43,15 @@ NC='\033[0m'
|
|||||||
|
|
||||||
print_banner() {
|
print_banner() {
|
||||||
echo -e "${CYAN}========================================${NC}"
|
echo -e "${CYAN}========================================${NC}"
|
||||||
echo -e "${CYAN} OpenConnect-SSO VPN Connection ${NC}"
|
echo -e "${CYAN} Cistech VPN Connection Script ${NC}"
|
||||||
echo -e "${CYAN}========================================${NC}"
|
echo -e "${CYAN}========================================${NC}"
|
||||||
echo ""
|
echo ""
|
||||||
}
|
}
|
||||||
|
|
||||||
# Flags
|
# Flags
|
||||||
|
SKIP_AUTO_CONNECT=false
|
||||||
DO_CONNECT=false
|
DO_CONNECT=false
|
||||||
DO_DISCONNECT=false
|
DO_DISCONNECT=false
|
||||||
DO_SETUP_KEYRING=false
|
|
||||||
|
|
||||||
# Logging
|
# Logging
|
||||||
log() {
|
log() {
|
||||||
@@ -61,6 +69,7 @@ log() {
|
|||||||
WARN) echo -e "${GRAY}[$timestamp_short]${NC} ${YELLOW}[WARN]${NC} $msg" ;;
|
WARN) echo -e "${GRAY}[$timestamp_short]${NC} ${YELLOW}[WARN]${NC} $msg" ;;
|
||||||
ERROR) echo -e "${GRAY}[$timestamp_short]${NC} ${RED}[ERROR]${NC} $msg" ;;
|
ERROR) echo -e "${GRAY}[$timestamp_short]${NC} ${RED}[ERROR]${NC} $msg" ;;
|
||||||
DEBUG) echo -e "${GRAY}[$timestamp_short]${NC} ${CYAN}[DEBUG]${NC} $msg" ;;
|
DEBUG) echo -e "${GRAY}[$timestamp_short]${NC} ${CYAN}[DEBUG]${NC} $msg" ;;
|
||||||
|
CMD) echo -e "${GRAY}[$timestamp_short]${NC} ${GRAY}[CMD]${NC} $msg" ;;
|
||||||
*) echo -e "${GRAY}[$timestamp_short]${NC} $msg" ;;
|
*) echo -e "${GRAY}[$timestamp_short]${NC} $msg" ;;
|
||||||
esac
|
esac
|
||||||
}
|
}
|
||||||
@@ -68,7 +77,7 @@ log() {
|
|||||||
run_cmd() {
|
run_cmd() {
|
||||||
local desc="$1"
|
local desc="$1"
|
||||||
shift
|
shift
|
||||||
log DEBUG "$desc: $*"
|
log CMD "$desc: $*"
|
||||||
output=$("$@" 2>&1)
|
output=$("$@" 2>&1)
|
||||||
local rc=$?
|
local rc=$?
|
||||||
if [ -n "$output" ]; then
|
if [ -n "$output" ]; then
|
||||||
@@ -79,12 +88,35 @@ run_cmd() {
|
|||||||
return $rc
|
return $rc
|
||||||
}
|
}
|
||||||
|
|
||||||
# Fetch server certificate fingerprint from VPN host
|
show_help() {
|
||||||
|
echo -e "${CYAN}Cistech VPN Connection Script${NC}"
|
||||||
|
echo ""
|
||||||
|
echo "Usage: $0 [OPTIONS]"
|
||||||
|
echo ""
|
||||||
|
echo "Options:"
|
||||||
|
echo " -c, --connect Connect to VPN and exit"
|
||||||
|
echo " -d, --disconnect Disconnect VPN and exit"
|
||||||
|
echo " -m, --menu Skip auto-connect, show menu directly"
|
||||||
|
echo " -r, --routes Show routing table and exit"
|
||||||
|
echo " -s, --status Show VPN status and exit"
|
||||||
|
echo " --help Show this help message"
|
||||||
|
echo ""
|
||||||
|
echo "Menu Options:"
|
||||||
|
echo " 1 - Connect VPN"
|
||||||
|
echo " 2 - Disconnect VPN"
|
||||||
|
echo " 3 - Show VPN status"
|
||||||
|
echo " 4 - Setup IP forwarding"
|
||||||
|
echo " 5 - Test connection"
|
||||||
|
echo " 6 - Show network status"
|
||||||
|
echo " 7 - Show routing table"
|
||||||
|
echo " 8 - Show live TOTP"
|
||||||
|
echo " q - Quit"
|
||||||
|
}
|
||||||
|
|
||||||
|
# Fetch server certificate fingerprint
|
||||||
get_server_cert() {
|
get_server_cert() {
|
||||||
local host="$1"
|
local host="$1"
|
||||||
# Strip protocol and path to get just hostname:port
|
|
||||||
local server=$(echo "$host" | sed -E 's|^https?://||; s|/.*$||')
|
local server=$(echo "$host" | sed -E 's|^https?://||; s|/.*$||')
|
||||||
# Add default port if not specified
|
|
||||||
[[ "$server" != *:* ]] && server="${server}:443"
|
[[ "$server" != *:* ]] && server="${server}:443"
|
||||||
|
|
||||||
log DEBUG "Fetching server certificate from $server..."
|
log DEBUG "Fetching server certificate from $server..."
|
||||||
@@ -103,7 +135,7 @@ get_server_cert() {
|
|||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
# Setup keyring with credentials for openconnect-sso
|
# Setup keyring with credentials
|
||||||
setup_keyring() {
|
setup_keyring() {
|
||||||
log INFO "Setting up keyring credentials..."
|
log INFO "Setting up keyring credentials..."
|
||||||
|
|
||||||
@@ -116,19 +148,16 @@ setup_keyring() {
|
|||||||
import keyring
|
import keyring
|
||||||
from keyrings.alt.file import PlaintextKeyring
|
from keyrings.alt.file import PlaintextKeyring
|
||||||
|
|
||||||
# Use plaintext keyring (works without desktop environment)
|
|
||||||
keyring.set_keyring(PlaintextKeyring())
|
keyring.set_keyring(PlaintextKeyring())
|
||||||
|
|
||||||
email = "$VPN_EMAIL"
|
email = "$VPN_EMAIL"
|
||||||
password = "$VPN_PASSWORD"
|
password = "$VPN_PASSWORD"
|
||||||
totp_secret = "$VPN_TOTP_SECRET"
|
totp_secret = "$VPN_TOTP_SECRET"
|
||||||
|
|
||||||
# Store password
|
|
||||||
if password:
|
if password:
|
||||||
keyring.set_password('openconnect-sso', email, password)
|
keyring.set_password('openconnect-sso', email, password)
|
||||||
print(f"Password stored in keyring for {email}")
|
print(f"Password stored in keyring for {email}")
|
||||||
|
|
||||||
# Store TOTP secret
|
|
||||||
if totp_secret:
|
if totp_secret:
|
||||||
keyring.set_password('openconnect-sso', f'totp/{email}', totp_secret.upper())
|
keyring.set_password('openconnect-sso', f'totp/{email}', totp_secret.upper())
|
||||||
print(f"TOTP secret stored in keyring for {email}")
|
print(f"TOTP secret stored in keyring for {email}")
|
||||||
@@ -144,27 +173,19 @@ PYTHON
|
|||||||
fi
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
show_help() {
|
get_totp() {
|
||||||
echo -e "${CYAN}OpenConnect-SSO VPN Connection Script${NC}"
|
oathtool --totp -b "$VPN_TOTP_SECRET"
|
||||||
|
}
|
||||||
|
|
||||||
|
show_totp() {
|
||||||
|
log INFO "Starting live TOTP display (Ctrl+C to stop)"
|
||||||
echo ""
|
echo ""
|
||||||
echo "Usage: $0 [OPTIONS]"
|
while true; do
|
||||||
echo ""
|
TOTP=$(get_totp)
|
||||||
echo "Options:"
|
SECONDS_LEFT=$((30 - ($(date +%s) % 30)))
|
||||||
echo " -c, --connect Connect to VPN"
|
echo -ne "\r ${CYAN}Current TOTP:${NC} ${GREEN}$TOTP${NC} (expires in ${YELLOW}${SECONDS_LEFT}s${NC}) "
|
||||||
echo " -d, --disconnect Disconnect from VPN"
|
sleep 1
|
||||||
echo " -s, --status Show VPN status"
|
done
|
||||||
echo " -r, --routes Show routing table"
|
|
||||||
echo " --setup-keyring Setup keyring credentials only"
|
|
||||||
echo " --help Show this help message"
|
|
||||||
echo ""
|
|
||||||
echo "Environment Variables:"
|
|
||||||
echo " VPN_EMAIL Email/username for SSO"
|
|
||||||
echo " VPN_PASSWORD Password for SSO"
|
|
||||||
echo " VPN_TOTP_SECRET TOTP secret for 2FA"
|
|
||||||
echo " VPN_HOST VPN server hostname"
|
|
||||||
echo " TARGET_IP Target IP for connectivity test"
|
|
||||||
echo " VPN_INTERFACE TUN interface name (default: tun0)"
|
|
||||||
echo " IBM_HOST IBM i Host"
|
|
||||||
}
|
}
|
||||||
|
|
||||||
get_vpn_interface() {
|
get_vpn_interface() {
|
||||||
@@ -295,7 +316,7 @@ disconnect_vpn() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
setup_forwarding() {
|
setup_forwarding() {
|
||||||
log INFO "Setting up IP forwarding rules..."
|
log INFO "Setting up IP forwarding rules for $TARGET_IP..."
|
||||||
|
|
||||||
local vpn_iface=$(get_vpn_interface)
|
local vpn_iface=$(get_vpn_interface)
|
||||||
if [ -z "$vpn_iface" ]; then
|
if [ -z "$vpn_iface" ]; then
|
||||||
@@ -310,19 +331,42 @@ setup_forwarding() {
|
|||||||
log DEBUG "VPN IP: $vpn_ip"
|
log DEBUG "VPN IP: $vpn_ip"
|
||||||
log DEBUG "Container IP: $container_ip"
|
log DEBUG "Container IP: $container_ip"
|
||||||
|
|
||||||
|
# Enable IP forwarding
|
||||||
run_cmd "Enabling IP forwarding" sysctl -w net.ipv4.ip_forward=1
|
run_cmd "Enabling IP forwarding" sysctl -w net.ipv4.ip_forward=1
|
||||||
|
|
||||||
# NAT masquerade for container network
|
# NAT masquerade for container network going through VPN
|
||||||
if ! iptables -t nat -C POSTROUTING -o "$vpn_iface" -j MASQUERADE 2>/dev/null; then
|
if ! iptables -t nat -C POSTROUTING -s "$CONTAINER_NETWORK" -o "$vpn_iface" -j MASQUERADE 2>/dev/null; then
|
||||||
run_cmd "Adding NAT masquerade" iptables -t nat -A POSTROUTING -o "$vpn_iface" -j MASQUERADE
|
run_cmd "Adding NAT masquerade for container network -> VPN" iptables -t nat -A POSTROUTING -s "$CONTAINER_NETWORK" -o "$vpn_iface" -j MASQUERADE
|
||||||
|
else
|
||||||
|
log DEBUG "NAT masquerade for container network already exists"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
# Forward rules at position 1
|
||||||
|
iptables -D FORWARD -d "$TARGET_IP" -j ACCEPT 2>/dev/null || true
|
||||||
|
iptables -D FORWARD -s "$TARGET_IP" -j ACCEPT 2>/dev/null || true
|
||||||
|
iptables -D FORWARD -s "$CONTAINER_NETWORK" -j ACCEPT 2>/dev/null || true
|
||||||
|
iptables -D FORWARD -d "$CONTAINER_NETWORK" -j ACCEPT 2>/dev/null || true
|
||||||
|
|
||||||
|
run_cmd "Inserting forward rule (to container network)" iptables -I FORWARD 1 -d "$CONTAINER_NETWORK" -j ACCEPT
|
||||||
|
run_cmd "Inserting forward rule (from container network)" iptables -I FORWARD 1 -s "$CONTAINER_NETWORK" -j ACCEPT
|
||||||
|
run_cmd "Inserting forward rule (from target)" iptables -I FORWARD 1 -s "$TARGET_IP" -j ACCEPT
|
||||||
|
run_cmd "Inserting forward rule (to target)" iptables -I FORWARD 1 -d "$TARGET_IP" -j ACCEPT
|
||||||
|
|
||||||
log INFO "Forwarding rules configured"
|
log INFO "Forwarding rules configured"
|
||||||
|
echo ""
|
||||||
|
|
||||||
# Trigger host routing service restart if available
|
# Trigger host routing service restart
|
||||||
if [ -d /runtime ]; then
|
log INFO "Triggering host routing service restart..."
|
||||||
touch /runtime/restart-routing 2>/dev/null || true
|
touch /runtime/restart-routing 2>/dev/null || true
|
||||||
|
sleep 2
|
||||||
|
if [ ! -f /runtime/restart-routing ]; then
|
||||||
|
log INFO "Host routing service restarted"
|
||||||
|
else
|
||||||
|
log WARN "Host watcher may not be running (trigger file still exists)"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
log INFO "Routing configured for $TARGET_IP through VPN tunnel"
|
||||||
|
echo ""
|
||||||
}
|
}
|
||||||
|
|
||||||
connect_vpn() {
|
connect_vpn() {
|
||||||
@@ -341,6 +385,13 @@ connect_vpn() {
|
|||||||
# Setup keyring credentials
|
# Setup keyring credentials
|
||||||
setup_keyring
|
setup_keyring
|
||||||
|
|
||||||
|
# Fetch server certificate
|
||||||
|
log INFO "Fetching server certificate..."
|
||||||
|
local servercert=$(get_server_cert "$VPN_HOST")
|
||||||
|
|
||||||
|
log INFO "Connecting to: $VPN_HOST"
|
||||||
|
log DEBUG "Interface: $VPN_INTERFACE"
|
||||||
|
|
||||||
# Build openconnect-sso command
|
# Build openconnect-sso command
|
||||||
local sso_args=()
|
local sso_args=()
|
||||||
sso_args+=("-s" "$VPN_HOST")
|
sso_args+=("-s" "$VPN_HOST")
|
||||||
@@ -349,12 +400,9 @@ connect_vpn() {
|
|||||||
sso_args+=("-u" "$VPN_EMAIL")
|
sso_args+=("-u" "$VPN_EMAIL")
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
# Use hidden browser for automated login
|
||||||
sso_args+=("--browser-display-mode" "hidden")
|
sso_args+=("--browser-display-mode" "hidden")
|
||||||
|
|
||||||
# Fetch server certificate
|
|
||||||
log INFO "Fetching server certificate..."
|
|
||||||
local servercert=$(get_server_cert "$VPN_HOST")
|
|
||||||
|
|
||||||
# Build openconnect args
|
# Build openconnect args
|
||||||
local oc_args=()
|
local oc_args=()
|
||||||
oc_args+=("--protocol=anyconnect")
|
oc_args+=("--protocol=anyconnect")
|
||||||
@@ -366,12 +414,9 @@ connect_vpn() {
|
|||||||
log DEBUG "Server cert: $servercert"
|
log DEBUG "Server cert: $servercert"
|
||||||
fi
|
fi
|
||||||
|
|
||||||
log INFO "Connecting to: $VPN_HOST"
|
|
||||||
log DEBUG "Interface: $VPN_INTERFACE"
|
|
||||||
|
|
||||||
# Launch openconnect-sso
|
# Launch openconnect-sso
|
||||||
log INFO "Launching openconnect-sso..."
|
log INFO "Launching openconnect-sso..."
|
||||||
openconnect-sso "${sso_args[@]}" -- /usr/sbin/openconnect "${oc_args[@]}" &
|
openconnect-sso "${sso_args[@]}" -- sudo /usr/sbin/openconnect "${oc_args[@]}" &
|
||||||
OC_PID=$!
|
OC_PID=$!
|
||||||
disown $OC_PID
|
disown $OC_PID
|
||||||
log DEBUG "openconnect-sso started with PID $OC_PID"
|
log DEBUG "openconnect-sso started with PID $OC_PID"
|
||||||
@@ -399,34 +444,95 @@ connect_vpn() {
|
|||||||
log DEBUG " Interface: $vpn_iface"
|
log DEBUG " Interface: $vpn_iface"
|
||||||
log DEBUG " VPN IP: $vpn_ip"
|
log DEBUG " VPN IP: $vpn_ip"
|
||||||
|
|
||||||
|
# Wait for routes to stabilize
|
||||||
|
log DEBUG "Waiting for routes to stabilize..."
|
||||||
sleep 3
|
sleep 3
|
||||||
|
|
||||||
|
# Setup forwarding
|
||||||
setup_forwarding
|
setup_forwarding
|
||||||
|
|
||||||
# Test connection if TARGET_IP is set
|
# Test connection
|
||||||
if [[ -n "$IBMI_HOST" ]]; then
|
if [[ -n "$TARGET_IP" ]]; then
|
||||||
log INFO "Testing connection to $IBMI_HOST..."
|
log INFO "Testing connection to $TARGET_IP..."
|
||||||
if ping -c 2 -W 3 "$IBMI_HOST" &>/dev/null; then
|
if ping -c 2 -W 3 "$TARGET_IP" &>/dev/null; then
|
||||||
log INFO "Connection test: ${GREEN}SUCCESS${NC}"
|
log INFO "Connection test: ${GREEN}SUCCESS${NC}"
|
||||||
else
|
else
|
||||||
log WARN "Connection test: ${RED}FAILED${NC}"
|
log WARN "Connection test: ${RED}FAILED${NC} (may need manual route on host)"
|
||||||
fi
|
fi
|
||||||
fi
|
fi
|
||||||
|
|
||||||
|
# Disable screen blanking
|
||||||
|
xset s off 2>/dev/null || true
|
||||||
|
xset -dpms 2>/dev/null || true
|
||||||
|
xset s noblank 2>/dev/null || true
|
||||||
|
log DEBUG "Screen blanking disabled"
|
||||||
|
|
||||||
log INFO "VPN setup complete"
|
log INFO "VPN setup complete"
|
||||||
|
|
||||||
|
# Start watchdog in background
|
||||||
|
start_watchdog &
|
||||||
|
WATCHDOG_PID=$!
|
||||||
|
log DEBUG "Watchdog started with PID $WATCHDOG_PID"
|
||||||
|
|
||||||
return 0
|
return 0
|
||||||
}
|
}
|
||||||
|
|
||||||
|
# Watchdog - monitors VPN and reconnects if dropped
|
||||||
|
start_watchdog() {
|
||||||
|
log INFO "Starting VPN watchdog (check every 60s, keepalive ping every 5min)..."
|
||||||
|
|
||||||
|
local check_interval=60
|
||||||
|
local keepalive_interval=300
|
||||||
|
local last_keepalive=0
|
||||||
|
local reconnect_attempts=0
|
||||||
|
local max_reconnect_attempts=3
|
||||||
|
|
||||||
|
while true; do
|
||||||
|
sleep $check_interval
|
||||||
|
|
||||||
|
local now=$(date +%s)
|
||||||
|
local vpn_iface=$(get_vpn_interface)
|
||||||
|
|
||||||
|
if [ -n "$vpn_iface" ]; then
|
||||||
|
# VPN is up
|
||||||
|
reconnect_attempts=0
|
||||||
|
|
||||||
|
# Keepalive ping every 5 minutes
|
||||||
|
if [ $((now - last_keepalive)) -ge $keepalive_interval ]; then
|
||||||
|
if [[ -n "$TARGET_IP" ]] && ping -c 1 -W 5 "$TARGET_IP" &>/dev/null; then
|
||||||
|
log DEBUG "Keepalive ping to $TARGET_IP successful"
|
||||||
|
else
|
||||||
|
log WARN "Keepalive ping to $TARGET_IP failed (VPN may be degraded)"
|
||||||
|
fi
|
||||||
|
last_keepalive=$now
|
||||||
|
fi
|
||||||
|
else
|
||||||
|
# VPN is down
|
||||||
|
((reconnect_attempts++))
|
||||||
|
log WARN "VPN disconnected! Reconnect attempt $reconnect_attempts/$max_reconnect_attempts..."
|
||||||
|
|
||||||
|
if [ $reconnect_attempts -le $max_reconnect_attempts ]; then
|
||||||
|
connect_vpn
|
||||||
|
else
|
||||||
|
log ERROR "Max reconnect attempts reached. Manual intervention required."
|
||||||
|
sleep 300
|
||||||
|
reconnect_attempts=0
|
||||||
|
fi
|
||||||
|
fi
|
||||||
|
done
|
||||||
|
}
|
||||||
|
|
||||||
# Main menu
|
# Main menu
|
||||||
main_menu() {
|
main_menu() {
|
||||||
echo -e "${GREEN}Options:${NC}"
|
echo -e "${GREEN}Options:${NC}"
|
||||||
echo -e " ${CYAN}1${NC} - Connect VPN"
|
echo -e " ${CYAN}1${NC} - Connect VPN"
|
||||||
echo -e " ${CYAN}2${NC} - Disconnect VPN"
|
echo -e " ${CYAN}2${NC} - Disconnect VPN"
|
||||||
echo -e " ${CYAN}3${NC} - Show VPN status"
|
echo -e " ${CYAN}3${NC} - Show VPN status"
|
||||||
echo -e " ${CYAN}4${NC} - Setup IP forwarding"
|
echo -e " ${CYAN}4${NC} - Setup IP forwarding only"
|
||||||
echo -e " ${CYAN}5${NC} - Test connection"
|
echo -e " ${CYAN}5${NC} - Test connection to $TARGET_IP"
|
||||||
echo -e " ${CYAN}6${NC} - Show network status"
|
echo -e " ${CYAN}6${NC} - Show network status"
|
||||||
echo -e " ${CYAN}7${NC} - Show routing table"
|
echo -e " ${CYAN}7${NC} - Show routing table"
|
||||||
echo -e " ${CYAN}8${NC} - Setup keyring"
|
echo -e " ${CYAN}8${NC} - Show live TOTP"
|
||||||
echo -e " ${CYAN}q${NC} - Quit"
|
echo -e " ${CYAN}q${NC} - Quit"
|
||||||
echo ""
|
echo ""
|
||||||
}
|
}
|
||||||
@@ -442,6 +548,10 @@ parse_args() {
|
|||||||
DO_DISCONNECT=true
|
DO_DISCONNECT=true
|
||||||
shift
|
shift
|
||||||
;;
|
;;
|
||||||
|
-m|--menu)
|
||||||
|
SKIP_AUTO_CONNECT=true
|
||||||
|
shift
|
||||||
|
;;
|
||||||
-s|--status)
|
-s|--status)
|
||||||
print_banner
|
print_banner
|
||||||
check_vpn_status
|
check_vpn_status
|
||||||
@@ -453,10 +563,6 @@ parse_args() {
|
|||||||
show_routes
|
show_routes
|
||||||
exit 0
|
exit 0
|
||||||
;;
|
;;
|
||||||
--setup-keyring)
|
|
||||||
DO_SETUP_KEYRING=true
|
|
||||||
shift
|
|
||||||
;;
|
|
||||||
--help)
|
--help)
|
||||||
show_help
|
show_help
|
||||||
exit 0
|
exit 0
|
||||||
@@ -468,6 +574,11 @@ parse_args() {
|
|||||||
;;
|
;;
|
||||||
esac
|
esac
|
||||||
done
|
done
|
||||||
|
|
||||||
|
if [ "$DO_CONNECT" = "true" ] && [ "$DO_DISCONNECT" = "true" ]; then
|
||||||
|
echo "Error: --connect and --disconnect are mutually exclusive"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
}
|
}
|
||||||
|
|
||||||
# Main
|
# Main
|
||||||
@@ -476,7 +587,8 @@ cleanup_old_logs
|
|||||||
|
|
||||||
echo "" >> "$(get_log_file)"
|
echo "" >> "$(get_log_file)"
|
||||||
echo "========================================" >> "$(get_log_file)"
|
echo "========================================" >> "$(get_log_file)"
|
||||||
log INFO "openconnect-vpn script started"
|
log INFO "=== Starting OpenConnect-SSO VPN ==="
|
||||||
|
echo ""
|
||||||
log DEBUG "VPN_EMAIL=$VPN_EMAIL"
|
log DEBUG "VPN_EMAIL=$VPN_EMAIL"
|
||||||
log DEBUG "VPN_HOST=$VPN_HOST"
|
log DEBUG "VPN_HOST=$VPN_HOST"
|
||||||
log DEBUG "TARGET_IP=$TARGET_IP"
|
log DEBUG "TARGET_IP=$TARGET_IP"
|
||||||
@@ -484,11 +596,6 @@ log DEBUG "VPN_TOTP_SECRET is $([ -n "$VPN_TOTP_SECRET" ] && echo 'set' || echo
|
|||||||
|
|
||||||
print_banner
|
print_banner
|
||||||
|
|
||||||
if [ "$DO_SETUP_KEYRING" = "true" ]; then
|
|
||||||
setup_keyring
|
|
||||||
exit $?
|
|
||||||
fi
|
|
||||||
|
|
||||||
if [ "$DO_DISCONNECT" = "true" ]; then
|
if [ "$DO_DISCONNECT" = "true" ]; then
|
||||||
disconnect_vpn
|
disconnect_vpn
|
||||||
exit $?
|
exit $?
|
||||||
@@ -499,7 +606,21 @@ if [ "$DO_CONNECT" = "true" ]; then
|
|||||||
exit $?
|
exit $?
|
||||||
fi
|
fi
|
||||||
|
|
||||||
# Interactive menu mode
|
# Auto-connect logic (unless -m flag)
|
||||||
|
if [ "$SKIP_AUTO_CONNECT" = "true" ]; then
|
||||||
|
log INFO "Menu mode - skipping auto-connect"
|
||||||
|
elif check_vpn_status; then
|
||||||
|
echo ""
|
||||||
|
log INFO "VPN already connected. Setting up forwarding..."
|
||||||
|
setup_forwarding
|
||||||
|
else
|
||||||
|
echo ""
|
||||||
|
log INFO "Auto-starting VPN connection..."
|
||||||
|
echo ""
|
||||||
|
connect_vpn
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Interactive menu loop
|
||||||
while true; do
|
while true; do
|
||||||
echo ""
|
echo ""
|
||||||
main_menu
|
main_menu
|
||||||
@@ -514,15 +635,15 @@ while true; do
|
|||||||
2) disconnect_vpn ;;
|
2) disconnect_vpn ;;
|
||||||
3) check_vpn_status ;;
|
3) check_vpn_status ;;
|
||||||
4) setup_forwarding ;;
|
4) setup_forwarding ;;
|
||||||
5) if [[ -n "$IBMI_HOST" ]]; then
|
5) if [[ -n "$TARGET_IP" ]]; then
|
||||||
log INFO "Testing connection to $IBMI_HOST..."
|
log INFO "Testing connection to $TARGET_IP..."
|
||||||
ping -c 3 "$IBMI_HOST" && log INFO "Connection test: ${GREEN}SUCCESS${NC}" || log ERROR "Connection test: ${RED}FAILED${NC}"
|
ping -c 3 "$TARGET_IP" && log INFO "Connection test: ${GREEN}SUCCESS${NC}" || log ERROR "Connection test: ${RED}FAILED${NC}"
|
||||||
else
|
else
|
||||||
log WARN "IBMI_HOST not set"
|
log WARN "TARGET_IP not set"
|
||||||
fi ;;
|
fi ;;
|
||||||
6) show_network_status ;;
|
6) show_network_status ;;
|
||||||
7) show_routes ;;
|
7) show_routes ;;
|
||||||
8) setup_keyring ;;
|
8) show_totp ;;
|
||||||
q|Q) log INFO "Goodbye!"; exit 0 ;;
|
q|Q) log INFO "Goodbye!"; exit 0 ;;
|
||||||
*) ;;
|
*) ;;
|
||||||
esac
|
esac
|
||||||
|
|||||||
Reference in New Issue
Block a user