Question

Je viens hérité du code Python et le besoin de corriger un bug le plus rapidement possible. J'ai très peu de connaissances Python donc s'il vous plaît excuser mon ignorance. J'utilise urllib2 pour extraire des données de pages Web. Malgré l'utilisation socket.setdefaulttimeout(30) je viens encore à travers les URL qui pendent apparemment indéfiniment.

Je veux temps l'extraction et ont obtenu ce bien après beaucoup de recherche sur le Web:

import socket 
socket.setdefaulttimeout(30)

reqdata = urllib2.Request(urltocollect)

    def handler(reqdata):
        ????  reqdata.close() ????


    t = Timer(5.0, handler,[reqdata])
    t.start()
    urldata = urllib2.urlopen(reqdata)
    t.cancel()

Les déclencheurs de la fonction de gestionnaire après le temps a passé, mais je ne sais pas comment l'obtenir pour arrêter l'opération de openurl.

Toute orientation serait reçue avec reconnaissance. C

Mise à jour ------------------------- Dans mon expérience quand il est utilisé sur les blocages et attend de certaines URL indéfiniment. Les URL qui font cela sont ceux que lorsque pointé avec un navigateur ne résolvent jamais, le navigateur attend juste avec l'indicateur d'activité en mouvement, mais jamais pleinement connecter. Je soupçonne que ces URL peuvent être coincé dans une sorte de redirect boucle infinie. L'argument de délai d'attente pour urlopen (dans les versions ultérieures de Python) et le socket.setdefaulttimeout () de paramètre global ne détecte pas ce problème sur mon système.

J'ai essayé un certain nombre de solutions, mais à la fin j'updraded à Python 2.7 et utilisé une variante de la réponse de Werner ci-dessous. Merci Werner.

Était-ce utile?

La solution

Vous pouvez y parvenir en utilisant des signaux.

Voici un exemple de mon décorateur de signal que vous pouvez utiliser pour définir le délai d'attente pour les fonctions individuelles.

Ps. pas sûr si cela est syntaxiquement correct pour 2.4. J'utilise 2.6 mais 2.4 supporte les signaux.

import signal
import time

class TimeOutException(Exception):
    pass

def timeout(seconds, *args, **kwargs):
    def fn(f):
        def wrapped_fn(*args, **kwargs):
            signal.signal(signal.SIGALRM, handler)
            signal.alarm(seconds)
            f(*args, **kwargs)
        return wrapped_fn
    return fn

def handler(signum, frame):
    raise TimeOutException("Timeout")

@timeout(5)
def my_function_that_takes_long(time_to_sleep):
    time.sleep(time_to_sleep)

if __name__ == '__main__':
    print 'Calling function that takes 2 seconds'
    try:
        my_function_that_takes_long(2)
    except TimeOutException:
        print 'Timed out'

    print 'Calling function that takes 10 seconds'
    try:
        my_function_that_takes_long(10)
    except TimeOutException:
        print 'Timed out'

Autres conseils

Il est là dans la fonction .

urllib2.urlopen(url[, data][, timeout])

par exemple:

urllib2.urlopen("www.google.com", data, 5)
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top