summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--doc/build/changelog/changelog_08.rst12
-rw-r--r--lib/sqlalchemy/dialects/mssql/pyodbc.py3
-rw-r--r--test/sql/test_unicode.py22
3 files changed, 36 insertions, 1 deletions
diff --git a/doc/build/changelog/changelog_08.rst b/doc/build/changelog/changelog_08.rst
index 01590b090..15f38fc45 100644
--- a/doc/build/changelog/changelog_08.rst
+++ b/doc/build/changelog/changelog_08.rst
@@ -12,6 +12,18 @@
:version: 0.8.7
.. change::
+ :tags: bug, mssql
+ :versions: 1.0.0, 0.9.7
+ :tickets: 3091
+
+ In the SQL Server pyodbc dialect, repaired the implementation
+ for the ``description_encoding`` dialect parameter, which when
+ not explicitly set was preventing cursor.description from
+ being parsed correctly in the case of result sets that
+ contained names in alternate encodings. This parameter
+ shouldn't be needed going forward.
+
+ .. change::
:tags: bug, sql
:versions: 1.0.0, 0.9.7
:tickets: 3124
diff --git a/lib/sqlalchemy/dialects/mssql/pyodbc.py b/lib/sqlalchemy/dialects/mssql/pyodbc.py
index ab45fa25e..31c55f502 100644
--- a/lib/sqlalchemy/dialects/mssql/pyodbc.py
+++ b/lib/sqlalchemy/dialects/mssql/pyodbc.py
@@ -250,8 +250,9 @@ class MSDialect_pyodbc(PyODBCConnector, MSDialect):
)
def __init__(self, description_encoding=None, **params):
+ if 'description_encoding' in params:
+ self.description_encoding = params.pop('description_encoding')
super(MSDialect_pyodbc, self).__init__(**params)
- self.description_encoding = description_encoding
self.use_scope_identity = self.use_scope_identity and \
self.dbapi and \
hasattr(self.dbapi.Cursor, 'nextset')
diff --git a/test/sql/test_unicode.py b/test/sql/test_unicode.py
index 99de16f7f..fc5205a3d 100644
--- a/test/sql/test_unicode.py
+++ b/test/sql/test_unicode.py
@@ -79,6 +79,28 @@ class UnicodeSchemaTest(fixtures.TestBase):
assert t2.select().execute().fetchall() == [(1, 1)]
assert t3.select().execute().fetchall() == [(1, 5, 1, 1)]
+ def test_col_targeting(self):
+ t1.insert().execute({u('méil'): 1, ue('\u6e2c\u8a66'): 5})
+ t2.insert().execute({u('a'): 1, u('b'): 1})
+ t3.insert().execute({ue('\u6e2c\u8a66_id'): 1,
+ ue('unitable1_\u6e2c\u8a66'): 5,
+ u('Unitéble2_b'): 1,
+ ue('\u6e2c\u8a66_self'): 1})
+
+ row = t1.select().execute().first()
+ eq_(row[t1.c[u('méil')]], 1)
+ eq_(row[t1.c[ue('\u6e2c\u8a66')]], 5)
+
+ row = t2.select().execute().first()
+ eq_(row[t2.c[u('a')]], 1)
+ eq_(row[t2.c[u('b')]], 1)
+
+ row = t3.select().execute().first()
+ eq_(row[t3.c[ue('\u6e2c\u8a66_id')]], 1)
+ eq_(row[t3.c[ue('unitable1_\u6e2c\u8a66')]], 5)
+ eq_(row[t3.c[u('Unitéble2_b')]], 1)
+ eq_(row[t3.c[ue('\u6e2c\u8a66_self')]], 1)
+
def test_reflect(self):
t1.insert().execute({u('méil'): 2, ue('\u6e2c\u8a66'): 7})
t2.insert().execute({u('a'): 2, u('b'): 2})