-
Notifications
You must be signed in to change notification settings - Fork 660
Proxies can be sent as a string #300
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you, I think this change would make API much better and more pleasant to use.
Just a couple of changes and it should be ready to go. As for the doc – I suggest you to not care about it for now. I wanted to rewrite the proxy section anyway, and this would be another good reason to finally get to it.
PS. Points for a good test! 😀
geopy/geocoders/base.py
Outdated
@@ -185,6 +187,10 @@ def __init__( | |||
else options.default_ssl_context) | |||
|
|||
if self.proxies: | |||
if isinstance(self.proxies, str): | |||
self.scheme = self.proxies.split('://')[0] |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
First of all, proxies
shouldn't affect self.scheme
in any way.
Proxy scheme and URL scheme are totally different and doesn't need to match.
For example, for proxies = 'http://my_proxy_server:8080'
and self.scheme = 'https'
the client would send a CONNECT method to the proxy (in plaintext), and then start TLS negotiation with the remote using that TCP connection.
Just remove this line and it will be fine.
geopy/geocoders/base.py
Outdated
@@ -185,6 +187,10 @@ def __init__( | |||
else options.default_ssl_context) | |||
|
|||
if self.proxies: | |||
if isinstance(self.proxies, str): | |||
self.scheme = self.proxies.split('://')[0] | |||
self.proxies = {self.scheme: self.proxies} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Given that we verify above that self.scheme
is either http
or https
, I would suggest to specify proxy for both schemes instead of the current one.
Consider this situation:
g = SomeGeocoder(proxies='http://my_proxy_server:8080', scheme='https')
g.scheme = 'http'
After assignment proxy wouldn't be used, which is unexpected.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess I wasn't clear enough on this one.
This is what I meant:
self.proxies = {'http': self.proxies, 'https': self.proxies}
That way my snippet above will work correctly.
geopy/geocoders/base.py
Outdated
@@ -185,6 +187,10 @@ def __init__( | |||
else options.default_ssl_context) | |||
|
|||
if self.proxies: | |||
if isinstance(self.proxies, str): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For compatibility with py2, geopy.compat.string_compare
should be used instead of str
.
@@ -70,6 +70,8 @@ class options(object): | |||
If specified, tunnel requests through the specified proxy. | |||
E.g., ``{"https": "192.0.2.0"}``. For more information, see | |||
documentation on :class:`urllib.request.ProxyHandler`. | |||
Can be sent as a string ``"https://192.0.2.0"``, this will | |||
automatically set the scheme to the ``https`` |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
To be honest, I don't like it 🤔. But I'm not ready to propose a better phrasing for now as well.
Let's just keep it, but I'll get to this later after merging.
Thanks as usual for review and friendliness. Yeah, it's definitely going to be easier to use.
Thank you very much, putting the right thought into the docs is still the most tough part for me.
Thanks, I didn't do much just copied the exsiting test. It took me some time to understand that there is a default scheme. This is why I put 2 tests, one with the https which is default, and one with http. But they both set explicitly, I think we can omit setting it explicitly in the https test, should we? |
test/test_proxy.py
Outdated
base_http = urlopen(self.remote_website_http, timeout=self.timeout) | ||
base_html = base_http.read() | ||
geocoder_dummy = DummyGeocoder(proxies=self.proxy_url, | ||
geocoder_dummy = DummyGeocoder(proxies=self.proxy_url, scheme='http', |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
No, I don't think we need to test two schemes in two almost identical integration tests, which aren't cheap with regards to time.
It would be better to keep the previous single test, and add a new unit test here. Something like this:
g = DummyGeocoder(proxies=self.proxy_url, scheme='http')
self.assertDictEqual(g.proxies, {'http': self.proxy_url, 'https': self.proxy_url})
That should be enough. We already tested that the g.proxies
dict is respected in the integration tests, but we didn't check if both schemes are respected – which is exactly what this test does.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am not sure if I get this right, but this will assert error:
self.assertDictEqual(g.proxies, {'http': self.proxy_url, 'https': self.proxy_url})
So I added 2 DummyGeocoders to check if both schemes are respected.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Have you by chance missed this comment? #300 (comment)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Also it would've been better if it was in a separate test_*
function.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Oh yeah, I did miss this comment, pardon my inattention.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks! Just a couple of simple corrections and it's ready to go 👍
test/test_proxy.py
Outdated
def test_geocoder_constructor_uses_str_proxy(self): | ||
base_http = urlopen(self.remote_website_http, timeout=self.timeout) | ||
base_html = base_http.read() | ||
geocoder_dummy = DummyGeocoder(proxies=self.proxy_url, scheme='http', |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is there any reason to set the scheme
kwarg explicitly? If not, could you please remove that?
test/test_proxy.py
Outdated
base_html = base_http.read() | ||
geocoder_dummy = DummyGeocoder(proxies=self.proxy_url, scheme='http', | ||
timeout=self.timeout) | ||
print(geocoder_dummy.scheme, geocoder_dummy.proxies, 'proxy') |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🙃
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
whoops 😅
Thanks! 🎉 |
Yay! Thank you very much, I'm looking forward to continue my work with you (can we call it this way?) 🎂 |
Of course, you're very welcome! I'm very grateful to you for your efforts on making geopy better. ✨🦄 |
this commit fixes #290