You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 

125 lines
4.0 KiB

import re
import httpx
import sys
import socket
import urllib.request
import json
domains = []
bad_stuns = {
r"stun[\d]{0,1}\.l\.google\.com": "Google"
}
badAsnDesc = [
"GOOGLE",
"AMAZON",
"CLOUDFLARE",
"MICROSOFT"
]
outputs = []
notAccessible = []
def checkStun(domain):
isAvailable = True
isBad = False
try:
page = httpx.get('https://' + domain + "/sdlkndflfdldhdfhdsofofbvcxbsd", timeout=30.0)
except httpx._exceptions.NetworkError as err:
isAvailable = False
sys.stderr.write(str(err) + "\n")
return isAvailable, isBad
if page.status_code != 200:
isAvailable = False
for (bad_stun, reason) in bad_stuns.items():
matches = re.findall("\n.*" + bad_stun, page.text)
for match in matches:
if "//" not in match:
isBad = True
break
return isAvailable, isBad
def getCountry(domain):
with urllib.request.urlopen("https://tools.keycdn.com/geo.json?host=" + domain) as url:
data = json.loads(url.read().decode())
if data['status'] == "success":
return data['data']['geo']['country_code']
else:
return "n.A."
def checkHoster(domain):
with urllib.request.urlopen("https://tools.keycdn.com/geo.json?host=" + domain) as url:
data = json.loads(url.read().decode())
if data['status'] == "success":
for asnDesc in badAsnDesc:
if data['data']['geo']['isp'].casefold().find(asnDesc.casefold()) != -1:
return True, data['data']['geo']['isp']
return False, data['data']['geo']['isp']
return False, "n.A."
def parseText(path):
f = open(path, "r")
char = f.read(1)
while char:
if char == "\"":
domain = ""
char = f.read(1)
while char != "\"":
domain = domain + char
char = f.read(1)
domains.append(domain)
char = f.read(1)
f.close()
def outputList(outputs):
for output in outputs:
if (not output['available']):
sys.stdout.write("[" + output['domain'] + "](https://" + output['domain'] + ") ")
else:
sys.stdout.write("[" + output['domain'] + "](https://" + output['domain'] + ") ")
sys.stdout.write(output['countryCode'] + " ")
sys.stdout.write("(" + output['hoster'] + ") ")
if not output['bad']:
sys.stdout.write("\u2705 ")
if output['hosterBad']:
sys.stdout.write("\u274c")
sys.stdout.write("\\\n")
def main():
if (len(sys.argv) <= 1):
sys.stderr.write("Please provide list with 'python3 main.py /path/to/list.txt'\n")
sys.exit(1)
else:
parseText(sys.argv[1])
domains.sort()
total = len(domains)
i = 0
for domain in domains:
sys.stderr.write(f"{i}/{total} done, ")
i = i + 1
sys.stderr.write("doing " + domain + " now\n")
available, bad = checkStun(domain)
hosterBad, hoster = checkHoster(domain)
if (not available):
sys.stderr.write(domain + " is unavailable\n")
output = {
"domain": domain,
"bad": bad,
"countryCode": getCountry(domain),
"available": available,
"hosterBad": hosterBad,
"hoster": hoster,
}
if available:
outputs.append(output)
else:
notAccessible.append(output)
sys.stdout.write("# Jitsi Instanzen\n")
outputList(sorted(outputs, key=lambda output: output['countryCode']))
sys.stdout.write("\n## Aktuell nicht erreichbar\n")
outputList(sorted(notAccessible, key=lambda output: output['countryCode']))
sys.stdout.write("\n# Legende\n")
sys.stdout.write("\u2705: Die Instanz nutzt nicht den Google STUN Server\n\n")
sys.stdout.write("\u274c: Die Instanz ist bei Google, Amazon, Cloudflare oder Microsoft gehostet")
if __name__ == '__main__':
main()