简体   繁体   English

Python套接字,如何摆脱无限循环和处理异常

[英]Python sockets, how to escape from infinite loop and handle exceptions

I have a script that connects to a remote server. 我有一个连接到远程服务器的脚本。 The code is below 代码如下

s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((remote_host,remote_port))
s.setblocking(False)


while True:
    try:
        data = s.recv(1024)

        if not data:
           break

        pkt_type = ord(data[2]) # get pkt type

        if pkt_type == Reset:
           s.send(data)

        if pkt_type == Authenticate:
           processAuthenticate(s,data)
           break

    except:
        pass

while(True)
 .
 .
 .

I wait for reset and echo back to the server, then wait for an Authenticate packet, twiddle a few bit and echo that back to the server. 我等待重置并回显到服务器,然后等待Authenticate数据包,然后旋转几下,然后将其回显到服务器。 Once this is done successfully I can now request data from the the server. 成功完成此操作后,我现在可以从服务器请求数据。 This is done in the next while(true) loop. 这是在下一个while(true)循环中完成的。

Is this the best way of doing this. 这是这样做的最好方法。 Sometimes when I run the script I get an error, what is the simplest way of handling the exception and preventing execuation of the next wile loop? 有时,当我运行脚本时遇到错误,处理异常并阻止执行下一个wile循环的最简单方法是什么?

Thanks 谢谢

A Finite State Machine (FSM) is pretty much the canonical way to do this sort of thing. 有限状态机(FSM)几乎是执行此类操作的规范方法。 A good reference for doing FSMs in Python is this: http://wiki.python.org/moin/FiniteStateMachine 在Python中执行FSM的一个很好的参考是: http : //wiki.python.org/moin/FiniteStateMachine

EDIT: Looks like a FSM should be handy here. 编辑: 看起来FSM应该在这里很方便。

Actually, I suggest you take a look at Twisted Reactor - haven't used it myself (yet), but it does all the bulk work and nasty stuff that you would have to implement yourself if using a FSM and an event loop (which your while -loop essentially is) 实际上,我建议您看一下Twisted Reactor-尚未亲自使用过,但它可以完成所有繁琐的工作和令人讨厌的工作,而如果使用FSM和事件循环,则需要自己实施while -loop本质上是)

EDIT 2: 编辑2:

A few notes (while waiting for your complete code) 一些注意事项(在等待您的完整代码时)

  1. the fact that you have 2 consecutive while(true) is, well, odd 您连续有2个while(true)的事实很奇怪
  2. you probably want to move the except: statement up, before the if not data statement and replace pass with continue 您可能想将except:语句上移至if not data语句之前,并用continue替换pass
  3. ord(data[2]) suggests that you are using a binary protocol, you really should consider using the struct modules unpack() and pack() instead. ord(data[2])建议您使用的是二进制协议,您实际上应该考虑使用struct模块unpack()pack()代替。

In addition to the above tips, you need to buffer the data - when using a stream protocol you can't just assume that you will get all the data you want in one call to recv. 除了上述提示之外,您还需要缓冲数据-使用流协议时,您不能仅仅假设一次调用recv就可以获取所有想要的数据。 Instead you must take what you read from recv and add it to a buffer, then examine the buffer to see if it contains all the data for a message yet. 相反,您必须将您从recv读取的内容添加到缓冲区中,然后检查缓冲区以查看其是否包含消息的所有数据。 If it does, extract the message, handle it, then repeat with the rest of the buffer. 如果是这样,请提取消息,进行处理,然后对其余缓冲区重复上述操作。 When you can't extract any further messages, you go back and read more from the socket. 当您无法提取更多消息时,请返回并从套接字中阅读更多内容。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM