diff --git a/core/attributedef.class.inc.php b/core/attributedef.class.inc.php index 689b7ba31..4cd87e1a2 100644 --- a/core/attributedef.class.inc.php +++ b/core/attributedef.class.inc.php @@ -5248,6 +5248,20 @@ class AttributeEnum extends AttributeString } protected function GetSQLCol($bFullSpec = false) + { + // Get the definition of the column, including the actual values present in the table + return $this->GetSQLColHelper($bFullSpec, true); + } + + /** + * A more versatile version of GetSQLCol + * @since 3.0.0 + * @param bool $bFullSpec + * @param bool $bIncludeActualValues + * @param string $sSQLTableName The table where to look for the actual values (may be useful for data synchro tables) + * @return string + */ + protected function GetSQLColHelper($bFullSpec = false, $bIncludeActualValues = false, $sSQLTableName = null) { $oValDef = $this->GetValuesDef(); if ($oValDef) @@ -5258,6 +5272,19 @@ class AttributeEnum extends AttributeString { $aValues = array(); } + + // Preserve the values already present in the database to ease migrations + if ($bIncludeActualValues) + { + if ($sSQLTableName == null) + { + // No SQL table given, use the one of the attribute + $sHostClass = $this->GetHostClass(); + $sSQLTableName = MetaModel::DBGetTable($sHostClass, $this->GetCode()); + } + $aValues = array_unique(array_merge($aValues, $this->GetActualValuesInDB($sSQLTableName))); + } + if (count($aValues) > 0) { // The syntax used here do matters @@ -5276,6 +5303,48 @@ class AttributeEnum extends AttributeString } } + /** + * @since 3.0.0 + * {@inheritDoc} + * @see AttributeDefinition::GetImportColumns() + */ + public function GetImportColumns() + { + // Note: this is used by the Data Synchro to build the "data" table + // Right now the function is not passed the "target" SQL table, but if we improve this in the future + // we may call $this->GetSQLColHelper(true, true, $sDBTable); to take into account the actual 'enum' values + // in this table + return $this->GetSQLColHelper(true, false); + } + + /** + * Get the list of the actual 'enum' values present in the database + * @since 3.0.0 + * @return string[] + */ + protected function GetActualValuesInDB(string $sDBTable) + { + $aValues = array(); + try + { + $sSQL = "SELECT DISTINCT `".$this->GetSQLExpr()."` AS value FROM `$sDBTable`;"; + $aValuesInDB = CMDBSource::QueryToArray($sSQL); + foreach($aValuesInDB as $aRow) + { + if ($aRow['value'] !== null) + { + $aValues[] = $aRow['value']; + } + } + } + catch(MySQLException $e) + { + // Never mind, maybe the table does not exist yet (new installation from scratch) + // It seems more efficient to try and ignore errors than to test if the table & column really exists + } + return CMDBSource::Quote($aValues); + } + protected function GetSQLColSpec() { $default = $this->ScalarToSQL($this->GetDefaultValue()); diff --git a/pages/schema.php b/pages/schema.php index dfa246bd3..d25711b3d 100644 --- a/pages/schema.php +++ b/pages/schema.php @@ -881,12 +881,7 @@ function DisplayClassDetails($oPage, $sClass, $sContext) $sAllowedValues = ""; $sMoreInfo = ""; $sDefaultNullValue = ''; - $aCols = array(); - foreach ($oAttDef->GetSQLColumns() as $sCol => $sFieldDesc) - { - $aCols[] = "$sCol: $sFieldDesc"; - } - if (count($aCols) > 0) + if (call_user_func(array(get_class($oAttDef), 'IsBasedOnDBColumns'))) { $aMoreInfo = array(); diff --git a/synchro/synchrodatasource.class.inc.php b/synchro/synchrodatasource.class.inc.php index a22ac4da1..5ae90539c 100644 --- a/synchro/synchrodatasource.class.inc.php +++ b/synchro/synchrodatasource.class.inc.php @@ -1120,7 +1120,7 @@ EOF } } } - elseif (strcasecmp(CMDBSource::GetFieldType($sTable, $sColName), $sColumnDef) != 0) + elseif (!CMDBSource::IsSameFieldTypes(CMDBSource::GetFieldSpec($sTable, $sColName), $sColumnDef)) { $bFixNeeded = true; $bOneColIsMissing = true;