問題はかなり厄介であることが判明しました。つまり、MySQL文字列データ型 追加のBINARYフラグを使用してMySQLのインターフェースで単一のデータ型にマップします。
したがって、MySQLのVARCHAR
、VARBINARY
、および文字列リテラルは同じMySQLdb.constants.FIELD_TYPE.VAR_STRING
にマップされます 列タイプの定義を入力しますが、追加のMySQLdb.constants.FLAG.BINARY
があります タイプがVARBINARY
の場合のフラグ または*_bin
と照合された文字列 照合。
MySQLdb.constants.FIELD_TYPE.VARCHAR
がありますが タイプ、それがいつ使用されるかを見つけることができませんでした。私が言ったように、MySQL VARCHAR
列はFIELD_TYPE.VAR_STRING
にマップされます 。
アプリケーションが真のバイナリ文字列を使用する場合(たとえば、画像を保存し、テキストと同じ接続でフェッチする場合)、すべてのバイナリ文字列をUnicodeにデコードすることを前提としているため、ソリューションはかなり脆弱になります。しかし、それは機能します。
公式の
実際には、お尻の本当の痛みは、独自のコンバーター辞書を作成するプロセスかもしれません。ただし、デフォルトのものはMySQLdb.converters.conversions
からインポートできます。 パッチを適用するか、接続のインスタンスにパッチを適用します。秘訣は、FLAG.BINARY
用の特別なコンバーターを削除することです。 すべての場合にフラグを立ててデコーダーを追加します。 charset
を明示的に指定した場合 MySQLdb.connect
のパラメーター 、use_unicode=1
を強制します パラメータ。デコーダを追加しますが、自分で行うこともできます:
>>> con = MySQLdb.connect(**params)
>>> con.converter[FIELD_TYPE.VAR_STRING]
[(128, <type 'str'>), (None, <function string_decoder at 0x01FFA130>)]
>>> con.converter[FIELD_TYPE.VAR_STRING] = [(None, con.string_decoder)]
>>> c = con.cursor()
>>> c.execute("SELECT %s COLLATE utf8_bin", u'м')
1L
>>> c.fetchone()
(u'\u043c',)
FIELD_TYPE.STRING
に対しても同じハックを行う必要があるかもしれません。 必要に応じて。
別の解決策は、明示的なuse_unicode=0
を渡すことです。 MySQLdb.connect
へ コード内ですべてのデコードを行いますが、私はしません。
願わくば、これが誰かに役立つかもしれません。