如何將 MySQL 4.0 的繁體中文資料庫移轉到 MySQL 5.1

我很久以前曾經寫過一篇【MySQL 4.1/5 如何將現有 latin1 中文資料匯入成 UTF-8 資料】文章,而我最近為了協助客戶將他們舊有的網站從 PHP 4.3 + MySQL 4.0 全面升級到 PHP 5 + MySQL 5.1 也是費了一番功夫,本次的心得比上次更精簡、實用。

MySQL 4.0 升級到 MySQL 5.1 最大的困難點在於資料庫本身對文字編碼 (Text Encoding) 的支援,舊版的 MySQL 4.0 所匯出的資料對 MySQL 5.1 來說,所有的文字都是 latin1 字集,所以你在 MySQL 5.1 中建立資料庫時選的若是 latin1 的話,要匯入這些資料是完全沒問題的,只是你就再也無法透過任何 MySQL 管理工具看到正常的中文字了。

所以要正確的從 MySQL 4.0 匯入資料到 MySQL 5.0 的話,一定要讓匯入的資料變成具有文字編碼特性的資料,要成功匯入資料我認為有以下步驟:

  1. 從 MySQL 4.0 匯出資料 ( 透過 mysqldump 指令 )
  2. 修正匯出的 SQL 指令檔
  3. 將資料修正成符合 big5 字集的格式
  4. 匯入檔時要設定正確的字集
  5. 將修正過的 SQL 指令執行匯入到 MySQL 5.1
    • 匯入過程若還有錯誤可手動再修正過再重新匯入
    • 有時後會因為某筆資料的某欄位的最後一個字元當 ASCII 字碼大於 127 的字元 ( High bit ) 時,而導致將欄位結尾的單引號 ( ' ) 給吃掉,這在後來匯入時會導致錯誤發生!

首先,我先準備一個檔案 ( prepend-big5.txt ),用來修正舊版匯出檔案的字集 ( Big5 ),之後要加在 SQL 指令檔最前面的:

SET NAMES 'big5';

SET CHARACTER SET 'big5';

然後,我也寫了一支 PHP 程式用來修正 MySQL 4.0 匯出檔用的,將 SQL 指令全部轉成符合 Big5 字集的指令,其實最主要也是修正「許功蓋」的問題而已,大部分的文字都是 Big5 編碼應該是沒錯的。

檔名:Fix_MySQL_Script_For_Big5.php

<?php

set_time_limit(0);

$fp = fopen('php://stdin', "r");

while($line = fgets($fp))
{
    $hasB5 = false;
    $len = strlen($line);

    for($i=0 ; $i < $len ; $i++)
    {
        $highbit = ord($line[$i]);
        if($highbit >= 0x81 && $highbit <= 0xFE)
        {
            $hasB5 = true;
            break;
        }
    }

    if($hasB5) for($high=0x81; $high <= 0xFE; $high++)
    {
        $line = str_replace(
                   chr($high) . '\\' . '\\', 
                   chr($high) . '\\', 
                   $line);
    }
    echo $line;
}

fclose($fp);

?>

這支程式會讀入 stdin 的串流資料,並且修正語法後在輸出到 stdout 串流中。

準備好資料與程式後,就是重頭戲了。

從 MySQL 4.0 匯出資料並修正字集問題

1. 先將之前準備的 prepend-big5.txt 加到 dbname.sql 檔案中

cat prepend-big5.txt > dbname.sql

2. 從 MySQL 4.0 匯出指令檔,並附加到 dbname.sql 中

mysqldump -Q --all --add-drop-table -u root -pYourPassword dbname >> dbname.sql

3. 透過 Fix_MySQL_Script_For_Big5.php 指令修正 SQL 指令檔將 dbname.sql 轉換成 dbname-big5.sql

cat dbname.sql | php -q Fix_MySQL_Script_For_Big5.php > dbname-big5.sql

此時,這個 dbname-big5.sql 已經是符合 big5 字集的 SQL 指令檔了,這時就可以準備將資料正式匯入 MySQL 5.1 資料庫。

匯入資料至 MySQL 5.1

1. 建立資料庫 ( 預設為 utf-8 字集 )

mysqladmin -u root -pYourPassword create dbname

2. 匯入資料 ( 需指明匯入的指令檔字集為 big5 )

mysql --default-character-set=big5 -u root -pYourPassword dbname < dbname-big5.sql
如果你運氣好的話,應該一次就能成功了!
  

此文章由 will 發表於 2009/3/9 下午 05:03:22

永久連結 | 評論 (18) | 此文章的RSSRSS comment feed |

分類: Linux | MySQL | PHP | 系統管理

標籤: ,

收藏:

相關文章

評論

三月 9. 2009 23:21

winzen

你客戶的舊有的網站架構 PHP 4.3 + MySQL 4.0 跟我目前完全相同,也遇到相同問題一直不敢下手,希望你的這篇能對我有所幫助。謝謝!

winzen tw

三月 9. 2009 23:23

will

有幫助的話,記得回來再留個言,讓我知道你轉移成功了! ^^

will tw

三月 10. 2009 10:01

tomexou

我當初轉換db是使用Navicat軟體將資料匯出成Unicode XML,再匯入新的db就解決,讓編碼的工作由軟體幫我作。

tomexou tw

三月 10. 2009 12:07

will

tomexou: 這在 Navicat 商業版才有提供,不過看起來還挺不錯的,還能有智慧的判斷來源資料是 Big5 並轉成 Unicode 之後中文還沒有亂碼!

不過我覺得匯出成 Unicode XML 後,原本資料中有「許功蓋」的字元應該還是會加上反斜線 ( \ ) 吧!

will tw

三月 10. 2009 18:56

winzen

請問此指令cat prepend-big5.txt > dbname.sql
windows 介面下該怎麼下參數?沒有cat的指令?!

winzen tw

三月 10. 2009 18:59

will

在 Windows 平台請用 type 指令:

type prepend-big5.txt > dbname.sql

will tw

三月 11. 2009 13:37

winzen

你好我在執行到此指令時『type dbname.sql | php -q Fix_MySQL_Script_For_Big5.php > dbname-big5.sql』會出現
PHP非內部或外部命令!請問是哪裡出問題嗎?新手上路請見諒~

winzen tw

三月 11. 2009 18:26

will

type dbname.sql | C:\php\php.exe -q Fix_MySQL_Script_For_Big5.php > dbname-big5.sql

will

三月 11. 2009 19:25

winzen

謝謝,到目前為止已經ok了,剩下匯入的動作啦!等我心臟夠大顆的時候再匯入看看,有問題再求教,謝謝啦!

winzen tw

三月 11. 2009 22:32

winzen

不好意思我又來問問題了,再最後匯入資料庫時發生錯誤,
假設出現「我很久以前曾經寫過一篇? 」
多了「? 」請問這要怎麼解決?
該用哪一個軟體去修正[?] 的狀況所引起的失敗?


winzen tw

三月 11. 2009 22:36

will

請手動修正!

這也就是我第5點所說的:「有時後會因為某筆資料的某欄位的最後一個字元當 ASCII 字碼大於 127 的字元 ( High bit ) 時,而導致將欄位結尾的單引號 ( ' ) 給吃掉,這在後來匯入時會導致錯誤發生!」

把欄位結尾的單引號(') 吃掉後,就會出現問號(?) !!

will

三月 12. 2009 10:57

winzen

找問題太統苦了,且資料庫太大一直出問題,忍統刪除一些無用的資料縮小資料庫大小後!
真是太神奇了,總算成功了!

winzen tw

四月 24. 2009 12:35

Steven

太利害了,我一直不敢升級說~
Steven

Steven hk

五月 21. 2009 18:00

孤獨中人

請問我也出現?問題~但是我去看SQL檔案裡面~卻沒有大大所說的欄位的最後單引號被吃掉~請問我該如何修正呢?

孤獨中人 tw

五月 22. 2009 10:11

孤獨中人

找到問題點了~~~應該不是說會被吃掉~~~應該說有時後SQL指令會多了一單引號~造成整個SQL錯誤~或是欄位結束單引號被加入了/ 符號~這樣欄位結束的單引號會被判別成字元~也會造成SQL語法錯誤(因為沒有結束單引號)~所以真的如同大大所說的要手動修正它~再重新刪除匯入~這樣就成功了~感謝大大的文章~幫助我很大~小弟

孤獨中人 tw

五月 22. 2009 10:12

孤獨中人

小弟是從MYSQL 3.23 移轉到 MYSQL 5.X ~單引號真的要多注意~有問題就手動修正~

孤獨中人 tw

九月 20. 2009 23:56

winzen

你好!我之前按照你的教學升級~
功蓋許都沒有問題…
唯獨輸入「會」時會出現錯誤訊息…(如下)
但是這個字卻是我們財務單位最常查詢的關鍵字…
請問有遇過這情形嗎?該怎麼解決?謝謝…

Illegal mix of collations (utf8_general_ci,IMPLICIT) and
(big5_chinese_ci,COERCIBLE) for operation 'like'

winzen tw

九月 21. 2009 09:23

Will 保哥

從錯誤訊息看來應該是你的文字不緊緊包含 big5 字碼,可能還包含了 UTF-8 字碼才會這樣,這就有點複雜了。

Will 保哥 tw

新增評論


(將顯示您的Gravatar圖示)  

  Country flag

[b][/b] - [i][/i] - [u][/u]- [quote][/quote]



線上預覽

三月 13. 2010 08:12