Python套接字连接异常

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/25447803/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-18 20:13:47  来源:igfitidea点击:

Python socket connection exception

pythonsocketsexceptionexception-handling

提问by erling

I have a socket-connection going on and I wanna improve the exception handling and Im stuck. Whenever I use the socket.connect(server_address) function with an invalid argument the program stops, but doesnt seem to throw any exceptions. Heres my code

我有一个套接字连接,我想改进异常处理,但我卡住了。每当我使用带有无效参数的 socket.connect(server_address) 函数时,程序就会停止,但似乎不会抛出任何异常。这是我的代码

import socket
import sys
import struct
class ARToolkit():

    def __init__(self):
        self.x = 0
        self.y = 0
        self.z = 0
        self.sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        self.logging = False


    def connect(self,server_address):
        try:
            self.sock.connect(server_address)
        except socket.error, msg:
            print "Couldnt connect with the socket-server: %s\n terminating program" % msg
            sys.exit(1)


    def initiate(self):
        self.sock.send("start_logging")

    def log(self):
        self.logging  = True  
        buf = self.sock.recv(6000)
        if len(buf)>0:
            nbuf = buf[len(buf)-12:len(buf)]
            self.x, self.y, self.z = struct.unpack("<iii", nbuf)





    def stop_logging(self):
        print "Stopping logging"
        self.logging = False
        self.sock.close()

The class maybe looks a bit wierd but its used for receiving coordinates from another computer running ARToolKit. Anyway, the issue is at the function connect():

这个类可能看起来有点奇怪,但它用于从另一台运行 ARToolKit 的计算机接收坐标。无论如何,问题出在函数上connect()

def connect(self,server_address):
        try:
            self.sock.connect(server_address)
        except socket.error, msg:
            print "Couldnt connect with the socket-server: %s\n terminating program" % msg
            sys.exit(1)

If I call that function with a random IP-address and portnumber the whole program just stops up at the line:

如果我使用随机 IP 地址和端口号调用该函数,则整个程序只会停在该行:

self.sock.connect(server_address)

The documentation I've read states that in case of an error it will throw a socket.error-exception. I've also tried with just:

我读过的文档指出,如果出现错误,它将抛出 socket.error-exception。我也试过:

except Exception, msg:

This, if I'm not mistaken, will catch any exceptions, and still it yields no result. I would be very grateful for a helping hand. Also, is it okay to exit programs using sys.exit when an unwanted exception occurs?

如果我没记错的话,这会捕获任何异常,但仍然不会产生任何结果。我将非常感谢您的帮助。另外,当发生不需要的异常时,是否可以使用 sys.exit 退出程序?

Thank you

谢谢

采纳答案by mhawke

If you have chosen a random, but valid, IP address and port, socket.connect()will attempt to make a connection to that endpoint. By default, if no explicit timeout is set for the socket, it will block while doing so and eventually timeout, raising exception socket.error: [Errno 110] Connection timed out.

如果您选择了一个随机但有效的 IP 地址和端口,socket.connect()将尝试与该端点建立连接。默认情况下,如果没有为套接字设置明确的超时,它会在这样做时阻塞并最终超时,引发异常socket.error: [Errno 110] Connection timed out

The default timeout on my machine is 120 seconds. Perhaps you are not waiting long enough for socket.connect()to return (or timeout)?

我机器上的默认超时是 120 秒。也许您等待socket.connect()返回(或超时)的时间不够长?

You can try reducing the timeout like this:

您可以尝试像这样减少超时:

import socket

s = socket.socket()
s.settimeout(5)   # 5 seconds
try:
    s.connect(('123.123.123.123', 12345))         # "random" IP address and port
except socket.error, exc:
    print "Caught exception socket.error : %s" % exc

Note that if a timeout is explicitly set for the socket, the exception will be socket.timeoutwhich is derived from socket.errorand will therefore be caught by the above except clause.

请注意,如果为套接字显式设置了超时,则异常将socket.timeout来自于socket.error上面的 except 子句,因此将被捕获。

回答by erling

The problem with your last general exception is the colon placement. It needs to be after the entire exception, not after the except statement. Thus to capture all exceptions you would need to do:

您最后一个一般例外的问题是冒号的位置。它需要在整个异常之后,而不是在except语句之后。因此,要捕获您需要执行的所有异常:

except Exception,msg:

However from Python 2.6+ you should use the as statement instead of a comma like so:

但是,从 Python 2.6+ 开始,您应该使用 as 语句而不是像这样的逗号:

except Exception as msg:

I was able to run the code fine (note you need to throw in a tuple to the connect method). If you want to specifically catch only socket errors then you would need to except the socket.errorclass. Like you have:

我能够很好地运行代码(请注意,您需要向 connect 方法添加一个元组)。如果您只想专门捕获套接字错误,则需要排除socket.error该类。就像你有:

except socket.error as msg:

If you want to make sure that a tuple is entered simply add another exception loop:

如果要确保输入元组,只需添加另一个异常循环:

except socket.error as msg:
    print "Socket Error: %s" % msg
except TypeError as msg:
    print "Type Error: %s" % msg