awk '{print $1}' /var/log/nginx/access.log | sort | uniq -c | sort -nr | head -10
Source: https://www.tecmint.com/find-top-ip-address-accessing-apache-web-server/
Get top /24 for ipv4
#!/usr/bin/env python3
"""
Find top /24 subnets from a file of IPv4 addresses (one per line).
Usage: python3 top_subnets.py <file> [--top N]
"""
import sys
import argparse
from collections import Counter
def get_24_subnet(ip: str) -> str | None:
parts = ip.strip().split(".")
if len(parts) != 4:
return None
try:
if all(0 <= int(p) <= 255 for p in parts):
return f"{parts[0]}.{parts[1]}.{parts[2]}.0/24"
except ValueError:
pass
return None
def main():
parser = argparse.ArgumentParser(description="Find top /24 subnets from a list of IPs.")
parser.add_argument("file", help="Path to the file (one IPv4 per line)")
parser.add_argument("--top", type=int, default=10, help="Number of top subnets to show (default: 10, 0 = all)")
args = parser.parse_args()
counter = Counter()
skipped = 0
with open(args.file) as f:
for line in f:
line = line.strip()
if not line or line.startswith("#"):
continue
subnet = get_24_subnet(line)
if subnet:
counter[subnet] += 1
else:
skipped += 1
total_ips = sum(counter.values())
top_n = args.top if args.top > 0 else len(counter)
results = counter.most_common(top_n)
print(f"{'Rank':<6} {'Subnet':<20} {'Count':>8} {'% of IPs':>10}")
print("-" * 50)
for rank, (subnet, count) in enumerate(results, 1):
pct = count / total_ips * 100
print(f"{rank:<6} {subnet:<20} {count:>8} {pct:>9.2f}%")
print("-" * 50)
print(f"Total unique /24 subnets : {len(counter)}")
print(f"Total valid IPs : {total_ips}")
if skipped:
print(f"Skipped (invalid lines) : {skipped}")
if __name__ == "__main__":
main()
Get top /20 for ipv6
THRESHOLD=10
# 1. Count uniques
sort acces.log | uniq -c > ips_count.txt
# 2. Create /20 blocks without strtonum()
awk -v t="$THRESHOLD" '{
count = $1
ip = $2
split(ip, h, ":")
h1 = h[1]
# Bash-style hex AND: printf + substr
cmd = "printf \"%x\" $((0x" h[2] " & 0xF0))"
cmd | getline h2_prefix
close(cmd)
block = h1 ":" h2_prefix "::/20"
blocks[block] += count
}
END {
for (b in blocks)
if (blocks[b] >= t)
print blocks[b], b
}' ips_count.txt | sort -nr | head -50
Leave a Reply