用python中的mysql连接器从mysql数据库正确获取blob

xiozqbni  于 2021-06-18  发布在  Mysql
关注(0)|答案(4)|浏览(451)

执行以下代码时:

import mysql.connector
connection = mysql.connector.connect(...) # connection params here
cursor = connection.cursor()
cursor.execute('create table test_table(value blob)')
cursor.execute('insert into test_table values (_binary %s)', (np.random.sample(10000).astype('float').tobytes(),))
cursor.execute('select * from test_table')
cursor.fetchall()

我得到以下错误:
unicodedecodeerror:“utf-8”编解码器无法解码位置1中的字节0xf7:无效的起始字节
(…然后是一个堆栈跟踪,我认为在这里没有用)
似乎mysql连接器将我的blob转换为字符串(但失败了)。如何在没有任何转换的情况下以字节的形式获取这些数据?

h22fl7wq

h22fl7wq1#

我复制了上述错误:

Traceback (most recent call last):
File "demo.py", line 16, in <module>
    cursor.execute(query, ())
return codecs.utf_8_decode(input, errors, True)
UnicodeDecodeError: 'utf8' codec can't decode byte '0xff ... ' 
in position 0: invalid start byte

使用版本:

$  python --version
Python 2.7.10

>>> mysql.connector.__version__
'8.0.15'

使用python代码


# !/usr/bin/python

# -*- coding: utf-8 -*-

import mysql.connector
conn = mysql.connector.connect(
      user='asdf', 
      password='asdf',
      host='1.2.3.4',
      database='the_db',
      connect_timeout=10)

cursor = conn.cursor(buffered=True)                     #error is raised here
try:
    query = ("SELECT data_blob FROM blog.cmd_table")
    cursor.execute(query, ())                         
except mysql.connector.Error as err:                    #error is caught here
    #error is caught here, and printed:
    print(err)                                          #printed thustly

使用python变量“raw byte binary”填充python的 open( 这样地:

def read_file_as_blob(filename):
    #r stands for read
    #b stands for binary
    with open(filename, 'rb') as f:
        data = f.read()
    return data

所以问题就在文件中数据的编码转换->mysql blob的数据编码->和mysql如何提升blob并将其转换回utf-8之间。

两种解决方案:

解决方案1和阿哈尔瓦尔说的一模一样 use_pure=True 参数并传递给 mysql.connector.connect( ... ) . 奇怪的是,它居然起作用了。但优秀的程序员会注意到,遵从神秘的咒语是一种糟糕的代码气味。布朗运动的修正招致技术债务。
解决方案2是尽早和经常地对数据进行编码,并防止双重重新编码和双重数据解码,这是这些问题的根源。尽快将其锁定为通用编码格式。
对我来说,令人满意的解决方案是在这个过程的早期强制使用utf-8编码。到处都是utf-8。

data.encode('UTF-8')

poo的unicode堆代表了我对不同操作系统和编码方案上的不同设备之间的字符编码的这种保姆式的看法。

nzkunb0c

nzkunb0c2#

我们遇到了同样的问题,在mysql 8.0.13、mysql connector python 8.0.13和sqlalchemy 1.2.14中,blob被错误地读回为utf-8字符串。
我们的诀窍是使 use_pure mysql连接器选项。违约 use_pure 已在8.0.11中更改,新的默认值是使用c扩展。因此,我们推迟了选项:

create_engine(uri, connect_args={'use_pure': True}, ...)

错误和堆栈跟踪的详细信息:

UnicodeDecodeError: 'utf-8' codec can't decode byte 0x9c in position 1: invalid start byte
The above exception was the direct cause of the following exception:

Traceback (most recent call last):
    ....
    File "/usr/local/lib/python3.6/site-packages/mysql/connector/cursor_cext.py", line 272, in execute
        self._handle_result(result)
    File "/usr/local/lib/python3.6/site-packages/mysql/connector/cursor_cext.py", line 163, in _handle_result
        self._handle_resultset()
    File "/usr/local/lib/python3.6/site-packages/mysql/connector/cursor_cext.py", line 651, in _handle_resultset
        self._rows = self._cnx.get_rows()[0]
    File "/usr/local/lib/python3.6/site-packages/mysql/connector/connection_cext.py", line 273, in get_rows
        row = self._cmysql.fetch_row()
    SystemError: <built-in method fetch_row of _mysql_connector.MySQL object at 0x5627dcfdf9f0> returned a result with an error set
blpfk2vs

blpfk2vs3#

另一种方法是使用 raw=True 连接初始化时的参数:

connection = mysql.connector.connect(
    host="localhost",
    user="user",
    password="password",
    database="database",
    raw=True
)
yvfmudvl

yvfmudvl4#

显然,这是python'mysql'模块的一个已知问题。尝试改用“pymysql”。

相关问题