/** * Returns the difference between the tables $fromTable and $toTable. * * If there are no differences this method returns the boolean false. * * @param \Doctrine\DBAL\Schema\Table $fromTable * @param \Doctrine\DBAL\Schema\Table $toTable * @return bool|\Doctrine\DBAL\Schema\TableDiff|\TYPO3\CMS\Core\Database\Schema\TableDiff * @throws \InvalidArgumentException */ public function diffTable(Table $fromTable, Table $toTable) { $newTableOptions = array_merge($fromTable->getOptions(), $toTable->getOptions()); $optionDiff = array_diff_assoc($newTableOptions, $fromTable->getOptions()); $tableDifferences = parent::diffTable($fromTable, $toTable); // No changed table options, return parent result if (count($optionDiff) === 0) { return $tableDifferences; } if ($tableDifferences === false) { $tableDifferences = GeneralUtility::makeInstance(TableDiff::class, $fromTable->getName()); $tableDifferences->fromTable = $fromTable; } else { // Rebuild TableDiff with enhanced TYPO3 TableDiff class $tableDifferences = GeneralUtility::makeInstance(TableDiff::class, $tableDifferences->name, $tableDifferences->addedColumns, $tableDifferences->changedColumns, $tableDifferences->removedColumns, $tableDifferences->addedIndexes, $tableDifferences->changedIndexes, $tableDifferences->removedIndexes, $tableDifferences->fromTable); } // Set the table options to be parsed in the AlterTable event. $tableDifferences->setTableOptions($optionDiff); return $tableDifferences; }
/** * Add a table object to the schema * * @param Table $table table object to add * * @return void */ public function addTable(Table $table) { //echo '<h2>addTable()</h2>'; try { $name = $table->getName(); $len = strlen($this->xPrefix); if (substr_compare($name, $this->xPrefix, 0, $len) === 0) { $name = substr($name, $len); if (empty($this->tableList) || in_array($name, $this->tableList)) { $idGeneratorType = 0; // how should we handle this? $newtable = new Table($name, $table->getColumns(), $table->getIndexes(), $table->getForeignKeys(), $idGeneratorType, $table->getOptions()); $this->_addTable($newtable); } } //Debug::dump($table); } catch (\Exception $e) { \Xoops::getInstance()->events()->triggerEvent('core.exception', $e); throw $e; } }
/** * @param \TYPO3\CMS\Core\Database\Schema\Parser\AST\CreateIndexDefinitionItem $item * @return \Doctrine\DBAL\Schema\Index * @throws \Doctrine\DBAL\Schema\SchemaException * @throws \InvalidArgumentException */ protected function addIndex(CreateIndexDefinitionItem $item) : Index { $indexName = $item->indexName->getQuotedName(); $columnNames = array_map(function (IndexColumnName $columnName) { if ($columnName->length) { return $columnName->columnName->getQuotedName() . '(' . $columnName->length . ')'; } return $columnName->columnName->getQuotedName(); }, $item->columnNames); if ($item->isPrimary) { $this->table->setPrimaryKey($columnNames); $index = $this->table->getPrimaryKey(); } else { $index = GeneralUtility::makeInstance(Index::class, $indexName, $columnNames, $item->isUnique, $item->isPrimary); if ($item->isFulltext) { $index->addFlag('fulltext'); } elseif ($item->isSpatial) { $index->addFlag('spatial'); } $this->table = GeneralUtility::makeInstance(Table::class, $this->table->getQuotedName($this->platform), $this->table->getColumns(), array_merge($this->table->getIndexes(), [strtolower($indexName) => $index]), $this->table->getForeignKeys(), 0, $this->table->getOptions()); } return $index; }
/** * Gets the SQL statement(s) to create a table with the specified name, columns and constraints * on this platform. * * @param string $table The name of the table. * @param int $createFlags * @return array The sequence of SQL statements. */ public function getCreateTableSQL(Table $table, $createFlags = self::CREATE_INDEXES) { if (!is_int($createFlags)) { throw new \InvalidArgumentException("Second argument of AbstractPlatform::getCreateTableSQL() has to be integer."); } if (count($table->getColumns()) == 0) { throw DBALException::noColumnsSpecifiedForTable($table->getName()); } $tableName = $table->getQuotedName($this); $options = $table->getOptions(); $options['uniqueConstraints'] = array(); $options['indexes'] = array(); $options['primary'] = array(); if (($createFlags & self::CREATE_INDEXES) > 0) { foreach ($table->getIndexes() as $index) { /* @var $index Index */ if ($index->isPrimary()) { $options['primary'] = $index->getColumns(); } else { $options['indexes'][$index->getName()] = $index; } } } $columnSql = array(); $columns = array(); foreach ($table->getColumns() as $column) { /* @var \Doctrine\DBAL\Schema\Column $column */ if (null !== $this->_eventManager && $this->_eventManager->hasListeners(Events::onSchemaCreateTableColumn)) { $eventArgs = new SchemaCreateTableColumnEventArgs($column, $table, $this); $this->_eventManager->dispatchEvent(Events::onSchemaCreateTableColumn, $eventArgs); $columnSql = array_merge($columnSql, $eventArgs->getSql()); if ($eventArgs->isDefaultPrevented()) { continue; } } $columnData = array(); $columnData['name'] = $column->getQuotedName($this); $columnData['type'] = $column->getType(); $columnData['length'] = $column->getLength(); $columnData['notnull'] = $column->getNotNull(); $columnData['fixed'] = $column->getFixed(); $columnData['unique'] = false; // TODO: what do we do about this? $columnData['version'] = $column->hasPlatformOption("version") ? $column->getPlatformOption('version') : false; if (strtolower($columnData['type']) == "string" && $columnData['length'] === null) { $columnData['length'] = 255; } $columnData['unsigned'] = $column->getUnsigned(); $columnData['precision'] = $column->getPrecision(); $columnData['scale'] = $column->getScale(); $columnData['default'] = $column->getDefault(); $columnData['columnDefinition'] = $column->getColumnDefinition(); $columnData['autoincrement'] = $column->getAutoincrement(); $columnData['comment'] = $this->getColumnComment($column); if (in_array($column->getName(), $options['primary'])) { $columnData['primary'] = true; } $columns[$columnData['name']] = $columnData; } if (($createFlags & self::CREATE_FOREIGNKEYS) > 0) { $options['foreignKeys'] = array(); foreach ($table->getForeignKeys() as $fkConstraint) { $options['foreignKeys'][] = $fkConstraint; } } if (null !== $this->_eventManager && $this->_eventManager->hasListeners(Events::onSchemaCreateTable)) { $eventArgs = new SchemaCreateTableEventArgs($table, $columns, $options, $this); $this->_eventManager->dispatchEvent(Events::onSchemaCreateTable, $eventArgs); if ($eventArgs->isDefaultPrevented()) { return array_merge($eventArgs->getSql(), $columnSql); } } $sql = $this->_getCreateTableSQL($tableName, $columns, $options); if ($this->supportsCommentOnStatement()) { foreach ($table->getColumns() as $column) { if ($this->getColumnComment($column)) { $sql[] = $this->getCommentOnColumnSQL($tableName, $column->getName(), $this->getColumnComment($column)); } } } return array_merge($sql, $columnSql); }
/** * @param \Doctrine\DBAL\Schema\Table $table * @param string $newName * @return \Doctrine\DBAL\Schema\Table */ protected function renameTableSchema(Table $table, $newName) { /** * @var \Doctrine\DBAL\Schema\Index[] $indexes */ $indexes = $table->getIndexes(); $newIndexes = array(); foreach ($indexes as $index) { if ($index->isPrimary()) { // do not rename primary key $indexName = $index->getName(); } else { // avoid conflicts in index names $indexName = $this->config->getSystemValue('dbtableprefix', 'oc_') . $this->random->generate(13, ISecureRandom::CHAR_LOWER); } $newIndexes[] = new Index($indexName, $index->getColumns(), $index->isUnique(), $index->isPrimary()); } // foreign keys are not supported so we just set it to an empty array return new Table($newName, $table->getColumns(), $newIndexes, array(), 0, $table->getOptions()); }
/** * Gets the SQL statement(s) to create a table with the specified name, columns and constraints * on this platform. * * @param string $table The name of the table. * @param int $createFlags * @return array The sequence of SQL statements. */ public function getCreateTableSQL(Table $table, $createFlags = self::CREATE_INDEXES) { if (!is_int($createFlags)) { throw new \InvalidArgumentException("Second argument of AbstractPlatform::getCreateTableSQL() has to be integer."); } if (count($table->getColumns()) == 0) { throw DBALException::noColumnsSpecifiedForTable($table->getName()); } $tableName = $table->getName(); $options = $table->getOptions(); $options['uniqueConstraints'] = array(); $options['indexes'] = array(); $options['primary'] = array(); if (($createFlags & self::CREATE_INDEXES) > 0) { foreach ($table->getIndexes() as $index) { /* @var $index Index */ if ($index->isPrimary()) { $options['primary'] = $index->getColumns(); } else { $options['indexes'][$index->getName()] = $index; } } } $columns = array(); foreach ($table->getColumns() as $column) { /* @var \Doctrine\DBAL\Schema\Column $column */ $columnData = array(); $columnData['name'] = $column->getName(); $columnData['type'] = $column->getType(); $columnData['length'] = $column->getLength(); $columnData['notnull'] = $column->getNotNull(); $columnData['unique'] = $column->hasPlatformOption("unique") ? $column->getPlatformOption('unique') : false; $columnData['version'] = $column->hasPlatformOption("version") ? $column->getPlatformOption('version') : false; if (strtolower($columnData['type']) == "string" && $columnData['length'] === null) { $columnData['length'] = 255; } $columnData['precision'] = $column->getPrecision(); $columnData['scale'] = $column->getScale(); $columnData['default'] = $column->getDefault(); $columnData['columnDefinition'] = $column->getColumnDefinition(); if (in_array($column->getName(), $options['primary'])) { $columnData['primary'] = true; if ($table->isIdGeneratorIdentity()) { $columnData['autoincrement'] = true; } } $columns[$columnData['name']] = $columnData; } if (($createFlags & self::CREATE_FOREIGNKEYS) > 0) { $options['foreignKeys'] = array(); foreach ($table->getForeignKeys() as $fkConstraint) { $options['foreignKeys'][] = $fkConstraint; } } return $this->_getCreateTableSQL($tableName, $columns, $options); }
/** * {@inheritDoc} * Gets the SQL statement(s) to create a table with the specified name, columns and constraints * on this platform. * * @param Table $table The name of the table. * @param integer $createFlags * * @return array The sequence of SQL statements. */ public function getCreateTableSQL(Table $table, $createFlags = self::CREATE_INDEXES) { if (!is_int($createFlags)) { $msg = "Second argument of CratePlatform::getCreateTableSQL() has to be integer."; throw new \InvalidArgumentException($msg); } if (count($table->getColumns()) === 0) { throw DBALException::noColumnsSpecifiedForTable($table->getName()); } $tableName = $table->getQuotedName($this); $options = $table->getOptions(); $options['uniqueConstraints'] = array(); $options['indexes'] = array(); $options['primary'] = array(); if (($createFlags & self::CREATE_INDEXES) > 0) { foreach ($table->getIndexes() as $index) { /* @var $index Index */ if ($index->isPrimary()) { $platform = $this; $options['primary'] = array_map(function ($columnName) use($table, $platform) { return $table->getColumn($columnName)->getQuotedName($platform); }, $index->getColumns()); $options['primary_index'] = $index; } else { $options['indexes'][$index->getName()] = $index; } } } $columnSql = array(); $columns = array(); foreach ($table->getColumns() as $column) { if (null !== $this->_eventManager && $this->_eventManager->hasListeners(Events::onSchemaCreateTableColumn)) { $eventArgs = new SchemaCreateTableColumnEventArgs($column, $table, $this); $this->_eventManager->dispatchEvent(Events::onSchemaCreateTableColumn, $eventArgs); $columnSql = array_merge($columnSql, $eventArgs->getSql()); if ($eventArgs->isDefaultPrevented()) { continue; } } $columns[$column->getQuotedName($this)] = $this->prepareColumnData($column, $options['primary']); } if (null !== $this->_eventManager && $this->_eventManager->hasListeners(Events::onSchemaCreateTable)) { $eventArgs = new SchemaCreateTableEventArgs($table, $columns, $options, $this); $this->_eventManager->dispatchEvent(Events::onSchemaCreateTable, $eventArgs); if ($eventArgs->isDefaultPrevented()) { return array_merge($eventArgs->getSql(), $columnSql); } } $sql = $this->_getCreateTableSQL($tableName, $columns, $options); if ($this->supportsCommentOnStatement()) { foreach ($table->getColumns() as $column) { if ($this->getColumnComment($column)) { $sql[] = $this->getCommentOnColumnSQL($tableName, $column->getName(), $this->getColumnComment($column)); } } } return array_merge($sql, $columnSql); }
/** * @param \Doctrine\DBAL\Schema\Table $table * @param string $newName * @return \Doctrine\DBAL\Schema\Table */ protected function renameTableSchema(Table $table, $newName) { /** * @var \Doctrine\DBAL\Schema\Index[] $indexes */ $indexes = $table->getIndexes(); $newIndexes = array(); foreach ($indexes as $index) { if ($index->isPrimary()) { // do not rename primary key $indexName = $index->getName(); } else { // avoid conflicts in index names $indexName = 'oc_' . \OCP\Util::generateRandomBytes(13); } $newIndexes[] = new Index($indexName, $index->getColumns(), $index->isUnique(), $index->isPrimary()); } // foreign keys are not supported so we just set it to an empty array return new Table($newName, $table->getColumns(), $newIndexes, array(), 0, $table->getOptions()); }
/** * Tests whether both tables are equal. * * @param Table $expected * @param Table $actual */ protected function compareTable(Table $expected, Table $actual) { $this->assertEquals($expected->getColumns(), $actual->getColumns()); $this->assertEquals($expected->getOptions(), $actual->getOptions()); }
/** * Accept a table * * @param Table $table a table object * * @return void */ public function acceptTable(Table $table) { $this->schemaArray['tables'][$table->getName()]['options'] = $table->getOptions(); }