]> git.ipfire.org Git - thirdparty/sqlalchemy/sqlalchemy.git/commitdiff
don't check standard_conforming_strings less than server version 8.2
authorMike Bayer <mike_mp@zzzcomputing.com>
Sat, 14 Nov 2020 00:35:25 +0000 (19:35 -0500)
committerMike Bayer <mike_mp@zzzcomputing.com>
Sat, 14 Nov 2020 00:35:25 +0000 (19:35 -0500)
Fixed a small regression where the query for "show
standard_conforming_strings" upon initialization would be emitted even if
the server version info were detected as less than version 8.2, previously
it would only occur for server version 8.2 or greater. The query fails on
Amazon Redshift which reports a PG server version older than this value.

Fixes: #5698
Change-Id: Ib27ce4b05106d986a618597e4cf253504f981bf1

doc/build/changelog/unreleased_14/5698.rst [new file with mode: 0644]
lib/sqlalchemy/dialects/postgresql/base.py
test/dialect/postgresql/test_dialect.py

diff --git a/doc/build/changelog/unreleased_14/5698.rst b/doc/build/changelog/unreleased_14/5698.rst
new file mode 100644 (file)
index 0000000..a011d8b
--- /dev/null
@@ -0,0 +1,10 @@
+.. change::
+    :tags: bug, postgresql
+    :tickets: 5698
+
+    Fixed a small regression where the query for "show
+    standard_conforming_strings" upon initialization would be emitted even if
+    the server version info were detected as less than version 8.2, previously
+    it would only occur for server version 8.2 or greater. The query fails on
+    Amazon Redshift which reports a PG server version older than this value.
+
index bf257ab3fd422747bc5c4ff2c5f1e5a8d49b5c53..d738393e78794dd9672bb0a6e82e6c29f17cd81d 100644 (file)
@@ -2922,12 +2922,15 @@ class PGDialect(default.DefaultDialect):
         # http://www.postgresql.org/docs/9.3/static/release-9-2.html#AEN116689
         self.supports_smallserial = self.server_version_info >= (9, 2)
 
-        std_string = connection.exec_driver_sql(
-            "show standard_conforming_strings"
-        ).scalar()
-        self._backslash_escapes = (
-            self.server_version_info < (8, 2) or std_string == "off"
-        )
+        if self.server_version_info < (8, 2):
+            self._backslash_escapes = False
+        else:
+            # ensure this query is not emitted on server version < 8.2
+            # as it will fail
+            std_string = connection.exec_driver_sql(
+                "show standard_conforming_strings"
+            ).scalar()
+            self._backslash_escapes = std_string == "off"
 
         self._supports_create_index_concurrently = (
             self.server_version_info >= (8, 2)
index d1e9c2e6de697f379977b5a5d90bce815fa844e0..bfdd14845421e2e414a141d1c5a0974c59da9e67 100644 (file)
@@ -103,6 +103,12 @@ class DialectTest(fixtures.TestBase):
                 "(Red Hat 4.8.5-11), 64-bit",
                 (10,),
             ),
+            (
+                "PostgreSQL 8.0.2 on i686-pc-linux-gnu, compiled by GCC gcc "
+                "(GCC) 3.4.2 20041017 (Red Hat 3.4.2-6.fc3), "
+                "Redshift 1.0.12103",
+                (8, 0, 2),
+            ),
         ]:
             eq_(dialect._get_server_version_info(mock_conn(string)), version)
 
@@ -764,6 +770,38 @@ class MiscBackendTest(
             ".".join(str(x) for x in v)
         )
 
+    @testing.combinations(
+        ((8, 1), False, False),
+        ((8, 1), None, False),
+        ((11, 5), True, False),
+        ((11, 5), False, True),
+    )
+    def test_backslash_escapes_detection(
+        self, version, explicit_setting, expected
+    ):
+        engine = engines.testing_engine()
+
+        def _server_version(conn):
+            return version
+
+        if explicit_setting is not None:
+
+            @event.listens_for(engine, "connect", insert=True)
+            @event.listens_for(engine, "first_connect", insert=True)
+            def connect(dbapi_connection, connection_record):
+                cursor = dbapi_connection.cursor()
+                cursor.execute(
+                    "SET SESSION standard_conforming_strings = %s"
+                    % ("off" if not explicit_setting else "on")
+                )
+                dbapi_connection.commit()
+
+        with mock.patch.object(
+            engine.dialect, "_get_server_version_info", _server_version
+        ):
+            with engine.connect():
+                eq_(engine.dialect._backslash_escapes, expected)
+
     def test_readonly_flag_connection(self):
         with testing.db.connect() as conn:
             # asyncpg requires serializable for readonly..