Automating Public IP Monitoring and Email Notifications in Windows

Automating Public IP Monitoring and Email Notifications in Windows

Functionality:

This solution monitors changes in your public IP address and automatically sends notifications to specified email addresses when changes occur. It's particularly useful for environments without dynamic DNS services or port forwarding configurations.

Prerequisites:

  • Python 3.x installed on your Windows system
  • requests library for Python
pip install requests

Required Files:

  • ip_history.txt - Stores the last known IP address
  • ip_monitor.py - Main script for IP monitoring and email notifications
  • run_monitor.bat - Batch script to execute the Python script

ip_history.txt Content:

Leave this file empty initially.

ip_monitor.py Content:

import smtplib
import ssl
import requests
import os
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from email.mime.base import MIMEBase
from email import encoders

def dispatch_notification(subject, message_body, recipients, sender_email, sender_password, mail_server, mail_port, file_attachment=None):
    """
    Compose and send an email notification with optional attachment
    """
    email_msg = MIMEMultipart()
    email_msg['From'] = sender_email
    email_msg['To'] = ', '.join(recipients)
    email_msg['Subject'] = subject
    email_msg.attach(MIMEText(message_body, 'plain'))
    
    if file_attachment:
        try:
            with open(file_attachment, 'rb') as attachment_file:
                email_part = MIMEBase('application', 'octet-stream')
                email_part.set_payload(attachment_file.read())
                encoders.encode_base64(email_part)
                email_part.add_header('Content-Disposition', f"attachment; filename= {os.path.basename(file_attachment)}")
                email_msg.attach(email_part)
        except Exception as attachment_error:
            print(f"Attachment failed: {attachment_error}")
    
    try:
        ssl_context = ssl.create_default_context()
        with smtplib.SMTP_SSL(mail_server, mail_port, context=ssl_context) as mail_client:
            mail_client.set_debuglevel(1)
            mail_client.login(sender_email, sender_password)
            email_text = email_msg.as_string()
            mail_client.sendmail(sender_email, recipients, email_text)
        print("Email notification dispatched successfully")
    except smtplib.SMTPAuthenticationError as auth_error:
        print(f"Authentication failure: {auth_error.smtp_code} - {auth_error.smtp_error}")
    except smtplib.SMTPException as mail_error:
        print(f"SMTP error: {mail_error}")
    except Exception as general_error:
        print(f"Notification dispatch failed: {general_error}")

def retrieve_external_ip():
    """
    Fetch the current external IP address from an online service
    """
    try:
        ip_response = requests.get('https://api.ipify.org?format=', timeout=10)
        ip_response.raise_for_status()
        ip_data = ip_response.()
        return ip_data.get('ip')
    except requests.RequestException as ip_error:
        print(f"IP retrieval error: {ip_error}")
        return None

def main():
    # Configuration parameters
    ip_storage_file = 'ip_history.txt'
    notification_subject = "External IP Address Change Detected"
    notification_body = "Your current external IP address is: "
    recipient_list = ["your_email@example.com", "backup@example.com"]  # Replace with actual email addresses
    sender_address = "your_sender@example.com"  # Replace with your email address
    sender_credentials = "your_email_password"  # Replace with your email password or app-specific password
    smtp_host = "smtp.example.com"  # Replace with your SMTP server
    smtp_port = 465  # Standard SSL port for SMTP
    attachment_file = None  # Set to file path if attachment is needed
    
    # Retrieve current external IP
    current_external_ip = retrieve_external_ip()
    
    if current_external_ip:
        try:
            with open(ip_storage_file, 'r', encoding='utf-8') as ip_file:
                previous_external_ip = ip_file.read().strip()
        except FileNotFoundError:
            previous_external_ip = ""
        
        if current_external_ip != previous_external_ip:
            print(f"IP address changed!\nPrevious IP: {previous_external_ip}\nCurrent IP: {current_external_ip}")
            
            # Prepare and send notification
            notification_details = notification_body + current_external_ip
            dispatch_notification(
                notification_subject,
                notification_details,
                recipient_list,
                sender_address,
                sender_credentials,
                smtp_host,
                smtp_port,
                attachment_file
            )
            
            # Update IP history file
            with open(ip_storage_file, 'w', encoding='utf-8') as ip_file:
                ip_file.write(current_external_ip)
        else:
            print("IP address unchanged")
    else:
        print("Failed to retrieve external IP address")

if __name__ == "__main__":
    main()

run_monitor.bat Content:

@echo off
cd /d C:\path\to\your\script\folder
python ip_monitor.py

Scheduling the Task:

To automate this script, create a scheduled task in Windows Task Scheduler that runs the run_monitor.bat file at regular intervals (e.g., every hour).

Tags: Windows python IP Monitoring Email Automation System Administration

Posted on Wed, 04 Nov 2026 16:33:18 +0000 by tomc_1