文件首頁
MySQL 9.0 參考手冊
相關文件 下載本手冊
PDF (美式 Letter) - 40.0Mb
PDF (A4) - 40.1Mb
Man Pages (TGZ) - 258.2Kb
Man Pages (Zip) - 365.3Kb
Info (Gzip) - 4.0Mb
Info (Zip) - 4.0Mb


MySQL 9.0 參考手冊  /  字元集、校對、Unicode  /  連線字元集與校對

12.4 連線字元集與校對

連線是當用戶端程式連線到伺服器時所建立的,以便開始與伺服器互動的階段。用戶端透過階段連線傳送 SQL 陳述式,例如查詢。伺服器透過連線將回應(例如結果集或錯誤訊息)傳送回用戶端。

連線字元集與校對系統變數

有數個字元集與校對系統變數與用戶端與伺服器的互動相關。其中一些已在先前的章節中提及

其他字元集和校對系統變數涉及處理用戶端和伺服器之間連線的流量。每個用戶端都有工作階段特定的連線相關字元集和校對系統變數。這些工作階段系統變數值在連線時初始化,但可以在工作階段內變更。

有關用戶端連線字元集與校對處理的幾個問題可以用系統變數來解答

若要查看適用於目前工作階段的字元集和校對系統變數的值,請使用以下陳述式

SELECT * FROM performance_schema.session_variables
WHERE VARIABLE_NAME IN (
  'character_set_client', 'character_set_connection',
  'character_set_results', 'collation_connection'
) ORDER BY VARIABLE_NAME;

以下較簡單的陳述式也會顯示連線變數,但也會包含其他相關變數。它們可以用來查看所有字元集和校對系統變數

SHOW SESSION VARIABLES LIKE 'character\_set\_%';
SHOW SESSION VARIABLES LIKE 'collation\_%';

用戶端可以微調這些變數的設定,或依賴預設值(在這種情況下,您可以跳過本節的其餘部分)。如果您不使用預設值,您必須針對每個與伺服器的連線變更字元設定。

不允許的用戶端字元集

character_set_client 系統變數不能設定為某些字元集

ucs2
utf16
utf16le
utf32

嘗試使用任何這些字元集作為用戶端字元集會產生錯誤

mysql> SET character_set_client = 'ucs2';
ERROR 1231 (42000): Variable 'character_set_client'
can't be set to the value of 'ucs2'

如果任何這些字元集在下列情境中使用,也會發生相同的錯誤,這些情境都會導致嘗試將 character_set_client 設定為指定的字元集。

用戶端程式連線字元集設定

當用戶端連線到伺服器時,它會指示要用於與伺服器通訊的字元集。(實際上,用戶端會指示該字元集的預設排序規則,伺服器可以從中判斷字元集。)伺服器會使用此資訊將 character_set_clientcharacter_set_resultscharacter_set_connection 系統變數設定為該字元集,並將 collation_connection 設定為該字元集的預設排序規則。實際上,伺服器會執行與 SET NAMES 操作等效的操作。

如果伺服器不支援要求的字元集或排序規則,它會改用伺服器字元集和排序規則來設定連線。有關此回退行為的更多詳細資訊,請參閱 連線字元集錯誤處理

