0

I have a script that I would like to run only if VPN is up.

I can run a job via OpenVPN when the VPN starts up and shuts down, but I would like one job to run periodically when the VPN is up, and not at all when it is down.

What is the most elegant way to achieve this?

emk2203
  • 4,106
  • 1
  • 18
  • 46
  • Probably best to add the check to your script then exit the script if the VPN is not up. Cron will run regardless each time. – Terrance Mar 01 '17 at 18:44
  • Yes, I was thinking about that, but is there another way? The VPN is not up that often, and it seems unelegant to have a cron job which is aborted 99% of the time. – emk2203 Mar 01 '17 at 18:48
  • The cron will run the script at the specified time. In my opinion it is best to let the script exit if the VPN is down. `if [ ! VPN ]; then exit 1; fi` or something similar whatever it is you use as a check to see if your VPN is up or not. That way the cron job would not have to be aborted as it would actually complete the job. – Terrance Mar 01 '17 at 18:54
  • Is this more elegant? http://askubuntu.com/questions/28733/how-do-i-run-a-script-after-openvpn-has-connected-successfully – kukulo Mar 01 '17 at 19:27
  • 1
    When VPN comes up, add a job to /etc/cron.d. When VPN goes down, remove the job. Also needs a startup test to ensure the job doesn't survive an unexpected reboot. – user535733 Mar 01 '17 at 20:15
  • @user535733: I made your comment into an answer. It seems to be the best solution. – emk2203 Mar 05 '17 at 14:16

1 Answers1

1

Quick answer so the question has some closure:

The comment by @user535733 is the best way in my opinion. VPN is disabled at startup and started manually in this system, by systemd disable openvpn.

I have the following added to the vpn-up.sh script which is executed after the VPN starts by systemctl start openvpn:

#!/bin/bash

# Disable ipv6 to prevent leaks
echo 1 > /proc/sys/net/ipv6/conf/eth0/disable_ipv6

# Start services e.g. transmission
service transmission-daemon start

# Heredoc for crontab entry in /etc/cron.d
MINUTE=`date +%M`
tee /etc/cron.d/piaport <<-EOF >/dev/null
    # /etc/cron.d/piaport: crontab entries for pia-port script

    SHELL=/bin/sh
    PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin

    ${MINUTE} * * * * root /usr/local/bin/pia-port >> /var/log/piaport.log 2>&1
EOF

The script starts and generates a file piaport in /etc/cron.d which runs a script one hour after its generation, and again every hour afterwards.

The vpn-down.sh script which is run when the VPN service is stopped by systemctl stop openvpn:

#!/bin/sh

# Stop service like Transmission
service transmission-daemon stop

# Prevent DNS leaks 
/etc/openvpn/update-resolv-conf

# Reenable ipv6
echo 0 > /proc/sys/net/ipv6/conf/eth0/disable_ipv6

# Remove cronjob / heredoc
rm /etc/cron.d/piaport

For unexpected reboots, the script called by the cronjob checks for the existence of the VPN and deletes the cronjob /etc/cron.d/piaport if it was left over:

part of script:

# Check for tun0
tuncheck=$( { /sbin/ifconfig tun0; } 2>&1 )

tunnotfound="not found"
if [ "${tuncheck/$tunnotfound}" = "$tuncheck" ] ; then
  echo "- VPN tunnel appears to be up and connected (Good!)"
else
  echo "Error detected! tun0 does not exist."
  echo "Please make sure both internet and the VPN is connected!"
  echo ""
  echo "Then run this script again!"
  echo ""
  [[ -f /etc/cron.d/piaport ]] && rm -f /etc/cron.d/piaport
  exit

In total, the cronjob is only run when necessary, and when the VPN is up.

derHugo
  • 3,306
  • 5
  • 30
  • 49
emk2203
  • 4,106
  • 1
  • 18
  • 46