* Setup: updates from old versions (eg. 1.4 or 1.8) no longer require to update to 14.x and 16.1 first

This commit is contained in:
Ralf Becker 2018-04-13 13:46:49 +02:00
parent f1437d4ccb
commit 77b79f24b7
4 changed files with 70 additions and 20 deletions

View File

@ -8,7 +8,6 @@
* @package api * @package api
* @subpackage setup * @subpackage setup
* @license http://opensource.org/licenses/gpl-license.php GPL - GNU General Public License * @license http://opensource.org/licenses/gpl-license.php GPL - GNU General Public License
* @version $Id$
*/ */
$phpgw_baseline = array( $phpgw_baseline = array(

View File

@ -7,8 +7,7 @@
* @package api * @package api
* @subpackage db * @subpackage db
* @author Ralf Becker <RalfBecker-AT-outdoor-training.de> * @author Ralf Becker <RalfBecker-AT-outdoor-training.de>
* @copyright (c) 2003-16 by Ralf Becker <RalfBecker-AT-outdoor-training.de> * @copyright (c) 2003-18 by Ralf Becker <RalfBecker-AT-outdoor-training.de>
* @version $Id$
*/ */
namespace EGroupware\Api\Db; namespace EGroupware\Api\Db;
@ -514,7 +513,7 @@ class Backup
if (substr($line,0,9) == 'version: ') if (substr($line,0,9) == 'version: ')
{ {
$api_version = trim(substr($line,9)); // currenty not used: $api_version = trim(substr($line,9));
continue; continue;
} }
if (substr($line,0,9) == 'charset: ') if (substr($line,0,9) == 'charset: ')

View File

@ -12,7 +12,6 @@
* @license http://opensource.org/licenses/gpl-license.php GPL - GNU General Public License * @license http://opensource.org/licenses/gpl-license.php GPL - GNU General Public License
* @package api * @package api
* @subpackage db * @subpackage db
* @version $Id$
*/ */
namespace EGroupware\Api\Db; namespace EGroupware\Api\Db;
@ -20,7 +19,7 @@ namespace EGroupware\Api\Db;
use EGroupware\Api; use EGroupware\Api;
/** /**
* eGW's ADOdb based schema-processor * EGroupware's ADOdb based schema-processor
*/ */
class Schema class Schema
{ {
@ -536,7 +535,7 @@ class Schema
* Create an (unique) Index over one or more columns * Create an (unique) Index over one or more columns
* *
* @param string $sTableName table-name * @param string $sTableName table-name
* @param array $aColumnNames columns for the index * @param string|array $aColumnNames column(s) for the index
* @param boolean $bUnique =false true for a unique index, default false * @param boolean $bUnique =false true for a unique index, default false
* @param array|string $options ='' db-sepecific options, default '' = none * @param array|string $options ='' db-sepecific options, default '' = none
* @param string $sIdxName ='' name of the index, if not given (default) its created automaticaly * @param string $sIdxName ='' name of the index, if not given (default) its created automaticaly
@ -556,6 +555,18 @@ class Schema
if (!is_array($options)) $options = $options ? array($options) : array(); if (!is_array($options)) $options = $options ? array($options) : array();
if ($bUnique) $options[] = 'UNIQUE'; if ($bUnique) $options[] = 'UNIQUE';
// if index already exists drop it first
$definition = array();
$this->GetIndexes($sTableName, $definition);
$type = $bUnique ? 'uc' : 'ix';
if ($this->_in_index($aColumnNames, $definition[$type], true) ||
// sometimes index is listed as unique index too --> ignore that
($type == 'ix' && $this->_in_index($aColumnNames, $definition['uc'], true)))
{
//error_log(__METHOD__."('$sTableName', ['".implode("','", (array)$aColumnNames)."'], $bUnique, ...) already exists --> droping it first");
$this->DropIndex($sTableName, (array)$aColumnNames);
}
$aSql = $this->dict->CreateIndexSQL($sIdxName,$sTableName,$aColumnNames,$options); $aSql = $this->dict->CreateIndexSQL($sIdxName,$sTableName,$aColumnNames,$options);
return $this->ExecuteSQLArray($aSql,2,'CreateIndexSQL(%1,%2,%3,%4) sql=%5',False,$sTableName,$aColumnNames,$options,$sIdxName,$aSql); return $this->ExecuteSQLArray($aSql,2,'CreateIndexSQL(%1,%2,%3,%4) sql=%5',False,$sTableName,$aColumnNames,$options,$sIdxName,$aSql);
@ -1100,6 +1111,13 @@ class Schema
$ado_col = 'I AUTOINCREMENT NOTNULL'; $ado_col = 'I AUTOINCREMENT NOTNULL';
unset($col_data['nullable']); // else we set it twice unset($col_data['nullable']); // else we set it twice
break; break;
case 'binary': // varbinary column for MySQL/MariaDB
if ($this->sType == 'mysql' && $col_data['precision'] <= $this->max_varchar_length)
{
$ado_col = 'C('.$col_data['precision'].') CONSTRAINT "CHARACTER SET binary"';
break;
}
// fall through to blob
case 'blob': case 'blob':
$ado_col = 'B'; $ado_col = 'B';
break; break;
@ -1413,7 +1431,7 @@ class Schema
$s = strtolower($s); $s = strtolower($s);
}); });
} }
if (count($definition['pk']) && (implode(':',$definition['pk']) == implode(':',$index['columns']) || if (!empty($definition['pk']) && (implode(':',$definition['pk']) == implode(':',$index['columns']) ||
$index['unique'] && count(array_intersect($definition['pk'],$index['columns'])) == count($definition['pk']))) $index['unique'] && count(array_intersect($definition['pk'],$index['columns'])) == count($definition['pk'])))
{ {
continue; // is already the primary key => ignore it continue; // is already the primary key => ignore it
@ -1430,7 +1448,9 @@ class Schema
/** /**
* Check if all indexes exist and create them if not * Check if all indexes exist and create them if not
* *
* Does not check index-type of length! * Used eg. after restoring a backup to make sure all indexes are in place.
*
* Does not check index-type or length!
*/ */
function CheckCreateIndexes() function CheckCreateIndexes()
{ {
@ -1440,6 +1460,7 @@ class Schema
$definition = array(); $definition = array();
$this->GetIndexes($table, $definition); $this->GetIndexes($table, $definition);
$current = $this->m_odb->metadata($table, true);
// iterate though indexes we should have according to tables_current // iterate though indexes we should have according to tables_current
foreach(array('uc', 'ix') as $type) foreach(array('uc', 'ix') as $type)
@ -1449,6 +1470,12 @@ class Schema
// sometimes primary key is listed as (unique) index too --> ignore it // sometimes primary key is listed as (unique) index too --> ignore it
if ($this->_in_index($columns, array($table_def['pk']), true)) continue; if ($this->_in_index($columns, array($table_def['pk']), true)) continue;
// current table does NOT contain all columns, eg. not yet updated --> ignore index
if (array_diff((array)$columns, array_keys($current['meta'])))
{
//error_log(__METHOD__."() Can't create index over ", implode(',')." on table $table, as not all columns exist (yet)!");
continue;
}
// check if they exist in real table and create them if not // check if they exist in real table and create them if not
if (!$this->_in_index($columns, $definition[$type]) && if (!$this->_in_index($columns, $definition[$type]) &&
// sometimes index is listed as unique index too --> ignore that // sometimes index is listed as unique index too --> ignore that

View File

@ -10,7 +10,6 @@
* @author Miles Lott <milos@groupwhere.org> * @author Miles Lott <milos@groupwhere.org>
* @author Ralf Becker <RalfBecker-AT-outdoor-training.de> * @author Ralf Becker <RalfBecker-AT-outdoor-training.de>
* @license http://opensource.org/licenses/gpl-license.php GPL - GNU General Public License * @license http://opensource.org/licenses/gpl-license.php GPL - GNU General Public License
* @version $Id$
*/ */
use EGroupware\Api; use EGroupware\Api;
@ -515,17 +514,31 @@ class setup
'config_value' => $setup_info[$appname]['tables_prefix'], 'config_value' => $setup_info[$appname]['tables_prefix'],
),False,__LINE__,__FILE__); ),False,__LINE__,__FILE__);
} }
$this->db->insert($this->applications_table,array( try {
'app_name' => $appname, $this->db->insert($this->applications_table,array(
'app_enabled' => $enable, 'app_name' => $appname,
'app_order' => $setup_info[$appname]['app_order'], 'app_enabled' => $enable,
'app_tables' => (string)$tables, // app_tables is NOT NULL 'app_order' => $setup_info[$appname]['app_order'],
'app_version' => $setup_info[$appname]['version'], 'app_tables' => (string)$tables, // app_tables is NOT NULL
'app_index' => $setup_info[$appname]['index'], 'app_version' => $setup_info[$appname]['version'],
'app_icon' => $setup_info[$appname]['icon'], 'app_index' => $setup_info[$appname]['index'],
'app_icon_app' => $setup_info[$appname]['icon_app'], 'app_icon' => $setup_info[$appname]['icon'],
),False,__LINE__,__FILE__); 'app_icon_app' => $setup_info[$appname]['icon_app'],
),False,__LINE__,__FILE__);
}
catch (Api\Db\Exception\InvalidSql $e)
{
// ease update from pre 1.6 eg. 1.4 not having app_index, app_icon, app_icon_app columns
_egw_log_exception($e);
$this->db->insert($this->applications_table,array(
'app_name' => $appname,
'app_enabled' => $enable,
'app_order' => $setup_info[$appname]['app_order'],
'app_tables' => (string)$tables, // app_tables is NOT NULL
'app_version' => $setup_info[$appname]['version'],
),False,__LINE__,__FILE__);
}
Api\Egw\Applications::invalidate(); Api\Egw\Applications::invalidate();
} }
} }
@ -1024,6 +1037,18 @@ class setup
'account_email' => $email, 'account_email' => $email,
'account_members' => array() 'account_members' => array()
); );
// check if egw_accounts.account_description already exists, as the update otherwise fails
$meta = $GLOBALS['egw_setup']->db->metadata('egw_accounts', true);
if (!isset($meta['meta']['account_description']))
{
$GLOBALS['egw_setup']->oProc->AddColumn('egw_accounts','account_description',array(
'type' => 'varchar',
'precision' => '255',
'comment' => 'group description'
));
}
if (!($accountid = $this->accounts->save($account))) if (!($accountid = $this->accounts->save($account)))
{ {
error_log("setup::add_account('$username','$first','$last',\$passwd,'$primary_group',$changepw,'$email') failed! accountid=$accountid"); error_log("setup::add_account('$username','$first','$last',\$passwd,'$primary_group',$changepw,'$email') failed! accountid=$accountid");