mysqlmysqladminmysqlcheckmysqlimportmysqlshow 用戶端程式會按如下方式判斷要使用的預設字元集:

  • 在沒有其他資訊的情況下,每個用戶端都會使用編譯時預設字元集,通常是 utf8mb4

  • 每個用戶端都可以根據作業系統設定自動偵測要使用的字元集,例如 Unix 系統上的 LANGLC_ALL 地區環境變數的值,或 Windows 系統上的程式碼頁設定。對於可從作業系統取得地區設定的系統,用戶端會使用它來設定預設字元集,而不是使用編譯時預設字元集。例如,將 LANG 設定為 ru_RU.KOI8-R 會導致使用 koi8r 字元集。因此,使用者可以在其環境中設定地區設定,以供 MySQL 用戶端使用。

    如果沒有完全符合的字元集,作業系統字元集會對應到最接近的 MySQL 字元集。如果用戶端不支援相符的字元集,它會使用編譯時預設字元集。例如,utf8utf-8 對應到 utf8mb4,而 ucs2 不支援作為連線字元集,因此它會對應到編譯時預設字元集。

    C 應用程式可以在連線到伺服器之前,透過如下方式叫用 mysql_options(),使用基於作業系統設定的字元集自動偵測:

    mysql_options(mysql,
                  MYSQL_SET_CHARSET_NAME,
                  MYSQL_AUTODETECT_CHARSET_NAME);
  • 每個用戶端都支援 --default-character-set 選項,讓使用者可以明確指定字元集,以覆寫用戶端以其他方式判定的任何預設值。

    注意

    某些字元集不能用作用戶端字元集。嘗試將它們與 --default-character-set 一起使用會產生錯誤。請參閱 不允許的用戶端字元集

使用 mysql 用戶端時,若要使用與預設值不同的字元集,您可以在每次連線到伺服器時明確執行 SET NAMES 陳述式(請參閱 用戶端程式連線字元集設定)。若要更輕鬆地達成相同的結果,請在選項檔案中指定字元集。例如,下列選項檔案設定會在每次您叫用 mysql 時,將三個與連線相關的字元集系統變數變更為 koi8r

[mysql]
default-character-set=koi8r

如果您在使用啟用自動重新連線(不建議使用)的 mysql 用戶端,最好使用 charset 命令,而不是 SET NAMES。例如:

mysql> charset koi8r
Charset changed

charset 命令會發出 SET NAMES 陳述式,也會變更 mysql 在連線中斷後重新連線時使用的預設字元集。

在設定用戶端程式時,您也必須考量它們執行的環境。請參閱 第 12.5 節,「設定應用程式字元集和排序規則」

用於連線字元集設定的 SQL 陳述式

連線建立後,用戶端可以變更目前工作階段的字元集和排序規則系統變數。這些變數可以使用 SET 陳述式個別變更,但另外兩個更方便的陳述式會影響一組與連線相關的字元集系統變數:

  • SET NAMES 'charset_name' [COLLATE 'collation_name']

    SET NAMES 表示用戶端用於將 SQL 陳述式傳送到伺服器的字元集。因此,SET NAMES 'cp1251' 會告知伺服器,來自此用戶端的未來傳入訊息採用 cp1251 字元集。它也指定伺服器應使用哪個字元集將結果傳回給用戶端。(例如,如果您使用產生結果集的 SELECT 陳述式,它會指示要用於資料行值的字元集。)

    SET NAMES 'charset_name' 陳述式等同於以下三個陳述式:

    SET character_set_client = charset_name;
    SET character_set_results = charset_name;
    SET character_set_connection = charset_name;

    character_set_connection 設定為 charset_name 也會隱含地將 collation_connection 設定為 charset_name 的預設排序規則。不需要明確設定該排序規則。若要指定要用於 collation_connection 的特定排序規則,請新增 COLLATE 子句:

    SET NAMES 'charset_name' COLLATE 'collation_name'
  • SET CHARACTER SET 'charset_name''

    SET CHARACTER SET 類似於 SET NAMES,但會將 character_set_connectioncollation_connection 設定為 character_set_databasecollation_database(如先前所述,它們表示預設資料庫的字元集和排序規則)。

    SET CHARACTER SET charset_name 陳述式等同於以下三個陳述式:

    SET character_set_client = charset_name;
    SET character_set_results = charset_name;
    SET collation_connection = @@collation_database;

    設定 collation_connection 也會隱含地將 character_set_connection 設定為與排序規則相關聯的字元集(等同於執行 SET character_set_connection = @@character_set_database)。不需要明確設定 character_set_connection

注意

某些字元集不能用作用戶端字元集。嘗試將它們與 SET NAMESSET CHARACTER SET 一起使用會產生錯誤。請參閱 不允許的用戶端字元集

