Pregunta

El urllib2 documentación dice que Tiempo de espera se añadió parámetro en Python 2.6. Por desgracia mi base de código ha estado funcionando en Python 2.5 y 2.4 plataformas.

¿Hay alguna forma alternativa para simular el tiempo de espera? Todo lo que quiero hacer es permitir que el código para hablar al servidor remoto para una cantidad fija de tiempo.

Tal vez ninguna alternativa biblioteca incorporada? (No quiero instalar 3 ª Parte, como pycurl)

¿Fue útil?

Solución

se puede establecer un tiempo de espera global para todas las operaciones de socket (incluyendo las peticiones HTTP) mediante el uso de:

socket.setdefaulttimeout()

como esto:

import urllib2
import socket
socket.setdefaulttimeout(30)
f = urllib2.urlopen('http://www.python.org/')

En este caso, su solicitud sería urllib2 tiempo de espera después de 30 segundos y lanzar una excepción zócalo. (Esto se añadió en Python 2.3)

Otros consejos

Con la irritación considerable, se puede sustituir la clase de httplib.HTTPConnection que utiliza el urllib2.HTTPHandler.

def urlopen_with_timeout(url, data=None, timeout=None):

  # Create these two helper classes fresh each time, since
  # timeout needs to be in the closure.
  class TimeoutHTTPConnection(httplib.HTTPConnection):
    def connect(self):
      """Connect to the host and port specified in __init__."""
      msg = "getaddrinfo returns an empty list"
      for res in socket.getaddrinfo(self.host, self.port, 0,
                      socket.SOCK_STREAM): 
        af, socktype, proto, canonname, sa = res
        try:
          self.sock = socket.socket(af, socktype, proto)
          if timeout is not None:
            self.sock.settimeout(timeout)
          if self.debuglevel > 0:
            print "connect: (%s, %s)" % (self.host, self.port)
          self.sock.connect(sa)
        except socket.error, msg:
          if self.debuglevel > 0:
            print 'connect fail:', (self.host, self.port)
          if self.sock:
            self.sock.close()
          self.sock = None
          continue
        break
      if not self.sock:
        raise socket.error, msg

  class TimeoutHTTPHandler(urllib2.HTTPHandler):
    http_request = urllib2.AbstractHTTPHandler.do_request_
    def http_open(self, req):
      return self.do_open(TimeoutHTTPConnection, req)

  opener = urllib2.build_opener(TimeoutHTTPHandler)
  opener.open(url, data)

Creo que su mejor opción es que parchear (o desplegar una versión local de) su urllib2 con el cambio de la rama 2.6 mantenimiento

El archivo debe estar en /usr/lib/python2.4/urllib2.py (en Linux y 2.4)

Yo uso httplib de la librería estándar. Tiene una API simple muerto, pero sólo maneja http como puede imaginar. IIUC urllib utiliza httplib para poner en práctica las cosas http.

Debe establecer el tiempo de espera en dos lugares.

import urllib2
import socket

socket.setdefaulttimeout(30)
f = urllib2.urlopen('http://www.python.org/', timeout=30)

Bueno, la forma de tiempo de espera se maneja, ya sea en 2.4 o 2.6 es el mismo. Si abre el archivo urllib2.py en 2.6 u vería que toma un argumento extra como tiempo de espera y lo maneja utilizando el método socket.defaulttimeout () como se ha mencionado es la respuesta 1.

Así que realmente no necesita actualizar su urllib2.py en ese caso.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top