簡易代理服務器之python實現


代理服務器是在client和server之間的一個服務器,一般起到緩存的作用,所以也叫緩存服務器。比如:

A ----(HTTP)----》 B ----(HTTP)----》 C

其中A是客戶端,C是服務器端,那么B就是proxy server了,是代理服務器,也是緩存服務器:當A發起請求時要求獲得C上的一個文件,需要先經過B,B在自己的文件系統中尋找是否有A所請求的文件,如果有,就發給A,完成一次響應;如果沒有,則在B上創建新的HTTP請求,發送到C,並將C的響應緩存到文件中,同時回發給A。

只要代理服務器B上存在A所需要的文件,就不必勞煩C重新發送響應,一定程度上減輕C的壓力,同時減少響應時間。

下面我們用socket編程來實現一個簡單的代理服務器,功能為:
訪問 localhost:8899/helloworld.html 格式的url時,若helloworld.html與proxy server在同一目錄下,那么返回這個文件,否則報錯
訪問 localhost:8899/www.baidu.com 格式的url時,從proxy server的文件系統中查找www.baidu.com的緩存文件,若存在則返還;若不存在則向baidu.com發起HTTP請求,將得到的響應緩存並發給客戶端。

其中發送的HTTP請求,由tcp socket實現。

#coding:utf-8
from socket import *


# 創建socket,綁定到端口,開始監聽
tcpSerPort = 8899
tcpSerSock = socket(AF_INET, SOCK_STREAM)

# Prepare a server socket
tcpSerSock.bind(('', tcpSerPort))
tcpSerSock.listen(5)

while True:
	# 開始從客戶端接收請求
	print 'Ready to serve...'
	tcpCliSock, addr = tcpSerSock.accept()
	print 'Received a connection from: ', addr
	message = tcpCliSock.recv(4096)

	# 從請求中解析出filename
	print message.split()[1]
	filename = message.split()[1].partition("/")[2]
	fileExist = "false"
	filetouse = "/" + filename
	try:
		# 檢查緩存中是否存在該文件
		f = open(filetouse[1:], "r")
		outputdata = f.readlines()
		fileExist = "true"
		print 'File Exists!'

		# 緩存中存在該文件,把它向客戶端發送
		tcpCliSock.send("HTTP/1.0 200 OK\r\n\r\n")

		for i in range(0, len(outputdata)):
			tcpCliSock.send(outputdata[i])
		print 'Read from cache'

		# 緩存中不存在該文件,異常處理
	except IOError:
		print 'File Exist: ', fileExist
		if fileExist == "false":
			# 在代理服務器上創建一個tcp socket
			print 'Creating socket on proxyserver'
			c = socket(AF_INET, SOCK_STREAM)

			hostn = filename.replace("www.", "", 1)
			print 'Host Name: ', hostn
			try:
				# 連接到遠程服務器80端口
				c.connect((hostn, 80))
				print 'Socket connected to port 80 of the host'

				# 在代理服務器上緩存請求的文件
				fileobj = c.makefile('r', 0)
				#拼湊http get請求的請求行。注意格式為: "請求方法 URI HTTP版本",空格不能省略!
				fileobj.write("GET " + "http://" + filename + " HTTP/1.0\n\n")

				# Read the response into buffer
				buff = fileobj.readlines()

				# Create a new file in the cache for the requested file.
				# Also send the response in the buffer to client socket
				# and the corresponding file in the cache
				tmpFile = open("./" + filename,"wb")
				for i in range(0, len(buff)):
					tmpFile.write(buff[i])
					tcpCliSock.send(buff[i])

			except:
				print "Illegal request"

		else:
			# HTTP response message for file not found
			# Do stuff here
			print 'File Not Found...Stupid Andy'
			a = 2
	# Close the client and the server sockets
	tcpCliSock.close()
# Fill in start.
tcpSerSock.close()
# Fill in end.

ref:《計算機網絡:自頂向下方法》第二章 套接字編程作業4


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM