No creo que volver a plantear la excepción sea una forma adecuada de resolver este problema.
Como dijo @ Jonathan Vanasco,
if you're opening a.com , and it 301 redirects to b.com , urlopen will automatically follow that because an HTTPError with a redirect was raised. if b.com causes the URLError , the code above marks a.com as not existing
Mi solución es sobrescribir redirect_request
de urllib2.HTTPRedirectHandler
import urllib2
class NewHTTPRedirectHandler(urllib2.HTTPRedirectHandler):
def redirect_request(self, req, fp, code, msg, headers, newurl):
m = req.get_method()
if (code in (301, 302, 303, 307) and m in ("GET", "HEAD")
or code in (301, 302, 303) and m == "POST"):
newurl = newurl.replace(' ', '%20')
newheaders = dict((k,v) for k,v in req.headers.items()
if k.lower() not in ("content-length", "content-type")
)
# reuse the req object
# mind that req will be changed if redirection happends
req.__init__(newurl,
headers=newheaders,
origin_req_host=req.get_origin_req_host(),
unverifiable=True)
return req
else:
raise HTTPError(req.get_full_url(), code, msg, headers, fp)
opener = urllib2.build_opener(NewHTTPRedirectHandler)
urllib2.install_opener(opener)
# mind that req will be changed if redirection happends
#req = urllib2.Request('http://127.0.0.1:5000')
req = urllib2.Request('http://www.google.com/')
try:
response = urllib2.urlopen(req)
except urllib2.URLError as e:
print 'error'
print req.get_full_url()
else:
print 'normal'
print response.geturl()
vamos a tratar de redirigir la dirección URL a una URL desconocida:
import os
from flask import Flask,redirect
app = Flask(__name__)
@app.route('/')
def hello():
# return 'hello world'
return redirect("http://a.com", code=302)
if __name__ == '__main__':
port = int(os.environ.get('PORT', 5000))
app.run(host='0.0.0.0', port=port)
Y el resultado es:
error
http://a.com/
normal
http://www.google.com/
+1 Sí, eso es lo que estaba buscando. Pensé que era simple, pero simplemente no estaba llegando a través de google o prueba y error. – mwolfe02
urlib2.urlopen() seguirá las redirecciones, por lo que 'e.url_original' sería más apropiado. no he podido averiguar cómo obtener el 'url_actual' que desencadenó el URLError. no estoy tratando de nitpick aquí. si está abriendo a.com, y 301 redirecciona a b.com, urlopen automáticamente lo seguirá porque se generó un HTTPError con una redirección. si b.com causa URLError, el código anterior marca a.com como no existente; cuando funciona y funciona perfectamente, solo apunta a una URL incorrecta en b.com. –
'e.reason =" URL no existe "' proporcionará 'AttributeError: no se puede establecer el atributo' – histrio