Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

Already on GitHub? Sign in to your account

Pickup proxy settings from http_proxy environment variable #754

Closed
prongs opened this Issue Apr 23, 2013 · 7 comments

Comments

Projects
None yet
3 participants

prongs commented Apr 23, 2013

I made an app with facebook login and since I'm behind proxy, I'm having trouble getting access token. My handler class is subclassed from FacebookGraphMixin and in the function get_authenticated_user, it calls the function fetch of an http client obtained by self.get_auth_http_client. Now I thought I could overwrite get_auth_http_client to manually set proxy in the resulting client but I don't see any way of setting proxy for AsyncHTTTPClient. The proxy can only be set on an HTTPClient which is instantiated by AsyncHTTPClient in the function fetch. Now it does not make sense to also have to subclass AsyncHTTPClient and HTTPClient, I suggest while initializing HTTPClient, we set proxy_host and proxy_port according to the environment variable http_proxy. This is a standard way of setting proxy for python applications. Many python applications including pip and easy_install also use this, .

Owner

bdarnell commented Apr 24, 2013

The default AsyncHTTPClient implementation (simple_httpclient) doesn't support proxies at all. The alternative, curl_httpclient, supports proxies and I believe will use the http_proxy environment variable automatically.

See the docs at http://www.tornadoweb.org/en/stable/httpclient.html#tornado.httpclient.AsyncHTTPClient.configure
to configure your application to use curl_httpclient instead of simple_httpclient. If curl_httpclient doesn't pick up the environment variable automatically, you can pass 'defaults={'proxy_host': '...'}' as a keyword argument to AsyncHTTPClient.configure (this needs to be documented).

prongs commented Apr 24, 2013

I tried with

    AsyncHTTPClient.configure("tornado.curl_httpclient.CurlAsyncHTTPClient")

and

    AsyncHTTPClient.configure("tornado.curl_httpclient.CurlAsyncHTTPClient", defaults=dict(proxy_host='x.y.z.w', proxy_port=3128))

but still I get

Traceback (most recent call last):
  File "C:\Python27\lib\site-packages\tornado\web.py", line 1019, in wrapper
    return callback(*args, **kwargs)
  File "C:\Python27\lib\site-packages\tornado\auth.py", line 1143, in _on_access_token
    future.set_exception(AuthError('Facebook auth error: %s' % str(response)))
  File "C:\Python27\lib\site-packages\tornado\concurrent.py", line 87, in set_exception
    self._set_done()
  File "C:\Python27\lib\site-packages\tornado\concurrent.py", line 97, in _set_done
    cb(self)
  File "C:\Python27\lib\site-packages\tornado\auth.py", line 88, in _auth_future_to_callback
    callback(result)
  File "c:\Users\Rajat\Documents\GitHub\Testimonial\handlers.py", line 75, in _on_auth
    raise HTTPError(500, "Facebook auth failed")
HTTPError: HTTP 500: Internal Server Error (Facebook auth failed)

with tornado version 3.0.1.

I put the configure call before starting the application and server. Is that correct place for it?

prongs commented Apr 24, 2013

I do get the following warning in the console:

WARNING:tornado.general:Facebook auth error: HTTPResponse(_body=None,buffer=None,code=599,effective_url='https://graph.facebook.com/oauth/access_token?client_secret=something&code=something&client_id=something&redirect_uri=http%3A%2F%2Flocalhost%3A8888%2Fauth%2Flogin%3Fnext%3D%252F',error=CurlError('HTTP 599: SSL certificate problem: unable to get local issuer certificate',),headers={},reason='Unknown',request=<tornado.httpclient.HTTPRequest object at 0x02B60710>,request_time=1.2690000534057617,time_info={})
WARNING:tornado.general:500 GET /auth/login?next=%2F&code=something (::1): Facebook auth failed
ERROR:tornado.access:500 GET /auth/login?next=%2F&code=something (::1) 1283.00ms
Owner

bdarnell commented Apr 25, 2013

It looks like your configure call is fine. The curl error indicates that your curl installation is missing its root certificate list (or that the server you're talking to does not have a valid certificate). If it's the former, see this page for information on making curl use your OS-provided SSL certificate list or installing a copy of the mozilla list.

prongs commented Apr 25, 2013

This worked:

defaults = dict(ca_certs=certifi.where())
http_proxy = os.environ.get('http_proxy')
if http_proxy:
    if http_proxy[:7] == "http://":
        http_proxy = http_proxy[7:]
    defaults['proxy_host'], defaults['proxy_port'] = http_proxy.split(":")
    defaults['proxy_port'] = int(defaults['proxy_port'])

AsyncHTTPClient.configure("tornado.curl_httpclient.CurlAsyncHTTPClient", defaults=defaults)

@prongs prongs closed this Apr 25, 2013

@kakawait kakawait referenced this issue in jakubroztocil/lastfmclient Sep 24, 2014

Open

Support http proxy #2

Contributor

lilydjwg commented Aug 13, 2015

CurlAsyncHTTPClient won't pick up those enviromental variables because it's explicitly disabled (set an empty string as the PROXY option). Sadly, that option can't be unset.

Owner

bdarnell commented Aug 16, 2015

OK. In that case you must tell tornado that you want to use a proxy by setting the proxy_host and proxy_port arguments.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment