我有这个套接字服务器脚本,
import SocketServer
import shelve
import zlib
class MyTCPHandler(SocketServer.BaseRequestHandler):
def handle(self):
self.words = shelve.open('/home/tipu/Dropbox/dev/workspace/search/words.db', 'r');
self.tweets = shelve.open('/home/tipu/Dropbox/dev/workspace/search/tweets.db', 'r');
param = self.request.recv(1024).strip()
try:
result = str(self.words[param])
except KeyError:
result = "set()"
self.request.send(str(result))
if __name__ == "__main__":
HOST, PORT = "localhost", 50007
SocketServer.TCPServer.allow_reuse_address = True
server = SocketServer.TCPServer((HOST, PORT), MyTCPHandler)
server.serve_forever()
这个接收器,
from django.http import HttpResponse
from django.template import Context, loader
import shelve
import zlib
import socket
def index(req, param = ''):
HOST = 'localhost'
PORT = 50007
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((HOST, PORT))
s.send(param)
data = zlib.decompress(s.recv(131072))
s.close()
print 'Received', repr(data)
t = loader.get_template('index.html')
c = Context({ 'foo' : data })
return HttpResponse(t.render(c))
我正在向接收器发送数百千字节的字符串。我最终只收到了一部分。有没有办法可以解决这个问题,以便发送整个字符串?
编辑:我要发送的字符串实际上是418437个字符。但是这里的想法是......我正在尝试使用str(set)发送一个集合的字符串表示,所以我可以使用eval重新组合集合。有没有办法可以让套接字发送完整的数据或压缩它,以便套接字可以立即发送它?我尝试使用zlib,但压缩数据也没有完全发送,因为我反复得到头错误,这是我能够找到的,因为压缩字符串不完整。
答案 0 :(得分:5)
socket.recv(N)并不能保证会收到确切的N个字节:相反,N只是一个gulp可以接收的最大字节数(为了提高效率,理想情况下应该如文档所示,是4096的一小部分。
你需要“继续接收”(循环和累积),直到你拥有你想要的所有字节(看起来你的协议没有传达那个关键价值:你将必须使其显式化,无论是在传输结束时使用前缀长度还是终结符,都无法从流套接字中隐式提取它。)
与发送类似,虽然在这种情况下您可以使用socket.sendall代表您进行必要的循环。
答案 1 :(得分:0)
使用pickle模块将对象序列化到套接字上并将其加载到另一端。类似的东西:
pkl_dict= pickle.dumps(THE_SET)
mysocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
mysocket.connect((HOST, PORT))
mysocket.send(pkl_dict)
mysocket.close()