redirect to bogus URL generates low-level exception; can do better

This issue is reported in tickets [#38](https://github.com/shazow/urllib3/issues/38) and  [#39](https://github.com/shazow/urllib3/issues/39) in urllib3.

These two URLs are examples that generate bogus redirect URLs.  The exceptions raised by urllib3 and by requests are not useful.  Can we create a more useful exception that says what is going on and can be caught specifically?

Is this a known issue?

Here are the two example URLs:

> http://stats.e-go.gr/rx.asp?nWebSrvID=100230&nCatID=23425&nLevelId=-20&target=mailto%3Aadvertising%40pegasusinteractive%2Egr
> 
> http://stclairshores.patch.com/articles/shores-veteran-to-receive-complimentary-wedding-on-veterans-day

```
>>> r = requests.get('http://stats.e-go.gr/rx.asp?nWebSrvID=100230&nCatID=23425&nLevelId=-20&target=mailto%3Aadvertising%40pegasusinteractive%2Egr', allow_redirects=False)
>>> r
<Response [302]>
>>> r.headers
{'content-length': '161', 'x-powered-by': 'ASP.NET', 'set-cookie': 'nUserID=4862144; expires=Mon, 21-Jan-2013 22:00:00 GMT; path=/, ASPSESSIONIDCSQABRTR=NOJOKALCFLCHFCALIBBMFJIJ; path=/', 'expires': 'Mon, 23 Jan 2012 13:40:53 GMT', 'server': 'Microsoft-IIS/6.0', 'location': 'mailto:advertising@pegasusinteractive.gr', 'cache-control': 'False', 'date': 'Mon, 23 Jan 2012 13:41:53 GMT', 'p3p': 'CP="CURa ADMa DEVa PSAo PSDo OUR BUS UNI PUR INT DEM STA PRE COM NAV OTC NOI DSP COR"', 'content-type': 'text/html'}
>>> 
>>> 
>>> r = requests.get('http://stats.e-go.gr/rx.asp?nWebSrvID=100230&nCatID=23425&nLevelId=-20&target=mailto%3Aadvertising%40pegasusinteractive%2Egr')Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python2.7/dist-packages/requests/api.py", line 50, in get
    return request('get', url, **kwargs)
  File "/usr/local/lib/python2.7/dist-packages/requests/api.py", line 38, in request
    return s.request(method=method, url=url, **kwargs)
  File "/usr/local/lib/python2.7/dist-packages/requests/sessions.py", line 200, in request
    r.send(prefetch=prefetch)
  File "/usr/local/lib/python2.7/dist-packages/requests/models.py", line 514, in send
    self._build_response(r)
  File "/usr/local/lib/python2.7/dist-packages/requests/models.py", line 253, in _build_response
    request.send()
  File "/usr/local/lib/python2.7/dist-packages/requests/models.py", line 430, in send
    conn = self._poolmanager.connection_from_url(url)
  File "/usr/local/lib/python2.7/dist-packages/requests/packages/urllib3/poolmanager.py", line 94, in connection_from_url
    scheme, host, port = get_host(url)
  File "/usr/local/lib/python2.7/dist-packages/requests/packages/urllib3/connectionpool.py", line 524, in get_host
    port = int(port)
ValueError: invalid literal for int() with base 10: 'advertising%40pegasusinteractive.gr'
>>> 
```

notice the http://http:// at the beginning of the new location! ---  (nice work Patch.com :-)

```
>>> r = requests.get('http://stclairshores.patch.com/articles/shores-veteran-to-receive-complimentary-wedding-on-veterans-day', allow_redirects=False)
>>> r.headers
{'status': '302', 'content-length': '160', 'content-encoding': 'gzip', 'set-cookie': 'p13n=%5B%5D; path=/, _patch_session=BAh7BzoPc2Vzc2lvbl9pZCIlNmEzYzM4YzZjMWIxMTdiNDkxMmEwNmEwM2JmZDQzYTU6FnByb21wdF9mb3Jfc3VydmV5aQA%3D--547af227538bb1d039809a3d01eaadb320a9a42b; domain=patch.com; path=/', 'x-powered-by': 'Phusion Passenger (mod_rails/mod_rack) 3.0.11', 'vary': 'Accept-Encoding', 'server': 'Apache/2.2.15 (Unix) mod_ssl/2.2.15 OpenSSL/0.9.8l Phusion_Passenger/3.0.11', 'x-runtime': '15', 'location': 'http://http://www.dailytribune.com/articles/2011/11/09/news/doc4ebb336cad1c7378471368.txt?viewmode=fullstory', 'cache-control': 'no-cache', 'date': 'Mon, 23 Jan 2012 13:32:36 GMT', 'content-type': 'text/html; charset=utf-8', 'x-rack-cache': 'miss'}
>>> 
>>> 
>>> r = requests.get('http://stclairshores.patch.com/articles/shores-veteran-to-receive-complimentary-wedding-on-veterans-day')Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/usr/local/lib/python2.7/dist-packages/requests/api.py", line 50, in get
    return request('get', url, **kwargs)
  File "/usr/local/lib/python2.7/dist-packages/requests/api.py", line 38, in request
    return s.request(method=method, url=url, **kwargs)
  File "/usr/local/lib/python2.7/dist-packages/requests/sessions.py", line 200, in request
    r.send(prefetch=prefetch)
  File "/usr/local/lib/python2.7/dist-packages/requests/models.py", line 514, in send
    self._build_response(r)
  File "/usr/local/lib/python2.7/dist-packages/requests/models.py", line 253, in _build_response
    request.send()
  File "/usr/local/lib/python2.7/dist-packages/requests/models.py", line 430, in send
    conn = self._poolmanager.connection_from_url(url)
  File "/usr/local/lib/python2.7/dist-packages/requests/packages/urllib3/poolmanager.py", line 94, in connection_from_url
    scheme, host, port = get_host(url)
  File "/usr/local/lib/python2.7/dist-packages/requests/packages/urllib3/connectionpool.py", line 524, in get_host
    port = int(port)
ValueError: invalid literal for int() with base 10: ''
```


Hmm, all we currently do is check that a schema exists in the url to verify that it's kosher.  


This problem is not only with redirects:

``` python
>>> requests.get('http://http://')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "requests\api.py", line 51, in get
    return request('get', url, **kwargs)
  File "requests\api.py", line 39, in request
    return s.request(method=method, url=url, **kwargs)
  File "requests\sessions.py", line 200, in request
    r.send(prefetch=prefetch)
  File "requests\models.py", line 463, in send
    conn = self._poolmanager.connection_from_url(url)
  File "requests\packages\urllib3\poolmanager.py", line 89, in connection_from_url
    scheme, host, port = get_host(url)
  File "requests\packages\urllib3\connectionpool.py", line 557, in get_host
    port = int(port)
ValueError: invalid literal for int() with base 10: ''
```


See also #323


Solving the problem where we hit a mailto: URL isn't too bad, we just have to sanity check the scheme. I'm reluctant to throw exceptions only for mailto: URLs: might be worth deciding which schemes requests supports, and explicitly checking against them.

The case of the other two examples here is more difficult. Neither is a valid URL, and urlparse doesn't check for URL validity. My reading of [RFC 3986](http://tools.ietf.org/html/rfc3986) is that a colon is not a valid character in a domain name, but checking for that in a stupid way makes using IPv6 literals impossible.

I see two obvious way of handling this. I could write a regex to determine if the netloc is an IP literal or a domain name, and throw a useful exception if it can't decide. Alternatively, we could catch the exceptions being raised by urllib3 and rethrow them. Doing that seems wrong, but I can't entirely articulate why.


We support `http` and `https`. That shouldn't be changing any time soon.