python编写https代理服务_Http/Https代理Python实现

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

对Python感兴趣,工作之余,参照部分文档初步实现了HTTP/HTTPs代理。(代码比较凌乱,各位留情。

laugh.gif)

使用Fiddler调试。

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~import socket

import time

import threading

BUFSIZE=1024

class Access_to_Host(object):

def handler(self,conn,addr):

self.conn=conn

self.addr=addr

all_src_data,hostname,port,ssl_flag=self.get_dst_host_from_header(self.conn,self.addr)

all_dst_data=self.get_data_from_host(hostname,port,all_src_data,ssl_flag)

if all_dst_data and not ssl_flag:

#self.send_data_to_client(self.conn,all_dst_data)

self.ssl_client_server_client(self.conn,self.conn_dst,all_dst_data)

elif ssl_flag:

sample_data_to_client=b"HTTP/1.0 200 Connection Established\r\n\r\n"

# print("\nSSL_Flag-1")

#self.send_data_to_client(self.conn,all_dst_data)

#print("SSL_Flag-2")

self.ssl_client_server_client(self.conn,self.conn_dst,sample_data_to_client)

#print("\nSSL_Flag-3")

else:

print('pls check network. cannot get hostname:'+hostname)

#self.conn.close()

def ssl_client_server(self,src_conn,dst_conn):

self.src_conn=src_conn

self.dst_conn=dst_conn

while True:

###get data from client

try:

ssl_client_data=self.src_conn.recv(BUFSIZE)

except Exception as e:

print("client disconnct ")

print(e)

self.src_conn.close()

#self.dst_conn.close()

return False

if ssl_client_data:

#####send data to server

try:

self.dst_conn.sendall(ssl_client_data)

except Exception as e:

print("server disconnct Err")

self.dst_conn.close()

return False

else:

self.src_conn.close()

return False

def ssl_server_client(self,src_conn,dst_conn):

self.src_conn=src_conn

self.dst_conn=dst_conn

while True:

###get data from server

try:

ssl_server_data=self.dst_conn.recv(BUFSIZE)

except Exception as e:

print("server disconnct ")

self.dst_conn.close()

return False

if ssl_server_data:

#####send data to client

try:

self.src_conn.sendall(ssl_server_data)

except Exception as e:

print("Client disconnct Err")

self.src_conn.close()

return False

else:

self.dst_conn.close()

return False

def ssl_client_server_client(self,src_conn,dst_conn,all_dst_data):

self.src_conn=src_conn

self.dst_conn=dst_conn

try:

#print(all_dst_data)

self.src_conn.sendall(all_dst_data)

except Exception as e:

print(e)

print("cannot sent data(HTTP/1.0 200) to SSL client")

return False

threadlist=[]

t1=threading.Thread(target=self.ssl_client_server,args=(self.src_conn,self.dst_conn))

t2=threading.Thread(target=self.ssl_server_client,args=(self.src_conn,self.dst_conn))

threadlist.append(t1)

threadlist.append(t2)

for t in threadlist:

t.start()

#t.join()

######线程控制,等待线程结束后,远程主机关闭socket后,客户端到主机的socket也不需要再做任何操作了。

while not self.dst_conn._closed:

time.sleep(1)

self.src_conn.close()

def get_src_client(self):

self.src_ip=self.s_src.getpeername()

return self.src_ip

def send_data_to_client(self,conn_src,data):

self.conn_src=conn_src

try:

self.conn_src.sendall(data)

except Exception as e:

print(e)

print("cannot sent data to client")

return False

#self.conn_dst.close()

def get_dst_host_from_header(self,conn_sock,addr):

self.s_src=conn_sock

self.addr=addr

header=""

ssl_flag=False

while True:

#print("Loop Loop Loop")

header=self.s_src.recv(BUFSIZE)

if header :

#####header的一行含有CONNECT,即为SSL(HTTPS)

indexssl=header.split(b"\n")[0].find(b"CONNECT")

# print("indexsll:"+str(indexssl))

if indexssl>-1:

#####CONNECT===7 +8 前面一个空格

hostname=str(header.split(b"\n")[0].split(b":")[0].decode())

hostname=hostname[indexssl+8:]

port=443

ssl_flag=True

return header,hostname,port,ssl_flag

index1=header.find(b"Host:")

index2=header.find(b"GET http")

index3=header.find(b"POST http")

if index1>-1:

indexofn=header.find(b"\n",index1)

##host:===5

host=header[index1+5:indexofn]

elif index2>-1 or index3>-1:

###no host sample :'GET http://saxn.sina.com.cn/mfp/view?......

host=header.split(b"/")[2]

else:

print("src socket host:")

print(self.s_src.getpeername())

print("cannot find out host!!:"+repr(header))

return

break

host=str(host.decode().strip("\r").lstrip())

if len(host.split(":"))==2:

port=host.split(":")[1]

hostname=host.split(":")[0].strip("")

else:

port=80

hostname=host.split(":")[0].strip("")

ssl_flag=False

return header,hostname,int(port),ssl_flag

def get_data_from_host(self,host,port,sdata,ssl_flag):

self.conn_dst=socket.socket(socket.AF_INET,socket.SOCK_STREAM)

all_dst_data=""

try:

self.conn_dst.connect((str(host),port))

except Exception as e:

print(e)

print("get_data_from_host: cannot get host:"+host)

self.conn_dst.close()

return False

#con_string="("+server+","+port+")"

############https只建立链接

try:

if ssl_flag:

return all_dst_data

else:

self.conn_dst.sendall(sdata)

except Exception as e:

print(e)

print("cannot send data to host:"+host)

self.conn_dst.close()

return False

# buffer=[]

rc_data=self.conn_dst.recv(BUFSIZE)

#####剩下的data交给线程去获取

return rc_data

class Server(object):

def Handle_Rec(conn_socket,addr):

print("This is Handler Fun")

pass

def __init__(self,host,port):

print("Server starting......")

self.host=host

self.port=port

self.s_s=socket.socket(socket.AF_INET,socket.SOCK_STREAM)

self.s_s.setsockopt(socket.SOL_SOCKET,socket.SO_REUSEADDR,1)

self.s_s.bind((host,port))

self.s_s.listen(20)

def start(self):

while True:

try:

conn,addr=self.s_s.accept()

threading.Thread(target=Access_to_Host().handler,args=(conn,addr)).start()

except Exception as e:

print(str(e))

print("\nExcept happend")

if __name__=="__main__":

svr=Server("127.0.0.1",8080)

svr.start()

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值