I wanted to share a setup I use to email me from my gmail account when someone connects and disconnects to/from my OpenVPN server that is running on my WNDRMACv2 using Gargoyle 1.6.X (built 06042014). The core scripts I copied from this link (http://linksysinfo.org/index.php?thread ... ons.36633/) and made some minor modifications so that they would work on Openwrt based firmware and the email notifications a little cleaner.
Prerequisites
- Router with at least 16MB of Flash storage (ex. WNDRMAC v2 or WNDR3700 v2)
- Gargoyle 1.6.X
- OpenVPN Server configured and working
- SSH Client such as Putty to configure
- [Optional] SCP Client for easier copying and backup
First, you must ssh into your router using your SSH client. Since I primarily use Windows 7, I prefer to use good ole Putty to accomplish this.
Once you've logged into your router using SSH, you must update the available packages for Gargyole using the following command:
Code: Select all
opkg update
Code: Select all
opkg install python
Code: Select all
opkg install python-openssl
Code: Select all
mkdir /root/scripts
/root/scripts/mail.py
Code: Select all
#!/bin/sh
import os
import smtplib
import mimetypes
from email.MIMEMultipart import MIMEMultipart
from email.MIMEBase import MIMEBase
from email.MIMEText import MIMEText
from email.MIMEAudio import MIMEAudio
from email.MIMEImage import MIMEImage
from email.Encoders import encode_base64
def sendMail(subject, text, *attachmentFilePaths):
gmailUser = 'yourgmailaccount@gmail.com'
gmailPassword = 'yourgmailpassword'
recipient = 'recipientaddress@whatever.com'
msg = MIMEMultipart()
msg['From'] = gmailUser
msg['To'] = recipient
msg['Subject'] = subject
msg.attach(MIMEText(text))
for attachmentFilePath in attachmentFilePaths:
msg.attach(getAttachment(attachmentFilePath))
mailServer = smtplib.SMTP('smtp.gmail.com', 587)
mailServer.ehlo()
mailServer.starttls()
mailServer.ehlo()
mailServer.login(gmailUser, gmailPassword)
mailServer.sendmail(gmailUser, recipient, msg.as_string())
mailServer.close()
print('Sent email to %s' % recipient)
def getAttachment(attachmentFilePath):
contentType, encoding = mimetypes.guess_type(attachmentFilePath)
if contentType is None or encoding is not None:
contentType = 'application/octet-stream'
mainType, subType = contentType.split('/', 1)
file = open(attachmentFilePath, 'rb')
if mainType == 'text':
attachment = MIMEText(file.read())
elif mainType == 'message':
attachment = email.message_from_file(file)
elif mainType == 'image':
attachment = MIMEImage(file.read(),_subType=subType)
elif mainType == 'audio':
attachment = MIMEAudio(file.read(),_subType=subType)
else:
attachment = MIMEBase(mainType, subType)
attachment.set_payload(file.read())
encode_base64(attachment)
file.close()
attachment.add_header('Content-Disposition', 'attachment', filename=os.path.basename(attachmentFilePath))
return attachment
yourgmailaccount@gmail.com to your own gmail account email address.
yourgmailpassword to your own gmail account password.
recipientaddress@whatever.com to the email address you'd like to send the notification to.
You can change the smtp.gmail.com information with another email provider if you want to use something other than gmail.
/root/scripts/client-connect.py
Code: Select all
#!/bin/sh
import datetime
import os
import socket
import mail
time = datetime.datetime.now()
formatted_time = time.strftime("%A, %B %d, %Y at %I:%M:%S %p")
name = os.environ['common_name']
localip = os.environ['ifconfig_pool_remote_ip']
remoteip = os.environ['untrusted_ip']
hostname = socket.getfqdn(remoteip)
subject = name + " has successfully connected via OPENVPN!"
message = formatted_time + "\r\n\r\nAn OpenVPN Client has connected.\r\n\r\nCommon Name: " + name + "\r\nRemote IP (DNS Name): " + remoteip + " (" + hostname + ") \r\nLocal IP: " + localip + "\r\n\r\n"
mail.sendMail(subject, message)
Code: Select all
#!/bin/sh
import datetime
import os
import socket
import mail
time = datetime.datetime.now()
formatted_time = time.strftime("%A, %B %d, %Y at %I:%M:%S %p")
name = os.environ['common_name']
localip = os.environ['ifconfig_pool_remote_ip']
remoteip = os.environ['untrusted_ip']
hostname = socket.getfqdn(remoteip)
bytesrec = os.environ['bytes_received']
bytessent = os.environ['bytes_sent']
duration = os.environ['time_duration']
subject = name + " has disconnected from OPENVPN!"
message = formatted_time + "\r\n\r\nAn OpenVPN Client has disconnected.\r\n\r\nCommon Name: " + name + "\r\nRemote IP (DNS Name): " + remoteip + " (" + hostname + ") \r\nLocal IP: " + localip + "\r\n\r\n" + "\r\nBytes sent: " + bytessent + "\r\nBytes received: " + bytesrec + "\r\nDuration: " + duration + " sec.\r\n\r\n"
mail.sendMail(subject, message)
Code: Select all
#!/bin/sh
python /root/scripts/client-connect.py
Code: Select all
#!/bin/sh
python /root/scripts/client-disconnect.py
Code: Select all
chmod 755 /root/scripts/mail.py
Code: Select all
chmod 755 /root/scripts/client-connect.py
Code: Select all
chmod 755 /root/scripts/client-disconnect.py
Code: Select all
chmod 755 /root/vpnconnect
Code: Select all
chmod 755 /root/vpndisconnect
/etc/config/openvpn/server.conf
Code: Select all
script-security 2
client-connect /root/vpnconnect
client-disconnect /root/vpndisconnect
Code: Select all
/etc/init.d/openvpn restart
The connect email will look like this:
Code: Select all
Friday, June 13, 2014 at 03:28:20 PM
An OpenVPN Client has connected.
Common Name: xxxxxxxxx
Remote IP (DNS Name): xxx.xxx.xxx.xxx (xxx.xxx.xxx.xxx)
Local IP: xxx.xxx.xxx.xxx
Code: Select all
Friday, June 06, 2014 at 10:00:31 PM
An OpenVPN Client has disconnected.
Common Name: xxxxxxx
Remote IP (DNS Name): xxx.xxx.xxx.xxx (xxx.xxx.xxx.xxx)
Local IP: xxx.xxx.xxx.xxx
Bytes sent: 7683
Bytes received: 6143
Duration: 379 sec.
Important Notes
Anytime you make a change to the OpenVPN setup via the Gargoyle gui, the server.conf modifications above will be removed. You will need to re-add the modifications above to re-enable these notices.
The configuration above is not automatically backed up or preserved via the Gargoyle backup process or when attempting to preserve the configuration during a firmware upgrade. I overcome this by using winscp to copy the setup from the root folder, perform a restore or upgrade, then copying the root folder back and performing the chmod steps above.
Enjoy!