summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Bayer <mike_mp@zzzcomputing.com>2015-04-08 12:14:56 -0400
committerMike Bayer <mike_mp@zzzcomputing.com>2015-04-08 12:14:56 -0400
commit07153dc0926568b35a907241d8e954ecf0ca54f1 (patch)
treed707c43a37c3c74faa3ea572f07f571235970c42
parent1b83b588f5573799dee8d508be13c252c2e57115 (diff)
downloadsqlalchemy-07153dc0926568b35a907241d8e954ecf0ca54f1.tar.gz
- ensure that the keys we put into the parameters dictionary
for an insert from select are the string names, and not the Column objects. The MSSQL dialect in particular relies upon checking for these keys in params to know if identity insert should be on. references #3360
-rw-r--r--doc/build/changelog/changelog_10.rst5
-rw-r--r--lib/sqlalchemy/sql/dml.py6
-rw-r--r--test/sql/test_query.py9
3 files changed, 16 insertions, 4 deletions
diff --git a/doc/build/changelog/changelog_10.rst b/doc/build/changelog/changelog_10.rst
index 281ebfc43..404e6f1c8 100644
--- a/doc/build/changelog/changelog_10.rst
+++ b/doc/build/changelog/changelog_10.rst
@@ -24,7 +24,10 @@
Fixed a regression where the "last inserted id" mechanics would
fail to store the correct value for MSSQL on an INSERT where the
- primary key value was present in the insert params before execution.
+ primary key value was present in the insert params before execution,
+ as well as in the case where an INSERT from SELECT would state the
+ target columns as column objects, instead of string keys.
+
.. change::
:tags: bug, mssql
diff --git a/lib/sqlalchemy/sql/dml.py b/lib/sqlalchemy/sql/dml.py
index 6a4768fa1..a2a564690 100644
--- a/lib/sqlalchemy/sql/dml.py
+++ b/lib/sqlalchemy/sql/dml.py
@@ -10,7 +10,8 @@ Provide :class:`.Insert`, :class:`.Update` and :class:`.Delete`.
"""
from .base import Executable, _generative, _from_objects, DialectKWArgs
-from .elements import ClauseElement, _literal_as_text, Null, and_, _clone
+from .elements import ClauseElement, _literal_as_text, Null, and_, _clone, \
+ _column_as_key
from .selectable import _interpret_as_from, _interpret_as_select, HasPrefixes
from .. import util
from .. import exc
@@ -544,7 +545,8 @@ class Insert(ValuesBase):
"This construct already inserts value expressions")
self.parameters, self._has_multi_parameters = \
- self._process_colparams(dict((n, Null()) for n in names))
+ self._process_colparams(
+ dict((_column_as_key(n), Null()) for n in names))
self.select_names = names
self.inline = True
diff --git a/test/sql/test_query.py b/test/sql/test_query.py
index 08afc3256..98f375018 100644
--- a/test/sql/test_query.py
+++ b/test/sql/test_query.py
@@ -275,13 +275,20 @@ class QueryTest(fixtures.TestBase):
r = t6.insert().values(manual_id=id).execute()
eq_(r.inserted_primary_key, [12, 1])
- def test_implicit_id_insert_select(self):
+ def test_implicit_id_insert_select_columns(self):
stmt = users.insert().from_select(
(users.c.user_id, users.c.user_name),
users.select().where(users.c.user_id == 20))
testing.db.execute(stmt)
+ def test_implicit_id_insert_select_keys(self):
+ stmt = users.insert().from_select(
+ ["user_id", "user_name"],
+ users.select().where(users.c.user_id == 20))
+
+ testing.db.execute(stmt)
+
def test_row_iteration(self):
users.insert().execute(
{'user_id': 7, 'user_name': 'jack'},