Hey everyone! If you’re like me and spend way too much time tinkering with network gear—especially Cisco appliances—you know how handy it is to quickly check what’s open on a device without firing up a full-blown tool like Nmap. Today, I’m sharing a lightweight Python port scanner I whipped up for internal testing. It’s super simple, uses only built-in libraries, and is perfect for spotting those common ports like SSH (22), HTTP (80), or SNMP (161) on your lab setup.
This isn’t production-grade (no UDP, no fancy service versioning), but it’s fast, threaded for efficiency, and gets the job done for quick audits. Important: This is for ethical, internal use only—get permission before scanning anything!
Why Build This?
- No Dependencies: Runs on any Python 3.6+ setup—no installs needed.
- Customizable: Scan any range, tweak timeouts, and focus on Cisco-friendly ports.
- Interactive: Just input an IP and go.
I originally needed this to poke around a Cisco router in my home lab. Now, it’s yours to play with.
The Code
Here’s the full script. Save it as port_scanner.py
and run with python port_scanner.py
.
import socket
import threading
import sys
from concurrent.futures import ThreadPoolExecutor, as_completed
def scan_port(target, port):
"""
Scan a single port to check if it's open.
"""
try:
sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
sock.settimeout(1) # 1 second timeout
result = sock.connect_ex((target, port))
if result == 0:
print(f"Port {port}: Open")
# Optional: Try to identify service
try:
sock.close()
# You can add service detection here if needed, e.g., using socket.getservbyport
service = socket.getservbyport(port)
print(f" Service: {service}")
except OSError:
print(f" Service: Unknown")
sock.close()
except Exception as e:
pass # Silently ignore errors for speed
def port_scan(target, start_port=1, end_port=1024, max_workers=100):
"""
Perform a port scan on the target IP from start_port to end_port.
Uses threading for faster scanning.
"""
print(f"Scanning {target} from port {start_port} to {end_port}...")
open_ports = []
with ThreadPoolExecutor(max_workers=max_workers) as executor:
# Submit all port scan tasks
future_to_port = {
executor.submit(scan_port, target, port): port for port in range(start_port, end_port + 1)
}
# Collect results
for future in as_completed(future_to_port):
port = future_to_port[future]
try:
# The scan_port function prints directly, but we can collect if needed
pass
except Exception as exc:
print(f"Port {port} generated an exception: {exc}")
print("Scan completed.")
if __name__ == "__main__":
target_ip = input("Enter the target IP address: ").strip()
if not target_ip:
print("No IP provided. Exiting.")
sys.exit(1)
# Validate IP format (basic check)
try:
socket.inet_aton(target_ip)
except socket.error:
print("Invalid IP address format. Please enter a valid IPv4 address.")
sys.exit(1)
# For Cisco appliances, common ports to check: 22 (SSH), 23 (Telnet), 80 (HTTP), 443 (HTTPS), 161 (SNMP), etc.
# Scan top 1024 ports for a general scan, or customize the range
port_scan(target_ip, start_port=1, end_port=1024)
How to Use It
- Run the Script: Fire it up in your terminal. It’ll prompt for the IP (e.g.,
192.168.1.100
). - Watch the Magic: It scans ports 1-1024 by default, printing open ones with basic service names.
- Tweak for Cisco: Edit the
port_scan
call to narrow it down—trystart_port=1, end_port=1000
or just common ones like 22, 80, 443.
Sample Output (scanning a test device):
Enter the target IP address: 192.168.1.100
Scanning 192.168.1.100 from port 1 to 1024...
Port 22: Open
Service: ssh
Port 80: Open
Service: http
Port 443: Open
Service: https
Scan completed.
Pro Tip: For even faster runs on known ports, hardcode a list instead of a range.
Caveats and Next Steps
- Limitations: TCP-only, basic detection. For deeper dives, grab Nmap.
- Legal/Ethical Note: Only scan what you own or have explicit permission for. This could trip IDS/IPS.
- Enhance It: Add UDP support? Output to JSON? Fork it on GitHub and let me know!
If you’re into this stuff, check out my GitHub repo for the full project (with a shiny README): github.com/www-lazy-xyz/port-scanner. Drop a comment below—what’s your go-to tool for network recon?