範例:假設 column1 定義為 CHAR(5) CHARACTER SET latin2。如果您沒有說 SET NAMESSET CHARACTER SET,則對於 SELECT column1 FROM t,伺服器會使用用戶端在連線時指定的字元集傳回 column1 的所有值。另一方面,如果您在發出 SELECT 陳述式之前說 SET NAMES 'latin1'SET CHARACTER SET 'latin1',伺服器會在將結果傳回之前,將 latin2 值轉換為 latin1。對於不在兩個字元集中的字元,轉換可能會遺失資訊。

連線字元集錯誤處理

嘗試使用不適當的連線字元集或排序規則可能會產生錯誤,或導致伺服器回退到其預設字元集和給定連線的排序規則。本節說明在設定連線字元集時可能發生的問題。這些問題可能會在建立連線時或在已建立的連線中變更字元集時發生。

連線時錯誤處理

某些字元集不能用作用戶端字元集;請參閱 不允許的用戶端字元集。如果您指定有效但不允許作為用戶端字元集的字元集,伺服器會傳回錯誤:

$> mysql --default-character-set=ucs2
ERROR 1231 (42000): Variable 'character_set_client' can't be set to
the value of 'ucs2'

如果您指定的字元集是客戶端無法辨識的,則會產生錯誤。

$> mysql --default-character-set=bogus
mysql: Character set 'bogus' is not a compiled character set and is
not specified in the '/usr/local/mysql/share/charsets/Index.xml' file
ERROR 2019 (HY000): Can't initialize character set bogus
(path: /usr/local/mysql/share/charsets/)

如果您指定的字元集是客戶端可以辨識但伺服器無法辨識的,則伺服器會回退到其預設字元集和校對規則。假設伺服器配置為使用 latin1latin1_swedish_ci 作為其預設值,且無法辨識 gb18030 作為有效的字元集。指定 --default-character-set=gb18030 的客戶端能夠連線到伺服器,但最終的字元集並非客戶端所期望的。

mysql> SHOW SESSION VARIABLES LIKE 'character\_set\_%';
+--------------------------+--------+
| Variable_name            | Value  |
+--------------------------+--------+
| character_set_client     | latin1 |
| character_set_connection | latin1 |
...
| character_set_results    | latin1 |
...
+--------------------------+--------+
mysql> SHOW SESSION VARIABLES LIKE 'collation_connection';
+----------------------+-------------------+
| Variable_name        | Value             |
+----------------------+-------------------+
| collation_connection | latin1_swedish_ci |
+----------------------+-------------------+

您可以看到連線系統變數已設定為反映 latin1latin1_swedish_ci 的字元集和校對規則。發生這種情況是因為伺服器無法滿足客戶端字元集請求,並回退到其預設值。

在這種情況下,客戶端無法使用其想要的字元集,因為伺服器不支援。客戶端必須願意使用不同的字元集,或連線到支援所需字元集的不同伺服器。

當客戶端告知伺服器使用伺服器可以辨識的字元集,但客戶端預設的校對規則在伺服器端未知時,也會發生相同的問題。

執行階段錯誤處理

在已建立的連線中,客戶端可以使用 SET NAMESSET CHARACTER SET 來請求變更連線字元集和校對規則。

某些字元集不能用作用戶端字元集;請參閱 不允許的用戶端字元集。如果您指定有效但不允許作為用戶端字元集的字元集,伺服器會傳回錯誤:

mysql> SET NAMES 'ucs2';
ERROR 1231 (42000): Variable 'character_set_client' can't be set to
the value of 'ucs2'

如果伺服器無法辨識字元集(或校對規則),則會產生錯誤。

mysql> SET NAMES 'bogus';
ERROR 1115 (42000): Unknown character set: 'bogus'

mysql> SET NAMES 'utf8mb4' COLLATE 'bogus';
ERROR 1273 (HY000): Unknown collation: 'bogus'
提示

想要驗證其請求的字元集是否被伺服器接受的客戶端,可以在連線後執行以下語句,並檢查結果是否為預期的字元集。

SELECT @@character_set_client;