2014-07-24 39 views
0

難道RowProxy對象的鍵被截斷了一段時間?在SQLAlchemy中映射non-ascii,長列名稱失敗,返回NoSuchColumnError

我有一個傳統的MSSQL數據庫,有一些帶重音字母的列名。

我繪製它的列用下面的代碼蟒蛇性質:

@event.listens_for(Table, "column_reflect") 
def column_reflect(inspector, table, column_info): 
    if table.name == 'D_Allomanylista_Komplex_V': 
     # set column.key = "attr_<lower_case_name>" 
     columns_to_change = { 
      'Allapot': 'allapot', 
      'BIZTNEVE': 'biztosito_neve', 
      u'Levelez\xe9siC\xedmUtca': 'LevelezesiCimUtca', 
      u'Szerz\u0151d\xe9sSorsz\xe1m': 'SzerzodesSzam', 
     } 
     column_info['key'] = columns_to_change.get(column_info['name'], column_info['name']) 

komplex_table = inspect_komplex_table() 

class BiztositasokModel(Base): 
    __table__ = komplex_table 
    __mapper_args__ = { 
     'primary_key': [ 
      komplex_table.c[u'KTVSZAM'], 
      komplex_table.c[u'NyugtaSzam'], 
      komplex_table.c[u'ajanlatszam'], 
      komplex_table.c['SzerzodesSzam'], 
      ], 
     'include_properties': [ 
      'biztosito_neve', 
      komplex_table.c['allapot'], 
      komplex_table.c['LevelezesiCimUtca'], 
      komplex_table.c['SzerzodesSzam'], 
      'KTVSZAM', 'NyugtaSzam', 'ajanlatszam'], 
    } 

不幸的是,當我嘗試查詢,指出SzerzodesSzam列不存在這個代碼給出了一個錯誤。

/Users/viktornagy/.virtualenvs/dosszie/lib/python2.7/site-packages/sqlalchemy/orm/loading.pyc in _instance(row, result) 
    361    identitykey = (
    362     identity_class, 
--> 363     tuple([row[column] for column in pk_cols]) 
    364   ) 
    365 

/Users/viktornagy/.virtualenvs/dosszie/lib/python2.7/site-packages/sqlalchemy/engine/result.pyc in _key_fallback(self, key, raiseerr) 
    329     raise exc.NoSuchColumnError(
    330      "Could not locate column in row for column '%s'" % 
--> 331      expression._string_or_unprintable(key)) 
    332    else: 
    333     return None 

NoSuchColumnError: "Could not locate column in row for column 'D_Allomanylista_Komplex_V.Szerz\\u0151d\\xe9sSorsz\\xe1m'" 

我進入調試模式,以找出問題的根源,並發現,在列上方363線是Column('Szerz\u0151d\xe9sSorsz\xe1m', INTEGER(), table=<D_Allomanylista_Komplex_V>, key='SzerzodesSzam', nullable=False)而相應row.key()u'D_Allomanylista_Komplex_V_Szerz\u0151d\xe9sSorsz'。就好像密鑰會被截斷一樣(u'Szerz\u0151d\xe9sSorsz'一次,u'Szerz\u0151d\xe9sSorsz\xe1m'另一點)。

查詢row[u'D_Allomanylista_Komplex_V_Szerz\u0151d\xe9sSorsz']確實有效,並給出了預期的結果。

有沒有辦法避免這種截斷?

回答

0

上述似乎是pyodbc驅動程序的限制。切換到pymssql解決了這個問題。

0

對我的作品(甚至在OSX與freetds的0.86,通常這就是Unicode的DDL翻倒嚴重):

from sqlalchemy import * 
from sqlalchemy.orm import * 
from sqlalchemy.ext.declarative import declarative_base 

Base = declarative_base() 

class Foo(Base): 
    __tablename__ = 'D_Allomanylista_Komplex_V' 

    bar = Column(u'Szerz\u0151d\xe9sSorsz\xe1m', INTEGER(), autoincrement=False, primary_key=True) 

e = create_engine("mssql+pyodbc://scott:[email protected]_2008", echo=True) 

c = e.connect() 
t = c.begin() 

Base.metadata.create_all(c) 

s = Session(c) 
s.add(Foo(bar=5)) 
s.commit() 

row = s.query(Foo).first() 

assert row.bar == 5 

輸出:

CREATE TABLE [D_Allomanylista_Komplex_V] (
    [SzerződésSorszám] INTEGER NOT NULL, 
    PRIMARY KEY ([SzerződésSorszám]) 
) 

2014-07-24 19:15:22,504 INFO sqlalchemy.engine.base.Engine() 
2014-07-24 19:15:22,507 INFO sqlalchemy.engine.base.Engine INSERT INTO [D_Allomanylista_Komplex_V] ([SzerződésSorszám]) VALUES (?) 
2014-07-24 19:15:22,507 INFO sqlalchemy.engine.base.Engine (5,) 
2014-07-24 19:15:22,510 INFO sqlalchemy.engine.base.Engine SELECT TOP 1 [D_Allomanylista_Komplex_V].[SzerződésSorszám] AS [D_Allomanylista_Komplex_V_SzerződésSorszám] 
FROM [D_Allomanylista_Komplex_V] 
+0

我認爲主要的區別的B/W的示例和我的是,我創建表使用檢查,而你建立它聲明。因此,我將一個神祕的表格附加到我的聲明類中。該錯誤不在連接Table和聲明類,而是在Table和真正的mssql列之間。 – Akasha