Python3 で MySQL に接続するドライバ
いくつもあって、どれがいいのか?
ぐぐって以下のようなものが出てきたので調べてみました。
- mysql-connector
- mysql-connector-python
- mysql-connector-python-repackaged
- mysql-connector-python-rf
- PyMySQL
環境
- OS Ubuntu Linux 20.04 ja
- MariaDB mysql Ver 15.1 Distrib 10.3.25-MariaDB, for debian-linux-gnu (x86_64) using readline 5.2
- Python 3.8.5
MariaDBは以下のように設定しました
「MariaDB on Ubuntu18.04 LTS (also Ubuntu20.04 LTS)」
https://qiita.com/nanbuwks/items/c98c51744bd0f72a7087
調査日は2021/03/26です。
https://pypi.org/project/ を辿って調べてみました。
mysql-connector
Python3.3までしか対応できてなくて却下
mysql-connector-python
MySQLの公式が作っているのかな?
https://pypi.org/project/mysql-connector-python/
mysql-connector-python-repackaged
Released: Mar 11, 2012
ということで、古くて却下。
mysql-connector-python-rf
Python3.3までしか対応できてないっぽくて却下
PyMySQL
活発ぽくてよさそう。
https://pypi.org/project/PyMySQL/
比較
残った2つを使ってみて比較
- mysql-connector-python
- PyMySQL
以下のようなテーブルを用意しておきます。
MariaDB [test]> select * from センサ;
+----+-----------+--------+--------+----------------+
| id | センサ | 温度 | 湿度 | メモ |
+----+-----------+--------+--------+----------------+
| 1 | 1 | 22 | 85 | ストーブON |
| 2 | 2 | 17 | 65 | 廊下 |
+----+-----------+--------+--------+----------------+
for row in ret:
print(row)
#</text:p>
#p = re.sub(r'##ALL:(.+?)@(.+?)##',str(ret[フィールド]),source)
#return(p)
import pymysql.cursors
import mysql.connector
# for mysql-connector-python
db=mysql.connector.connect(host="localhost", user="webdb", password="password") #
cursor=db.cursor(dictionary=True, buffered=True)
# for PyMySQL
#db=pymysql.connect(host="localhost", user="webdb", password="password" , cursorclass=pymysql.cursors.DictCursor)
#cursor=db.cursor()
cursor.execute("USE test")
db.commit()
sql=('SELECT * FROM センサ;')
cursor.execute(sql)
db.close()
if cursor != None:
for row in cursor:
print(row)
cursor.close()
mysql-connector-python を使う
実行結果
$ python3 db3.py
{'id': 1, 'センサ': 1, '温度': 22.0, '湿度': 85.0, 'メモ': b'\xe3\x82\xb9\xe3\x83\x88\xe3\x83\xbc\xe3\x83\x96ON'}
{'id': 2, 'センサ': 2, '温度': 17.0, '湿度': 65.0, 'メモ': b'\xe5\xbb\x8a\xe4\xb8\x8b'}
はて?
一部バイト列になってますね。
バイト列になったものは decode() すればいいのですが、どれがバイト列にるのか?
どうやらテキスト型だとバイト列になってしまうようです。
varchar(255) などだと問題が起こりませんでした。
MariaDB [test]> show fields from センサ;
+-----------+---------------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+-----------+---------------------+------+-----+---------+----------------+
| id | bigint(20) unsigned | NO | PRI | NULL | auto_increment |
| センサ | int(11) | YES | | NULL | |
| 温度 | double | YES | | NULL | |
| 湿度 | double | YES | | NULL | |
| メモ | text | YES | | NULL | |
+-----------+---------------------+------+-----+---------+----------------+
似た事例を探したところ、
「Python mysql-connector converts some strings into bytearray - Stack Overflow」
https://stackoverflow.com/questions/34944952/python-mysql-connector-converts-some-strings-into-bytearray
において、mysql-connector を使って類似の減少が起こったのが mysql-connector-python を使うと解消したとありました。
今回の実験では、 mysql-connector-python を使ってこのような現象が出ています。試しに mysql-connector-python をアンインストールして mysql-connector をインストールすればうまく動くようになりました。
しかしながら mysql-connector はメンテナンスされてない感じでアレですよね。
PyMySQL を使う
実行結果
$ python3 db3.py
{'id': 1, 'センサ': 1, '温度': 22.0, '湿度': 85.0, 'メモ': 'ストーブON'}
{'id': 2, 'センサ': 2, '温度':17.0, '湿度': 65.0, 'メモ': '廊下'}
正常ですね
結果
PyMySQL を使うことで幸せになれました