Ошибка UnicodeDecodeError: кодек ‘utf-16-le’ не может декодировать байты в позиции 10-11: недопустимая кодировка

#db2 #pyodbc

#db2 #pyodbc

Вопрос:

Я получаю

   File "/opt/rh/rh-python36/root/usr/lib64/python3.6/encodings/utf_16_le.py", line 16, in decode
    return codecs.utf_16_le_decode(input, errors, True)
UnicodeDecodeError: 'utf-16-le' codec can't decode bytes in position 10-11: illegal encoding
 

и когда — нибудь

  curr.execute(sql)
UnicodeDecodeError: 'utf-8' codec can't decode byte 0xe0 in position 4: unexpected end of data
 

подключение к
База данных DB2 с использованием iAccess Client Solutions драйвера

  • python 3.6
  • pyodbc 4.0.30

получен действительный объект подключения, поэтому соединение выполнено успешно, однако при разборе строки SQL возникают проблемы, не уверен, почему pyodbc не передает строку SQL драйверу, в SQL нет никаких специальных символов / символов, отличных от юникода.

Кроме того, тот же код отлично работает в python3.4 / pyodbc 3.0.7 с той же версией драйвера Db2 iAccess.

При захвате mtrace выходных данных он показывает ниже, где вызывается after curr execute call codecs.utf_16_le_decode , не знаю почему. Является ли это поведение по умолчанию в python 3.6?

 test_as400_36.py(41): curr.execute(sql)
 --- modulename: utf_16_le, funcname: decode
utf_16_le.py(16):     return codecs.utf_16_le_decode(input, errors, True)
 --- modulename: trace, funcname: _unsettrace
trace.py(77):         sys.settrace(None)

 
<pyodbc.Connection object at 0x7f3b3e8068a0>
 

ниже приведен код.

 import sys
import pyodbc
import csv
import logging

logging.basicConfig(level='INFO', format='[%(asctime)s] [%(levelname)s] [%(name)s] %(message)s')
logger = logging.getLogger(__name__)

pyodbc.pooling = False
print("pyodbc version "   pyodbc.version)

cnxn=pyodbc.connect(r'DSN={};UID={};PWD={};'.format("DSN1","User1","passwd"))

print(cnxn)

curr=cnxn.cursor()

sql='''select
FXLCCN
from AILLIB.annpymtK
'''

curr.execute(sql)


arraysize=500000
logging.get_logger()
rows_fetched=0

while True:
            results = curr.fetchmany(arraysize)
            cnt_rows_fetched = len(results)
            logger.debug('%s Rows Fetched', cnt_rows_fetched)
            rows_fetched  = cnt_rows_fetched
            logger.info('%s Total Rows Fetched', rows_fetched)
            if not results:
                curr.close()
                break

 

Комментарии:

1. Можете ли вы сделать простой select 1 as FXLCCN . (Я не знаю, поддерживает ли DB2 SELECT без FROM .)

2. Предлагаю вам проверить это на странице проблем github pyodbc, github.com/mkleehammer/pyodbc/issues , как сообщали об этом другие, и в некоторых случаях были найдены обходные пути.

3. github.com/mkleehammer/pyodbc/issues/755