diff options
| author | Mike Bayer <mike_mp@zzzcomputing.com> | 2014-09-05 16:44:42 -0400 |
|---|---|---|
| committer | Mike Bayer <mike_mp@zzzcomputing.com> | 2014-09-05 16:44:42 -0400 |
| commit | 7b766591b05ceeb9c47588d6326a6be56a230594 (patch) | |
| tree | fe0e35edbf3332a1c43428add875691d3b86ab4b | |
| parent | 583287259fbb6d143696b418756ed68e6110cd2d (diff) | |
| download | sqlalchemy-7b766591b05ceeb9c47588d6326a6be56a230594.tar.gz | |
- MySQL boolean symbols "true", "false" work again. 0.9's change
in :ticket:`2682` disallowed the MySQL dialect from making use of the
"true" and "false" symbols in the context of "IS" / "IS NOT", but
MySQL supports this syntax even though it has no boolean type.
MySQL remains "non native boolean", but the :func:`.true`
and :func:`.false` symbols again produce the
keywords "true" and "false", so that an expression like
``column.is_(true())`` again works on MySQL.
fixes #3186
| -rw-r--r-- | doc/build/changelog/changelog_10.rst | 17 | ||||
| -rw-r--r-- | doc/build/changelog/migration_10.rst | 19 | ||||
| -rw-r--r-- | lib/sqlalchemy/dialects/mysql/base.py | 12 | ||||
| -rw-r--r-- | test/dialect/mysql/test_query.py | 23 |
4 files changed, 70 insertions, 1 deletions
diff --git a/doc/build/changelog/changelog_10.rst b/doc/build/changelog/changelog_10.rst index e9b78fe78..55a275659 100644 --- a/doc/build/changelog/changelog_10.rst +++ b/doc/build/changelog/changelog_10.rst @@ -22,6 +22,23 @@ on compatibility concerns, see :doc:`/changelog/migration_10`. .. change:: + :tags: bug, mysql + :tickets: 3186 + + MySQL boolean symbols "true", "false" work again. 0.9's change + in :ticket:`2682` disallowed the MySQL dialect from making use of the + "true" and "false" symbols in the context of "IS" / "IS NOT", but + MySQL supports this syntax even though it has no boolean type. + MySQL remains "non native boolean", but the :func:`.true` + and :func:`.false` symbols again produce the + keywords "true" and "false", so that an expression like + ``column.is_(true())`` again works on MySQL. + + .. seealso:: + + :ref:`bug_3186` + + .. change:: :tags: changed, mssql :tickets: 3182 diff --git a/doc/build/changelog/migration_10.rst b/doc/build/changelog/migration_10.rst index 58aa42df0..2b9e5f0fd 100644 --- a/doc/build/changelog/migration_10.rst +++ b/doc/build/changelog/migration_10.rst @@ -808,6 +808,25 @@ a cursor to be closed unless all results are fully fetched. :ticket:`2515` +.. _bug_3186: + +MySQL boolean symbols "true", "false" work again +------------------------------------------------ + +0.9's overhaul of the IS/IS NOT operators as well as boolean types in +:ticket:`2682` disallowed the MySQL dialect from making use of the +"true" and "false" symbols in the context of "IS" / "IS NOT". Apparently, +even though MySQL has no "boolean" type, it supports IS / IS NOT when the +special "true" and "false" symbols are used, even though these are otherwise +synonymous with "1" and "0" (and IS/IS NOT don't work with the numerics). + +So the change here is that the MySQL dialect remains "non native boolean", +but the :func:`.true` and :func:`.false` symbols again produce the +keywords "true" and "false", so that an expression like ``column.is_(true())`` +again works on MySQL. + +:ticket:`3186` + .. _change_3182: PyODBC driver name is required with hostname-based SQL Server connections diff --git a/lib/sqlalchemy/dialects/mysql/base.py b/lib/sqlalchemy/dialects/mysql/base.py index 4dccd2760..247b7a143 100644 --- a/lib/sqlalchemy/dialects/mysql/base.py +++ b/lib/sqlalchemy/dialects/mysql/base.py @@ -1637,6 +1637,14 @@ class MySQLCompiler(compiler.SQLCompiler): value = value.replace('\\', '\\\\') return value + # override native_boolean=False behavior here, as + # MySQL still supports native boolean + def visit_true(self, element, **kw): + return "true" + + def visit_false(self, element, **kw): + return "false" + def get_select_precolumns(self, select): """Add special MySQL keywords in place of DISTINCT. @@ -2215,6 +2223,10 @@ class MySQLDialect(default.DefaultDialect): name = 'mysql' supports_alter = True + # MySQL has no true "boolean" type; we + # allow for the "true" and "false" keywords, however + supports_native_boolean = False + # identifiers are 64, however aliases can be 255... max_identifier_length = 255 max_index_name_length = 64 diff --git a/test/dialect/mysql/test_query.py b/test/dialect/mysql/test_query.py index dd11fe2b4..e085d86c1 100644 --- a/test/dialect/mysql/test_query.py +++ b/test/dialect/mysql/test_query.py @@ -1,11 +1,32 @@ # coding: utf-8 -from sqlalchemy.testing import eq_ +from sqlalchemy.testing import eq_, is_ from sqlalchemy import * from sqlalchemy.testing import fixtures, AssertsCompiledSQL from sqlalchemy import testing +class IdiosyncrasyTest(fixtures.TestBase, AssertsCompiledSQL): + __only_on__ = 'mysql' + __backend__ = True + + def test_is_boolean_symbols_despite_no_native(self): + is_( + testing.db.scalar(select([cast(true().is_(true()), Boolean)])), + True + ) + + is_( + testing.db.scalar(select([cast(true().isnot(true()), Boolean)])), + False + ) + + is_( + testing.db.scalar(select([cast(false().is_(false()), Boolean)])), + True + ) + + class MatchTest(fixtures.TestBase, AssertsCompiledSQL): __only_on__ = 'mysql' __backend__ = True |
