2010年7月22日 星期四

phpgacl setup failed! Specified key was too long; max key length is 1000 bytes

MySQL錯誤「Specified key was too long; max key length is 1000 bytes」的解決辦法

今天在為數據庫中的某兩個字段設置unique索引的時候,出現了Specified key was too long; max key length is 1000 bytes錯誤,經過查詢才知道,是Mysql的字段設置的太長了,於是我把這兩個字段的長度改了一下就好了。

建立索引時,數據庫計算key的長度是累加所有Index用到的字段的char長度後,
再按下面比例乘起來,不能超過限定的key長度1000:

latin1 = 1 byte = 1 character
uft8 = 3 byte = 1 character
gbk = 2 byte = 1 character

舉例能看得更明白些,以GBK為例:

CREATE UNIQUE INDEX `unique_record` ON reports (`report_name`, `report_client`, `report_city`);
其中report_name varchar(200), report_client varchar(200), report_city varchar(200)

(200 + 200 +200) * 2 = 1200 > 1000,所以就會報1071錯誤,
只要將report_city改為varchar(100)那麼索引就能成功建立。
如果表是UTF8字符集,那索引還是建立不了。

現在建立網站大都採UTF-8編碼,以同時兼容各國文字,而不會發生亂碼問題,
但UTF-8編碼佔的位元較多,因此需注意到如果使用的是國外的源碼,
因為國外語言一個字大都一個1 bite,但中文為2bite,所以可能會有長度的問題,
雖然這問題在一般狀況下並不常碰到..... 不過還是被我碰上了,
上網搜一搜才知道問題所在,順便提出來分享。

摘自:http://blog.xuite.net/chu.hsing/Think/33667688


Solutin :
$vi phpgacl/adodb/adodb-datadict.inc.php

// Executes the sql array returned by GetTableSQL and GetIndexSQL
function ExecuteSQLArray($sql, $continueOnError = true)
{
$rez = 2;
$conn = &$this->connection;
$saved = $conn->debug;
foreach($sql as $line) {
if(false !== strpos(strtolower($line),'create table')){ //Add This Code Start
$line .= 'default charset=latin1;';
} //Add This Code End
if ($this->debug) $conn->debug = true;
$ok = $conn->Execute($line);
$conn->debug = $saved;
if (!$ok) {
//var_dump($line);exit();
if ($this->debug) ADOConnection::outp($conn->ErrorMsg());
if (!$continueOnError) return 0;
$rez = 1;
}
}
return $rez;
}

沒有留言:

wibiya widget