2011-11-09 81 views
3

函數urllib2.urlopen凍結。所以我的問題很簡單:python urllib2.urlopen即使設置了超時也無限制地凍結腳本

  • 爲什麼urlopen凍結我的腳本永遠即使超時設置?
  • 如何在URL中訪問數據(在這種情況下是: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() 

這是堆棧跟蹤後,我的一個KeyboardInterrupt

 
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: '' 

回答

4

這個腳本根本不會凍結,但它是一個很好的例子,說明你爲什麼不應該在疲倦時編碼。應該嘗試連接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() 
+2

你可能已經通過DOS的網站讓網站管理員非常生氣:) –

4

您確認的urlopen()調用掛起?因爲如果調用成功,while循環不會終止。

+0

的確。也許如果你打印xmlstring,你可能會看到有價值的輸出。 –

+0

我不明白你們的意思。棧跟蹤清楚地表明,它凍結的地方,等待我的KeyboardInterrupt,在'connection = urllib2.urlopen(request,timeout = 10)'行中。如何更改該行下面的任何代碼可能會有所作爲?另外,我用更多的信息更新了我的問題。 – Hubro

+1

stacktrace只聲明你中斷它的地方在urlopen()調用中 - 這並不令人驚訝,因爲循環中只有兩條語句,而urlopen()可能是較慢的語句。 Andrew建議你在循環中加入打印語句嗎? – Cito

相關問題