mirror of
https://github.com/moodle/moodle.git
synced 2025-08-04 16:36:37 +02:00
MDL-34271 use the same collation when adding new tables or columns
This commit is contained in:
parent
ed047dabc9
commit
1eece17648
2 changed files with 113 additions and 3 deletions
|
@ -119,6 +119,9 @@ class mysql_sql_generator extends sql_generator {
|
|||
public function getCreateTableSQL($xmldb_table) {
|
||||
// First find out if want some special db engine.
|
||||
$engine = $this->mdb->get_dbengine();
|
||||
// Do we know collation?
|
||||
$collation = $this->mdb->get_dbcollation();
|
||||
|
||||
$sqlarr = parent::getCreateTableSQL($xmldb_table);
|
||||
|
||||
// Let's inject the extra MySQL tweaks.
|
||||
|
@ -127,6 +130,12 @@ class mysql_sql_generator extends sql_generator {
|
|||
if ($engine) {
|
||||
$sqlarr[$i] .= " ENGINE = $engine";
|
||||
}
|
||||
if ($collation) {
|
||||
if (strpos($collation, 'utf8_') === 0) {
|
||||
$sqlarr[$i] .= " DEFAULT CHARACTER SET utf8";
|
||||
}
|
||||
$sqlarr[$i] .= " DEFAULT COLLATE = $collation";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -141,9 +150,26 @@ class mysql_sql_generator extends sql_generator {
|
|||
* @return array of sql statements
|
||||
*/
|
||||
public function getCreateTempTableSQL($xmldb_table) {
|
||||
// Do we know collation?
|
||||
$collation = $this->mdb->get_dbcollation();
|
||||
$this->temptables->add_temptable($xmldb_table->getName());
|
||||
$sqlarr = parent::getCreateTableSQL($xmldb_table); // we do not want the engine hack included in create table SQL
|
||||
$sqlarr = preg_replace('/^CREATE TABLE (.*)/s', 'CREATE TEMPORARY TABLE $1', $sqlarr);
|
||||
|
||||
$sqlarr = parent::getCreateTableSQL($xmldb_table);
|
||||
|
||||
// Let's inject the extra MySQL tweaks.
|
||||
foreach ($sqlarr as $i=>$sql) {
|
||||
if (strpos($sql, 'CREATE TABLE ') === 0) {
|
||||
// We do not want the engine hack included in create table SQL.
|
||||
$sqlarr[$i] = preg_replace('/^CREATE TABLE (.*)/s', 'CREATE TEMPORARY TABLE $1', $sql);
|
||||
if ($collation) {
|
||||
if (strpos($collation, 'utf8_') === 0) {
|
||||
$sqlarr[$i] .= " DEFAULT CHARACTER SET utf8";
|
||||
}
|
||||
$sqlarr[$i] .= " DEFAULT COLLATE $collation";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return $sqlarr;
|
||||
}
|
||||
|
||||
|
@ -224,9 +250,21 @@ class mysql_sql_generator extends sql_generator {
|
|||
$xmldb_length='255';
|
||||
}
|
||||
$dbtype .= '(' . $xmldb_length . ')';
|
||||
if ($collation = $this->mdb->get_dbcollation()) {
|
||||
if (strpos($collation, 'utf8_') === 0) {
|
||||
$dbtype .= " CHARACTER SET utf8";
|
||||
}
|
||||
$dbtype .= " COLLATE $collation";
|
||||
}
|
||||
break;
|
||||
case XMLDB_TYPE_TEXT:
|
||||
$dbtype = 'LONGTEXT';
|
||||
if ($collation = $this->mdb->get_dbcollation()) {
|
||||
if (strpos($collation, 'utf8_') === 0) {
|
||||
$dbtype .= " CHARACTER SET utf8";
|
||||
}
|
||||
$dbtype .= " COLLATE $collation";
|
||||
}
|
||||
break;
|
||||
case XMLDB_TYPE_BINARY:
|
||||
$dbtype = 'LONGBLOB';
|
||||
|
|
|
@ -82,7 +82,13 @@ class mysqli_native_moodle_database extends moodle_database {
|
|||
throw new dml_connection_exception($dberr);
|
||||
}
|
||||
|
||||
$result = $conn->query("CREATE DATABASE $dbname DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci");
|
||||
if (isset($dboptions['dbcollation']) and strpos($dboptions['dbcollation'], 'utf8_') === 0) {
|
||||
$collation = $dboptions['dbcollation'];
|
||||
} else {
|
||||
$collation = 'utf8_unicode_ci';
|
||||
}
|
||||
|
||||
$result = $conn->query("CREATE DATABASE $dbname DEFAULT CHARACTER SET utf8 DEFAULT COLLATE ".$collation);
|
||||
|
||||
$conn->close();
|
||||
|
||||
|
@ -207,6 +213,72 @@ class mysqli_native_moodle_database extends moodle_database {
|
|||
return $engine;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the current MySQL db collation.
|
||||
*
|
||||
* This is an ugly workaround for MySQL default collation problems.
|
||||
*
|
||||
* @return string or null MySQL collation name
|
||||
*/
|
||||
public function get_dbcollation() {
|
||||
if (isset($this->dboptions['dbcollation'])) {
|
||||
return $this->dboptions['dbcollation'];
|
||||
}
|
||||
if ($this->external) {
|
||||
return null;
|
||||
}
|
||||
|
||||
$collation = null;
|
||||
|
||||
// Look for current collation of our config table (the first table that gets created),
|
||||
// so that we create all tables with the same collation.
|
||||
$sql = "SELECT collation_name
|
||||
FROM INFORMATION_SCHEMA.COLUMNS
|
||||
WHERE table_schema = DATABASE() AND table_name = '{$this->prefix}config' AND column_name = 'value'";
|
||||
$this->query_start($sql, NULL, SQL_QUERY_AUX);
|
||||
$result = $this->mysqli->query($sql);
|
||||
$this->query_end($result);
|
||||
if ($rec = $result->fetch_assoc()) {
|
||||
$collation = $rec['collation_name'];
|
||||
}
|
||||
$result->close();
|
||||
|
||||
if (!$collation) {
|
||||
// Get the default database collation, but only if using UTF-8.
|
||||
$sql = "SELECT @@collation_database";
|
||||
$this->query_start($sql, NULL, SQL_QUERY_AUX);
|
||||
$result = $this->mysqli->query($sql);
|
||||
$this->query_end($result);
|
||||
if ($rec = $result->fetch_assoc()) {
|
||||
if (strpos($rec['@@collation_database'], 'utf8_') === 0) {
|
||||
$collation = $rec['@@collation_database'];
|
||||
}
|
||||
}
|
||||
$result->close();
|
||||
}
|
||||
|
||||
if (!$collation) {
|
||||
// We want only utf8 compatible collations.
|
||||
$collation = null;
|
||||
$sql = "SHOW COLLATION WHERE Collation LIKE 'utf8\_%' AND Charset = 'utf8'";
|
||||
$this->query_start($sql, NULL, SQL_QUERY_AUX);
|
||||
$result = $this->mysqli->query($sql);
|
||||
$this->query_end($result);
|
||||
while ($res = $result->fetch_assoc()) {
|
||||
$collation = $res['Collation'];
|
||||
if (strtoupper($res['Default']) === 'YES') {
|
||||
$collation = $res['Collation'];
|
||||
break;
|
||||
}
|
||||
}
|
||||
$result->close();
|
||||
}
|
||||
|
||||
// Cache the result to improve performance.
|
||||
$this->dboptions['dbcollation'] = $collation;
|
||||
return $collation;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns localised database type name
|
||||
* Note: can be used before connect()
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue