A simple proxy server is implemented with just 50 lines of Python code
- 2020-05-07 19:57:24
- OfStack
The previous scenario is as follows:
I need to use the mongodb graphical client on my computer, but the server address of mongodb is not open to the external network, so I can only connect to mongodb server B by logging into the host A first, and then connecting to mongodb server B from A.
I intended to forward it via ssh port, but I don't have permission to connect ssh to B from machine A. So I wrote one in python.
The principle is simple.
1. Open one socket server to listen for connection requests
2. For each connection request received from a client, a connection request is made to the address to be forwarded. Namely client - > proxy- > forward. proxy is both an socket server (listening for client) and an socket client (requesting to forward).
3. The client - > proxy and proxy - > forward these two socket are bound with a dictionary.
4. Pass send/recv to data intact through the dictionary of this mapping
Here is the code.
#coding=utf-8
import socket
import select
import sys
to_addr = ('xxx.xxx.xx.xxx', 10000)# Forwarding address
class Proxy:
def __init__(self, addr):
self.proxy = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
self.proxy.bind(addr)
self.proxy.listen(10)
self.inputs = [self.proxy]
self.route = {}
def serve_forever(self):
print 'proxy listen...'
while 1:
readable, _, _ = select.select(self.inputs, [], [])
for self.sock in readable:
if self.sock == self.proxy:
self.on_join()
else:
data = self.sock.recv(8096)
if not data:
self.on_quit()
else:
self.route[self.sock].send(data)
def on_join(self):
client, addr = self.proxy.accept()
print addr,'connect'
forward = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
forward.connect(to_addr)
self.inputs += [client, forward]
self.route[client] = forward
self.route[forward] = client
def on_quit(self):
for s in self.sock, self.route[self.sock]:
self.inputs.remove(s)
del self.route[s]
s.close()
if __name__ == '__main__':
try:
Proxy(('',12345)).serve_forever()# The address to which the proxy server listens
except KeyboardInterrupt:
sys.exit(1)