在Python中,如何对有时会挂起的函数调用设置超时?

2 投票
2 回答
2862 浏览
提问于 2025-04-17 09:06

我正在用Python写一个爬虫,利用urllib2的OpenerDirector来抓取网络上的内容。问题是,当连接到一个https地址时,连接会卡住,似乎完全不管我设置的超时时间。

一个解决办法是把这个操作放到一个线程里,如果它卡住了,就杀掉这个线程然后重启。听说Python不支持直接杀掉线程,这被认为是个坏主意,因为会引发垃圾回收和其他问题。不过我还是觉得这个办法比较简单。

还有一个想法是使用像Twisted这样的异步库,但这并不能解决根本问题。

我需要一种方法来强制中断这个调用,或者修复urllib2的OpenerDirector处理超时的方式。谢谢。

2 个回答

0

我建议使用另一个进程,而不是线程。可以这样做:

from multiprocessing import Process

checker = Process(target=yourFunction, args=(some_queue))
timeout = 150
checker.start()
counter = 0
while checker.is_alive() == True:
        time.sleep(1)
        counter += 1
        if counter > timeout :
                print "Son process consumed too much run-time. Going to kill it!"
                kill(checker.pid)
                break

这样的话,无论发生什么,子进程在150秒后都会被杀掉。

2

另一个类似的问题可以在这里找到 这里。当我遇到类似的情况时,我发现把我正在做的事情转换成定义和调用函数会更简单,这样在超时事件发生时,函数可以返回一个值。这样做实际上可以利用不同的返回值,打开更多的可能性。

我上面提到的相关问题的另一个答案听起来更像是你想要的(根据我的理解): https://stackoverflow.com/a/5817436/1118357

撰写回答