From 5705b10d57d230ebd653b6c4dfef2835dad6c2fa Mon Sep 17 00:00:00 2001 From: Bernie Hackett Date: Fri, 20 Oct 2017 14:59:19 -0700 Subject: [PATCH] PYTHON-1378 - Fix DNS seedlist discovery with Eventlet This change also adds Python 3 support for dnspython versions back to 1.13.0, the first version to support Python 3. --- pymongo/uri_parser.py | 21 ++++++++++++++++++--- setup.py | 2 +- 2 files changed, 19 insertions(+), 4 deletions(-) diff --git a/pymongo/uri_parser.py b/pymongo/uri_parser.py index 262688b21..37aaccfdb 100644 --- a/pymongo/uri_parser.py +++ b/pymongo/uri_parser.py @@ -18,8 +18,11 @@ import re import warnings try: + # Eventlet monkey patches dnspython with a copy it bundles. + # We have to import dns.exception to ensure we can catch the + # patched DNSException. + import dns.exception from dns import rdata, resolver - from dns.exception import DNSException _HAVE_DNSPYTHON = True except ImportError: _HAVE_DNSPYTHON = False @@ -267,12 +270,24 @@ def split_hosts(hosts, default_port=DEFAULT_PORT): _BAD_DB_CHARS = re.compile('[' + re.escape(r'/ "$') + ']') +if PY3: + def maybe_decode(text): + if isinstance(text, bytes): + return text.decode() + return text +else: + def maybe_decode(text): + return text + + def _get_dns_srv_hosts(hostname): try: results = resolver.query('_mongodb._tcp.' + hostname, 'SRV') - return [(res.target.to_text(omit_final_dot=True), res.port) + # Some older versions of dnspython return bytes for target.to_text. + return [(maybe_decode( + res.target.to_text(omit_final_dot=True)), res.port) for res in results] - except DNSException as exc: + except dns.exception.DNSException as exc: raise ConfigurationError(str(exc)) diff --git a/setup.py b/setup.py index ef5f9def8..ba96a6556 100755 --- a/setup.py +++ b/setup.py @@ -320,7 +320,7 @@ vi = sys.version_info if vi[0] == 2: extras_require = {'tls': ["ipaddress"], 'srv': ["dnspython>=1.8.0,<2.0.0"]} else: - extras_require = {'tls': [], 'srv': ["dnspython>=1.15.0,<2.0.0"]} + extras_require = {'tls': [], 'srv': ["dnspython>=1.13.0,<2.0.0"]} if sys.platform == 'win32': extras_require['gssapi'] = ["winkerberos>=0.5.0"] if vi[0] == 2 and vi < (2, 7, 9) or vi[0] == 3 and vi < (3, 4):