MySQLプロファイルにdefault-character-setの設定を忘れたことによる文字化け問題
7476 ワード
文字セットの参考文献:
http://dev.mysql.com/doc/refman/5.6/en/server-system-variables.html#sysvar_character_setconnection
http://dev.mysql.com/doc/refman/5.6/en/faqs-cjk.html
今日、同僚がjdbcを使ってデータベースに接続して、文の結果集がないことを実行しますが、sqlyouを通じて同じ文を実行します。
実行するステートメントwhereの条件には中国語が含まれています。これは文字セットによるものです。
この開発テストの例は移転して間もないので、移行前の環境デフォルトの文字セットはutf 8です。
現在のデータベースの文字セットを表示します。 character_setclient character_setコンサート character_setレスリング 以上の三つのMsql clientを制御する文字セット character_setdatabase データベースの標準文字セットを設定します。 character_setserver 以上のすべてのデフォルトの文字セットを設定します。
server端の文字セットとclient端のグローバルキャラクタセット設定変数は、いずれも標準値latin 1であることが分かりました。
設定ファイルにパラメータ項目が追加されていないことが分かりました。 character-set-server=utf 8
文字化けの原因:
データ格納時の符号化復号処理
jdbc=>character_setclient=>table character
各環節の文字セットコードは全部utf 8で、トランスコードプロセスがありません。
character_setclientがlatin 1になったら、データを読み込む復号処理は
jdbc<=character_setclient<=table character
表にはutf 8符号化フォーマットが格納されています。判断とcharacter_setclientが一致しない場合は、latin 1のバイナリストリームにトランスコードし、リモート端末のクライアントに送信します。
クライアントjdbcは、設定された文字セットによって結果を示し、utf 8を用いてlatin 1を示しているので、文字化けが発生している。
解決策
文字セットがlatin 1に設定されている間に挿入されるデータ符号化格納プロセスについて:は、terminal(ここではjdbcクライアント)に入力方式を用いて入力する である。 terminalは、utf 8バイナリストリーム に変換される。バイナリストリームは、MySQLクライアントを介してMySQL Server に転送される。 Serverは、character-set-clientによって を復号する。は、character-set-clientとターゲットテーブルのcharsetが一致するかどうかを判断し、character-set-clientはlatin 1であり、ターゲットテーブルの文字セットはutf 8 である。が一致しない場合は、client-charsetからtable-charsetまでの一回の文字コード変換を行い、latin 1からutf 8 にトランスコードされる。変換された文字コードのバイナリストリームをファイルに保存します。 テストの場合、中間環節のcharacter-set-clientをutf 8に変更して、文字化けが発生するかどうかファイルからバイナリデータストリームを読み出します。 は、表文字セットlatin 1で符号化して復号する 。は、データをcharacter-set-clientの符号化laint 1 に変換する。
対応の変更前の一環:ファイルからバイナリデータストリームを読み出します。 は、表文字セットutf 8で符号化して復号する 。は、データをcharacter-set-clientの符号化laint 1 に変換する。
表データの文字セットを変更しても、文字セット全体が経験している復号とトランスコードのプロセスが一致しているため、一度にutf 8からlatin 1へのトランスコードを経験していることが分かります。
もう一つの文字セットに関する問題:表情記号をサポートするために、システムレベルのutf 8をutf 8 mb 4に設定し、対応するテーブルも文字セットの変更をしました。再起動アプリケーションは有効ではなく、データベースとアプリケーションを再起動してから有効になります。
参考記事は以下の通りです
http://blog.sina.com.cn/s/blog_93 b 45 b 0 f 0101 glfx.
参考記事:
符号化復号プロセス : http://cenalulu.github.io/mysql/mysql-mojibake/
転載先:https://www.cnblogs.com/Bccd/p/5941415.html
http://dev.mysql.com/doc/refman/5.6/en/server-system-variables.html#sysvar_character_setconnection
http://dev.mysql.com/doc/refman/5.6/en/faqs-cjk.html
今日、同僚がjdbcを使ってデータベースに接続して、文の結果集がないことを実行しますが、sqlyouを通じて同じ文を実行します。
実行するステートメントwhereの条件には中国語が含まれています。これは文字セットによるものです。
この開発テストの例は移転して間もないので、移行前の環境デフォルトの文字セットはutf 8です。
現在のデータベースの文字セットを表示します。
mysql> show variables like '%charac%';
+--------------------------+----------------------------------+
| Variable_name | Value |
+--------------------------+----------------------------------+
| character_set_client | utf8 |
| character_set_connection | utf8 |
| character_set_database | latin1 |
| character_set_filesystem | binary |
| character_set_results | utf8 |
| character_set_server | latin1 |
| character_set_system | utf8 |
| character_sets_dir | /usr/local/mysql/share/charsets/ |
+--------------------------+----------------------------------+
8 rows in set (0.00 sec)
server端の文字セットとclient端のグローバルキャラクタセット設定変数は、いずれも標準値latin 1であることが分かりました。
設定ファイルにパラメータ項目が追加されていないことが分かりました。 character-set-server=utf 8
文字化けの原因:
データ格納時の符号化復号処理
jdbc=>character_setclient=>table character
各環節の文字セットコードは全部utf 8で、トランスコードプロセスがありません。
character_setclientがlatin 1になったら、データを読み込む復号処理は
jdbc<=character_setclient<=table character
表にはutf 8符号化フォーマットが格納されています。判断とcharacter_setclientが一致しない場合は、latin 1のバイナリストリームにトランスコードし、リモート端末のクライアントに送信します。
クライアントjdbcは、設定された文字セットによって結果を示し、utf 8を用いてlatin 1を示しているので、文字化けが発生している。
解決策
# character_set_filesystem 、character_set_system 、character_sets_dir utf8
すべてのアプリケーションは、セッションレベルの文字セットを変更するには、データベースを再接続する必要があります。文字セットがlatin 1に設定されている間に挿入されるデータ符号化格納プロセスについて:
mysql> show variables like '%char%';
+--------------------------+----------------------------------+
| Variable_name | Value |
+--------------------------+----------------------------------+
| character_set_client | latin1 |
| character_set_connection | latin1 |
| character_set_database | utf8 |
| character_set_filesystem | binary |
| character_set_results | latin1 |
| character_set_server | utf8 |
| character_set_system | utf8 |
| character_sets_dir | /usr/local/mysql/share/charsets/ |
+--------------------------+----------------------------------+
8 rows in set (0.01 sec)
mysql> update t1 set col=' ' where id=4;
mysql> select * from t1 where id=4;
+----+-----------+------+
| id | col | time |
+----+-----------+------+
| 4 | | NULL |
+----+-----------+------+
crt terminal =》character_set_client =》character_set_server
utf8 latin1 utf8
1、
mysql> set names utf8;
Query OK, 0 rows affected (0.00 sec)
mysql> select * from t1 where id=4;
+----+-----------------------+------+
| id | col | time |
+----+-----------------------+------+
| 4 | ??o???è?? | NULL |
+----+-----------------------+------+
2、 crt terminal default
mysql> select * from t1 where id=4;
+----+-----------+------+
| id | col | time |
+----+-----------+------+
| 4 | | NULL |
+----+-----------+------+
3、
ALTER TABLE t1 CHANGE col col varchar(10) CHARACTER SET latin1;
mysql> select * from t1 where id=4;
+----+-----------+------+
| id | col | time |
+----+-----------+------+
| 4 | | NULL |
+----+-----------+------+
表の文字セットを変更するとlatin 1になります。データの読み込みは変更に関連しています。対応の変更前の一環:
表データの文字セットを変更しても、文字セット全体が経験している復号とトランスコードのプロセスが一致しているため、一度にutf 8からlatin 1へのトランスコードを経験していることが分かります。
もう一つの文字セットに関する問題:表情記号をサポートするために、システムレベルのutf 8をutf 8 mb 4に設定し、対応するテーブルも文字セットの変更をしました。再起動アプリケーションは有効ではなく、データベースとアプリケーションを再起動してから有効になります。
参考記事は以下の通りです
http://blog.sina.com.cn/s/blog_93 b 45 b 0 f 0101 glfx.
参考記事:
符号化復号プロセス : http://cenalulu.github.io/mysql/mysql-mojibake/
転載先:https://www.cnblogs.com/Bccd/p/5941415.html