summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Bayer <mike_mp@zzzcomputing.com>2016-08-04 12:34:55 -0400
committerMike Bayer <mike_mp@zzzcomputing.com>2016-08-04 12:34:55 -0400
commitaf6f4ab938f1ef66491cf239c91ffff393275d95 (patch)
treee61fcade57851acab0420679881413a6e6456a75
parentce1492ef3aae692a3dc10fff400e178e7b2edff8 (diff)
downloadsqlalchemy-af6f4ab938f1ef66491cf239c91ffff393275d95.tar.gz
Propagate kwargs to all MySQL CAST paths
Change-Id: I23a6abb26bbbe3d118887d043ce761fc4572d8d2 Fixes: #3766
-rw-r--r--doc/build/changelog/changelog_11.rst7
-rw-r--r--lib/sqlalchemy/dialects/mysql/base.py8
-rw-r--r--test/dialect/mysql/test_compiler.py35
3 files changed, 46 insertions, 4 deletions
diff --git a/doc/build/changelog/changelog_11.rst b/doc/build/changelog/changelog_11.rst
index 569373529..fe6be3b17 100644
--- a/doc/build/changelog/changelog_11.rst
+++ b/doc/build/changelog/changelog_11.rst
@@ -22,6 +22,13 @@
:version: 1.1.0
.. change::
+ :tags: bug, mysql
+ :tickets: 3766
+
+ Fixed bug where the "literal_binds" flag would not be propagated
+ to a CAST expression under MySQL.
+
+ .. change::
:tags: change, orm
Passing False to :meth:`.Query.order_by` in order to cancel
diff --git a/lib/sqlalchemy/dialects/mysql/base.py b/lib/sqlalchemy/dialects/mysql/base.py
index 5abb1f3d6..7ab9fad69 100644
--- a/lib/sqlalchemy/dialects/mysql/base.py
+++ b/lib/sqlalchemy/dialects/mysql/base.py
@@ -811,13 +811,13 @@ class MySQLCompiler(compiler.SQLCompiler):
else:
return None
- def visit_cast(self, cast, **kwargs):
+ def visit_cast(self, cast, **kw):
# No cast until 4, no decimals until 5.
if not self.dialect._supports_cast:
util.warn(
"Current MySQL version does not support "
"CAST; the CAST will be skipped.")
- return self.process(cast.clause.self_group())
+ return self.process(cast.clause.self_group(), **kw)
type_ = self.process(cast.typeclause)
if type_ is None:
@@ -825,9 +825,9 @@ class MySQLCompiler(compiler.SQLCompiler):
"Datatype %s does not support CAST on MySQL; "
"the CAST will be skipped." %
self.dialect.type_compiler.process(cast.typeclause.type))
- return self.process(cast.clause.self_group())
+ return self.process(cast.clause.self_group(), **kw)
- return 'CAST(%s AS %s)' % (self.process(cast.clause), type_)
+ return 'CAST(%s AS %s)' % (self.process(cast.clause, **kw), type_)
def render_literal_value(self, value, type_):
value = super(MySQLCompiler, self).render_literal_value(value, type_)
diff --git a/test/dialect/mysql/test_compiler.py b/test/dialect/mysql/test_compiler.py
index 8a7893445..88f9235e1 100644
--- a/test/dialect/mysql/test_compiler.py
+++ b/test/dialect/mysql/test_compiler.py
@@ -12,6 +12,8 @@ from sqlalchemy import Table, MetaData, Column, select, String, \
from sqlalchemy.dialects.mysql import base as mysql
from sqlalchemy.testing import fixtures, AssertsCompiledSQL
+from sqlalchemy.testing import mock
+from sqlalchemy import testing
from sqlalchemy.sql import table, column
import re
@@ -414,6 +416,39 @@ class SQLTest(fixtures.TestBase, AssertsCompiledSQL):
self.assert_compile(
cast(t.c.col, type_), "CAST(t.col AS SIGNED INTEGER)")
+ def test_cast_literal_bind(self):
+ expr = cast(column('foo', Integer) + 5, Integer())
+
+ self.assert_compile(
+ expr,
+ "CAST(foo + 5 AS SIGNED INTEGER)",
+ literal_binds=True
+ )
+
+ def test_unsupported_cast_literal_bind(self):
+ expr = cast(column('foo', Integer) + 5, Float)
+
+ with expect_warnings(
+ "Datatype FLOAT does not support CAST on MySQL;"
+ ):
+ self.assert_compile(
+ expr,
+ "(foo + 5)",
+ literal_binds=True
+ )
+
+ dialect = mysql.MySQLDialect()
+ dialect.server_version_info = (3, 9, 8)
+ with expect_warnings(
+ "Current MySQL version does not support CAST"
+ ):
+ eq_(
+ str(expr.compile(
+ dialect=dialect,
+ compile_kwargs={"literal_binds": True})),
+ "(foo + 5)"
+ )
+
def test_unsupported_casts(self):
t = sql.table('t', sql.column('col'))