Python套接字无法接收数据
问题描述:
我正在使用Python 3.2中的localhost套接字编写进程间通信并在Windows上测试它。以下是一些带有服务器和客户端的测试代码,相互发送消息。奇怪的是,它随机失败,RuntimeError
错误,在receive
函数中提出,在第5或第10个连接的某处。Python套接字无法接收数据
#!/usr/bin/python
# -*- coding: utf-8 -*-
import socket
import pickle
import time
import logging
from multiprocessing import Process
def receive(conn):
def ensure_receive(length):
parts = []
received = 0
while received < length:
chunk = conn.recv(length - received)
if not chunk:
raise RuntimeError("Connection broken")
parts.append(chunk)
received += len(chunk)
return b''.join(parts)
lengthString = ensure_receive(8)
serialized = ensure_receive(int(lengthString))
return pickle.loads(serialized)
def send(conn, message):
def ensure_send(message):
sent = 0
while sent < len(message):
sent += conn.send(message[sent:])
# logging.warning("Now sending")
serialized = pickle.dumps(message, 1)
messageLength = len(serialized)
ensure_send("{:8}".format(messageLength).encode('Latin-1'))
ensure_send(serialized)
def client_function(clientLimit):
for index in range(1, clientLimit + 1):
print ("Client", index)
try:
conn = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
conn.connect(('localhost', 12333))
send(conn, list(range(100000)))
message = receive(conn)
send(conn, list(range(100)))
# time.sleep(0.01)
conn.shutdown(socket.SHUT_WR)
conn.close()
except Exception:
logging.exception("Socket error in client")
def server_function(clientLimit):
newSocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
newSocket.bind(('localhost', 12333))
newSocket.listen(16)
for _ in range(clientLimit):
(conn, address) = newSocket.accept()
time.sleep(0.01)
message = receive(conn)
send(conn, list(range(10)))
message = receive(conn)
conn.shutdown(socket.SHUT_WR)
conn.close()
def test(clientLimit):
server = Process(target = server_function, args = (clientLimit,))
server.start()
time.sleep(1)
client = Process(target = client_function, args = (clientLimit,))
client.start()
client.join()
server.join()
if __name__ == "__main__":
test(100)
但是,有没有错误,如果我在client_function
取消注释time.sleep(0.01)
,或者如果我改变的消息整理了一下。
有没有办法让它工作,而不用随意等待,并允许任意协议?
答
这是因为你的server_function中的conn.shutdown(socket.SHUT_WR)。你需要的是socket.SHUT_RD,或者更好的是,根本不需要shutdown()调用。
+0
谢谢。根本没有帮助,但将其更改为SHUT_RD完成了这项工作。 – Kolmar 2011-12-17 17:57:36
有一个有用的[socketserver](http://docs.python.org/py3k/library/socketserver.html)模块,它使你的服务器代码更加稳定和可读。 – Kirill 2011-12-17 18:02:18