]> git.ipfire.org Git - thirdparty/sqlalchemy/sqlalchemy.git/commitdiff
- The regexp used by the :func:`.url.make_url` function now parses
authorMike Bayer <mike_mp@zzzcomputing.com>
Wed, 23 Oct 2013 19:02:36 +0000 (15:02 -0400)
committerMike Bayer <mike_mp@zzzcomputing.com>
Wed, 23 Oct 2013 19:02:56 +0000 (15:02 -0400)
ipv6 addresses, e.g. surrounded by brackets. [ticket:2851]

doc/build/changelog/changelog_07.rst
lib/sqlalchemy/engine/url.py
test/engine/test_parseconnect.py

index 3a46580db5f1220cc0fd393c3b7f8d5bba600f33..f658a7d87edc01ebbee277c1e3654ee3bf8fc84d 100644 (file)
@@ -6,6 +6,14 @@
 .. changelog::
     :version: 0.7.11
 
+    .. change::
+        :tags: bug, engine
+        :tickets: 2851
+        :versions: 0.8.3, 0.9.0
+
+        The regexp used by the :func:`.url.make_url` function now parses
+        ipv6 addresses, e.g. surrounded by brackets.
+
     .. change::
         :tags: bug, orm
         :tickets: 2807
index b15bfbd5243eb804c98e85e58c29ef9784beb141..08b620752fc12cb38a714926d680fb024b295614 100644 (file)
@@ -71,7 +71,10 @@ class URL(object):
                             else urllib.quote_plus(self.password))
             s += "@"
         if self.host is not None:
-            s += self.host
+            if ':' in self.host:
+                s += "[%s]" % self.host
+            else:
+                s += self.host
         if self.port is not None:
             s += ':' + str(self.port)
         if self.database is not None:
@@ -171,7 +174,10 @@ def _parse_rfc1738_args(name):
                 (?::(?P<password>[^/]*))?
             @)?
             (?:
-                (?P<host>[^/:]*)
+                (?:
+                    \[(?P<ipv6host>[^/]+)\] |
+                    (?P<ipv4host>[^/:]+)
+                )?
                 (?::(?P<port>[^/]*))?
             )?
             (?:/(?P<database>.*))?
@@ -196,6 +202,9 @@ def _parse_rfc1738_args(name):
             components['password'] = \
                 urllib.unquote_plus(components['password'])
 
+        ipv4host = components.pop('ipv4host')
+        ipv6host = components.pop('ipv6host')
+        components['host'] = ipv4host or ipv6host
         name = components.pop('name')
         return URL(name, **components)
     else:
index b7edb655cd380c9f2095aa378edb83bc3f9d4ca7..b9bb3393e70742970f01eb15908e7f6dd8fd20a5 100644 (file)
@@ -16,6 +16,7 @@ class ParseConnectTest(fixtures.TestBase):
         for text in (
             'dbtype://username:password@hostspec:110//usr/db_file.db',
             'dbtype://username:password@hostspec/database',
+            'dbtype+apitype://username:password@hostspec/database',
             'dbtype://username:password@hostspec',
             'dbtype://username:password@/database',
             'dbtype://username@hostspec',
@@ -23,25 +24,31 @@ class ParseConnectTest(fixtures.TestBase):
             'dbtype://hostspec/database',
             'dbtype://hostspec',
             'dbtype://hostspec/?arg1=val1&arg2=val2',
-            'dbtype:///database',
+            'dbtype+apitype:///database',
             'dbtype:///:memory:',
             'dbtype:///foo/bar/im/a/file',
             'dbtype:///E:/work/src/LEM/db/hello.db',
             'dbtype:///E:/work/src/LEM/db/hello.db?foo=bar&hoho=lala',
             'dbtype://',
-            'dbtype://username:password@/db',
-            'dbtype:////usr/local/mailman/lists/_xtest@example.com/memb'
-                'ers.db',
-            'dbtype://username:apples%2Foranges@hostspec/mydatabase',
+            'dbtype://username:password@/database',
+            'dbtype:////usr/local/_xtest@example.com/members.db',
+            'dbtype://username:apples%2Foranges@hostspec/database',
+            'dbtype://username:password@[2001:da8:2004:1000:202:116:160:90]/database?foo=bar',
+            'dbtype://username:password@[2001:da8:2004:1000:202:116:160:90]:80/database?foo=bar'
             ):
             u = url.make_url(text)
-            assert u.drivername == 'dbtype'
-            assert u.username == 'username' or u.username is None
-            assert u.password == 'password' or u.password \
-                == 'apples/oranges' or u.password is None
-            assert u.host == 'hostspec' or u.host == '127.0.0.1' \
-                or not u.host
-            assert str(u) == text
+
+            assert u.drivername in ('dbtype', 'dbtype+apitype')
+            assert u.username in ('username', None)
+            assert u.password in ('password', 'apples/oranges', None)
+            assert u.host in ('hostspec', '127.0.0.1',
+                        '2001:da8:2004:1000:202:116:160:90', '', None), u.host
+            assert u.database in ('database',
+                    '/usr/local/_xtest@example.com/members.db',
+                    '/usr/db_file.db', ':memory:', '',
+                    'foo/bar/im/a/file',
+                    'E:/work/src/LEM/db/hello.db', None), u.database
+            eq_(str(u), text)
 
 class DialectImportTest(fixtures.TestBase):
     def test_import_base_dialects(self):