首页 > 解决方案 > Python 在使用 fast_executemany = True 和 Sybase 表插入时因“字符串数据,右截断”而崩溃

问题描述

我正在使用以下函数插入具有大量数据的 Sybase 表。我正在使用 fast_executemany = True ,因为没有这个,性能会很慢并且不能满足我的要求。下面的代码给出了上述表格的错误。这是一个通用函数,它作为数据框并插入到作为输入传递给函数的目标表。我无法定制特定的表,因为表结构从一张表到另一张表不同。

功能

def _sybase_insert(source_df, targetTable, loadType, target, database):
    cursor = target.cnxn.cursor()
    sql = 'select top 1 * from ' + targetTable
    cursor.execute(sql)
    row = cursor.fetchall()
    db_types = [d[1] for d in cursor.description]
    print(db_types)
    rows = source_df.values.tolist()
    parms = ("?," * len(rows[0]))[:-1]
    if loadType == 'replace':
        sql = "delete  from " + targetTable
        cursor.execute(sql)
    sql = "INSERT INTO " + targetTable +" VALUES (%s)" % (parms)
    cursor.fast_executemany = True
    cursor.setinputsizes(db_types)
    cursor.executemany(sql, rows)
    cursor.close()
    target.cnxn.commit()

我的连接字符串是

self.cnxn = pyodbc.connect('DRIVER={Adaptive Server Enterprise};uid=' + self.user +';EncryptPassword=1;pwd=' + self.password + ';Port=' + self.dbport + ';Server=' + self.server +';Database=' + dbname)

下面是它因错误而失败的表结构**pyodbc.ProgrammingError: ('String data, right truncation: length 22 buffer 20', 'HY000')**


我也尝试过,但没有解决这个问题

cursor.setinputsizes(
    [
        (pyodbc.SQL_VARCHAR,500,1000),
        (pyodbc.SQL_INTEGER),
        (pyodbc.SQL_FLOAT),
    ]
)

目标表

COLUMN_NAME      DATA_TYPE TYPE_NAME COLUMN_SIZE BUFFER_LENGTH DECIMAL_DIGITS NUM_PREC_RADIX IS_NULLABLE 
---------------- --------- --------- ----------- ------------- -------------- -------------- ----------- 
Column1          4         int       10          10            0              10             NO          
Column2          4         int       10          10            0              10             NO          
Column3          4         int       10          10            0              10             NO          
Column4          4         int       10          10            0              10             NO          
Column5          4         int       10          10            0              10             NO          
column6          4         int       10          10            0              10             NO          
column7          4         int       10          10            0              10             NO          
column8          1         char      12          12            (null)         (null)         NO          
column9          1         char      12          12            (null)         (null)         NO          
column10         4         int       10          10            0              10             NO          
column11         4         int       10          10            0              10             NO          
column12         1         char      12          12            (null)         (null)         NO          
column13         4         int       10          10            0              10             NO          
column14         4         int       10          10            0              10             NO          
column15         4         int       10          10            0              10             NO          
column16         4         int       10          10            0              10             NO          
column17         1         char      30          30            (null)         (null)         NO          
column18         4         int       10          10            0              10             NO          
column19         4         int       10          10            0              10             NO          
column20         4         int       10          10            0              10             NO          
column21         93        datetime  23          23            3              10             NO          
column22         1         char      10          10            (null)         (null)         NO          
column23         4         int       10          10            0              10             NO          
    

由于这是一个通用函数,请让我知道代码有什么问题以及为什么我上面提到的表格失败了。


有错误的实际输出

下面是实际错误的输出。

[<class 'int'>, <class 'int'>, <class 'int'>, <class 'int'>, <class 'int'>, <class 'int'>, <class 'int'>, <class 'str'>, <class 'str'>, <class 'int'>, <class 'int'>, <class 'str'>, <class 'int'>, <class 'int'>, <class 'int'>, <class 'int'>, <class 'str'>, <class 'int'>, <class 'int'>, <class 'int'>, <class 'datetime.datetime'>, <class 'str'>, <class 'int'>]
Traceback (most recent call last):
  File "ODBCTableCopy.py", line 121, in <module>
    out.append(_table_copy_(targetTable=target_table, sourceObject=sql, source=source, target=target, database=Database , loadType=load_type))
  File "ODBCTableCopy.py", line 67, in _table_copy_
    _sybase_insert(source_df,targetTable, loadType, target, database)
  File "ODBCTableCopy.py", line 47, in _sybase_insert
    cursor.executemany(sql, rows)
pyodbc.ProgrammingError: ('String data, right truncation: length 22 buffer 20', 'HY000')

标签: pythonsybase

解决方案


推荐阅读