2013-10-24 10 views
3

我正在使用python编写一个简单的TCP服务器,并试图输入超时。我当前的代码:向python服务器添加超时时出现非阻塞错误

import socket 


def connect(): 
    HOST = ''     # Symbolic name meaning the local host 
    PORT = 5007    # Arbitrary non-privileged port 
    s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 
    s.bind((HOST, PORT)) 
    s.listen(1) 
    s.settimeout(5) 
    conn, addr = s.accept() 
    print 'Connected by', addr 
    return conn 

conn = connect() 

while 1: 
    data = conn.recv(1024) 
    if not data: break 
    print data 
conn.close() 

的问题是,当我尝试连接我的数据= conn.recv(1024)

error: [Errno 10035] A non-blocking socket operation could not be completed immediately 

代码工作没有超时的得到一个错误。

+0

我真的推荐'SocketServer'模块。它使我很容易切换到多线程等,它也被'SimpleHTTPServer'模块使用。 – User

+1

你知道为什么引发异常吗? – AmitE

回答

1

您可以打开阻塞:

# ... 
    conn.setblocking(1) 
    return conn 
# ... 
+2

这完全没有解释为什么设置超时会导致它变为非阻塞。就我所能找到的而言,这当然不在python文档中,我很好奇为什么会发生这种情况。 – Fulluphigh

+1

实际上设置一个超时会使其非阻塞。从文档 - >“s.settimeout(0.0)相当于s.setblocking(0); s.settimeout(无)相当于s.setblocking(1)。”请参阅https://docs.python.org/2/library/socket.html#socket.socket.settimeout – AmitE

1

碰到了同样的问题,29分钟前。找到一个简单的非优雅的工作......如果你通过执行time.sleep(1)来让socket有时间呼吸,捕获10035错误并重试它可以工作。我正在使用2.7.5 ...也许这是一个固定的错误。不确定。

代码示例...请理解这是我使用的非常简单的测试代码(一次只能接收1个字节)。所以,'s'是10s超时的套接字,'numbytes'是字节数I需要...

def getbytes(s,numbytes): 
    din = '' 
    socketerror10035count = 0 
    while True: 
      try: 
       r = s.recv(1).encode('hex') 
       din += r 
       if len(din)/2 == numbytes: 
        print 'returning',len(din)/2, 'bytes' 
        break 
      except socket.timeout as e: 
       din = 'socket timeout' 
       break 
      except socket.error as e: 
       if e[0] == 10035 and socketerror10035count < 5: 
        socketerror10035count = socketerror10035count +1 
        time.sleep(1) 
       else: 
        din = 'socket error' 
        break 
      except: 
       din = 'deaddead' 
       break 
    return din 
1

尝试设置套接字上的超时和连接上的阻塞。像这样:

import socket 

def connect(): 
    HOST = ''     # Symbolic name meaning the local host 
    PORT = 5007    # Arbitrary non-privileged port 
    s = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 
    s.settimeout(5) 
    s.bind((HOST, PORT)) 
    s.listen(1) 
    return s 

s = connect() 

while 1: 
    conn, addr = s.accept() 
    print 'Connected by', addr 
    conn.setblocking(1) 
    data = conn.recv(1024) 
    conn.close() 
    if not data: break 
    print data 
s.close() 
+1

它的工作原理,任何想法为什么添加超时将首先导致错误? – user3582887

+1

此外,此错误只发生在Windows中,当在Linux上运行时,不需要“conn.setblocking(1)”,并且超时按预期工作。 – user3582887