Python urllib2.urlopen 设置超时后仍无限冻结脚本
函数 urllib2.urlopen
会卡住。所以我有几个简单的问题:
- 为什么即使设置了超时,
urlopen
还是会让我的脚本永远卡住? - 我该如何访问一个网址的数据(在这个例子中是:http://api.own3d.tv/live?channel=FnaticTV),而不让我的 Python 程序永远卡住?
这是卡住的部分(在 own3d.py 中):
# Try three times to make contact
while True:
try:
# Connect to API
# Right here! It freezes here
connection = urllib2.urlopen(request, timeout=10)
xmlstring = connection.read()
except URLError as e:
tries += 1
if tries >= 3:
sys.stderr.write(
'own3dStreamsUpdater: Fatal error: Repeated timeouts')
exit()
这是我按下键盘中断后得到的堆栈跟踪信息
Traceback (most recent call last): File "", line 1, in File "honsapp/own3dStreamsUpdater.py", line 53, in updateStreamInfo streamInfo = getStreamInfo(stream) File "honsapp/own3d.py", line 98, in getStreamInfo connection = urllib2.urlopen(request, timeout=10) File "/usr/local/lib/python2.7/urllib2.py", line 126, in urlopen return _opener.open(url, data, timeout) File "/usr/local/lib/python2.7/urllib2.py", line 394, in open response = self._open(req, data) File "/usr/local/lib/python2.7/urllib2.py", line 412, in _open '_open', req) File "/usr/local/lib/python2.7/urllib2.py", line 372, in _call_chain result = func(*args) File "/usr/local/lib/python2.7/urllib2.py", line 1199, in http_open return self.do_open(httplib.HTTPConnection, req) File "/usr/local/lib/python2.7/urllib2.py", line 1170, in do_open r = h.getresponse(buffering=True) File "/usr/local/lib/python2.7/httplib.py", line 1027, in getresponse response.begin() File "/usr/local/lib/python2.7/httplib.py", line 407, in begin version, status, reason = self._read_status() File "/usr/local/lib/python2.7/httplib.py", line 365, in _read_status line = self.fp.readline() File "/usr/local/lib/python2.7/socket.py", line 447, in readline data = self._sock.recv(self._rbufsize) KeyboardInterrupt
编辑
我让我的脚本运行了一整夜。我不知道具体花了多长时间(不过超过五分钟),但最后脚本终于放弃了,并给了我一个堆栈跟踪:
Traceback (most recent call last): File "honsapp/own3dStreamsUpdater.py", line 260, in newInfo() File "honsapp/own3dStreamsUpdater.py", line 172, in newInfo result = updateStreamInfo(stream) File "honsapp/own3dStreamsUpdater.py", line 53, in updateStreamInfo streamInfo = getStreamInfo(stream) File "/root/Dropbox/Projects/honstreams/honsapp/own3d.py", line 98, in getStreamInfo connection = urllib2.urlopen(request, timeout=10) File "/usr/local/lib/python2.7/urllib2.py", line 126, in urlopen return _opener.open(url, data, timeout) File "/usr/local/lib/python2.7/urllib2.py", line 394, in open response = self._open(req, data) File "/usr/local/lib/python2.7/urllib2.py", line 412, in _open '_open', req) File "/usr/local/lib/python2.7/urllib2.py", line 372, in _call_chain result = func(*args) File "/usr/local/lib/python2.7/urllib2.py", line 1199, in http_open return self.do_open(httplib.HTTPConnection, req) File "/usr/local/lib/python2.7/urllib2.py", line 1170, in do_open r = h.getresponse(buffering=True) File "/usr/local/lib/python2.7/httplib.py", line 1027, in getresponse response.begin() File "/usr/local/lib/python2.7/httplib.py", line 407, in begin version, status, reason = self._read_status() File "/usr/local/lib/python2.7/httplib.py", line 371, in _read_status raise BadStatusLine(line) httplib.BadStatusLine: ''
2 个回答
4
你确定urlopen()这个调用会卡住吗?因为如果这个调用成功的话,你的while循环是不会结束的。
5
这个脚本根本不会卡住,但它很好地说明了为什么你不应该在疲惫的时候写代码。原本应该尝试连接API三次的循环会一直运行下去,因为我忘记在里面加一个break
语句。
这个问题真是太傻了,我不会怪你把它删掉。
修复后的代码:
# Try three times to make contact
while True:
try:
# Connect to API
connection = urllib2.urlopen(request, timeout=10)
xmlstring = connection.read()
break
except URLError as e:
tries += 1
if tries >= 3:
sys.stderr.write(
'own3dStreamsUpdater: Fatal error: Repeated timeouts')
exit()