python實(shí)現(xiàn)簡(jiǎn)單的TCP代理服務(wù)器
更新時(shí)間:2014年10月08日 09:57:44 投稿:shichen2014
這篇文章主要介紹了python實(shí)現(xiàn)簡(jiǎn)單的TCP代理服務(wù)器,包含了完整的實(shí)現(xiàn)過程及對(duì)應(yīng)的源碼與說明文檔下載,非常具有參考借鑒價(jià)值,需要的朋友可以參考下
本文實(shí)例講述了python實(shí)現(xiàn)簡(jiǎn)單的TCP代理服務(wù)器的方法,分享給大家供大家參考。
具體實(shí)現(xiàn)代碼如下:
# -*- coding: utf-8 -*-
'''
filename:rtcp.py
@desc:
利用python的socket端口轉(zhuǎn)發(fā),用于遠(yuǎn)程維護(hù)
如果連接不到遠(yuǎn)程,會(huì)sleep 36s,最多嘗試200(即兩小時(shí))
@usage:
./rtcp.py stream1 stream2
stream為:l:port或c:host:port
l:port表示監(jiān)聽指定的本地端口
c:host:port表示監(jiān)聽遠(yuǎn)程指定的端口
@author: watercloud, zd, knownsec team
@web: www.knownsec.com, blog.knownsec.com
@date: 2009-7
'''
import socket
import sys
import threading
import time
streams = [None, None] # 存放需要進(jìn)行數(shù)據(jù)轉(zhuǎn)發(fā)的兩個(gè)數(shù)據(jù)流(都是SocketObj對(duì)象)
debug = 1 # 調(diào)試狀態(tài) 0 or 1
def _usage():
print 'Usage: ./rtcp.py stream1 stream2\nstream : l:port or c:host:port'
def _get_another_stream(num):
'''
從streams獲取另外一個(gè)流對(duì)象,如果當(dāng)前為空,則等待
'''
if num == 0:
num = 1
elif num == 1:
num = 0
else:
raise "ERROR"
while True:
if streams[num] == 'quit':
print("can't connect to the target, quit now!")
sys.exit(1)
if streams[num] != None:
return streams[num]
else:
time.sleep(1)
def _xstream(num, s1, s2):
'''
交換兩個(gè)流的數(shù)據(jù)
num為當(dāng)前流編號(hào),主要用于調(diào)試目的,區(qū)分兩個(gè)回路狀態(tài)用。
'''
try:
while True:
#注意,recv函數(shù)會(huì)阻塞,直到對(duì)端完全關(guān)閉(close后還需要一定時(shí)間才能關(guān)閉,最快關(guān)閉方法是shutdow)
buff = s1.recv(1024)
if debug > 0:
print num,"recv"
if len(buff) == 0: #對(duì)端關(guān)閉連接,讀不到數(shù)據(jù)
print num,"one closed"
break
s2.sendall(buff)
if debug > 0:
print num,"sendall"
except :
print num,"one connect closed."
try:
s1.shutdown(socket.SHUT_RDWR)
s1.close()
except:
pass
try:
s2.shutdown(socket.SHUT_RDWR)
s2.close()
except:
pass
streams[0] = None
streams[1] = None
print num, "CLOSED"
def _server(port, num):
'''
處理服務(wù)情況,num為流編號(hào)(第0號(hào)還是第1號(hào))
'''
srv = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
srv.bind(('0.0.0.0', port))
srv.listen(1)
while True:
conn, addr = srv.accept()
print "connected from:", addr
streams[num] = conn # 放入本端流對(duì)象
s2 = _get_another_stream(num) # 獲取另一端流對(duì)象
_xstream(num, conn, s2)
def _connect(host, port, num):
''' 處理連接,num為流編號(hào)(第0號(hào)還是第1號(hào))
@note: 如果連接不到遠(yuǎn)程,會(huì)sleep 36s,最多嘗試200(即兩小時(shí))
'''
not_connet_time = 0
wait_time = 36
try_cnt = 199
while True:
if not_connet_time > try_cnt:
streams[num] = 'quit'
print('not connected')
return None
conn = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
try:
conn.connect((host, port))
except Exception, e:
print ('can not connect %s:%s!' % (host, port))
not_connet_time += 1
time.sleep(wait_time)
continue
print "connected to %s:%i" % (host, port)
streams[num] = conn #放入本端流對(duì)象
s2 = _get_another_stream(num) #獲取另一端流對(duì)象
_xstream(num, conn, s2)
if __name__ == '__main__':
if len(sys.argv) != 3:
_usage()
sys.exit(1)
tlist = [] # 線程列表,最終存放兩個(gè)線程對(duì)象
targv = [sys.argv[1], sys.argv[2] ]
for i in [0, 1]:
s = targv[i] # stream描述 c:ip:port 或 l:port
sl = s.split(':')
if len(sl) == 2 and (sl[0] == 'l' or sl[0] == 'L'): # l:port
t = threading.Thread(target=_server, args=(int(sl[1]), i))
tlist.append(t)
elif len(sl) == 3 and (sl[0] == 'c' or sl[0] == 'C'): # c:host:port
t = threading.Thread(target=_connect, args=(sl[1], int(sl[2]), i))
tlist.append(t)
else:
_usage()
sys.exit(1)
for t in tlist:
t.start()
for t in tlist:
t.join()
sys.exit(0)
完整實(shí)例代碼點(diǎn)擊此處本站下載。
希望本文所述對(duì)大家的Python程序設(shè)計(jì)有所幫助。
您可能感興趣的文章:
- python網(wǎng)絡(luò)編程之TCP通信實(shí)例和socketserver框架使用例子
- Python采用socket模擬TCP通訊的實(shí)現(xiàn)方法
- Python Socket實(shí)現(xiàn)簡(jiǎn)單TCP Server/client功能示例
- python實(shí)現(xiàn)TCP服務(wù)器端與客戶端的方法詳解
- 用Python實(shí)現(xiàn)一個(gè)簡(jiǎn)單的多線程TCP服務(wù)器的教程
- Python中的TCP socket寫法示例
- Python實(shí)現(xiàn)TCP/IP協(xié)議下的端口轉(zhuǎn)發(fā)及重定向示例
- Python+Socket實(shí)現(xiàn)基于TCP協(xié)議的客戶與服務(wù)端中文自動(dòng)回復(fù)聊天功能示例
- Python socket網(wǎng)絡(luò)編程TCP/IP服務(wù)器與客戶端通信
- python3.5實(shí)現(xiàn)socket通訊示例(TCP)
- python中的TCP(傳輸控制協(xié)議)用法實(shí)例分析
相關(guān)文章
python編寫函數(shù)注意事項(xiàng)總結(jié)
在本篇文章里小編給大家分享了一篇關(guān)于python編寫函數(shù)注意事項(xiàng)總結(jié)內(nèi)容,有需要的朋友們可以學(xué)習(xí)下。2021-03-03
python如何實(shí)現(xiàn)lazy segment tree惰性段樹算法
LazySegmentTree(惰性段樹)算法是一種數(shù)據(jù)結(jié)構(gòu),專門用于高效處理區(qū)間查詢和更新操作,它利用延遲更新技術(shù)(LazyPropagation),僅在必要時(shí)執(zhí)行實(shí)際更新,以提升效率,此結(jié)構(gòu)將數(shù)組表達(dá)為二叉樹,每個(gè)節(jié)點(diǎn)表示一個(gè)數(shù)組區(qū)間2024-10-10
Python實(shí)戰(zhàn)小程序利用matplotlib模塊畫圖代碼分享
這篇文章主要介紹了Python實(shí)戰(zhàn)小程序利用matplotlib模塊畫圖代碼分享,具有一定借鑒價(jià)值,需要的朋友可以了解下。2017-12-12
Python 處理數(shù)據(jù)庫事務(wù)的操作方法
在Python中,處理數(shù)據(jù)庫事務(wù)通常涉及使用特定的數(shù)據(jù)庫驅(qū)動(dòng)如sqlite3、PyMySQL和psycopg2等,這些庫提供事務(wù)管理功能,允許開發(fā)者手動(dòng)控制事務(wù)的提交和回滾,本文給大家介紹Python如何處理數(shù)據(jù)庫事務(wù),感興趣的朋友一起看看吧2024-10-10

