3
* $Id: Builder.php 2939 2007-10-19 14:23:42Z Jonathan.Wage $
5
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
6
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
7
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
8
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
9
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
10
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
11
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
12
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
13
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
14
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
15
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
17
* This software consists of voluntary contributions made by many individuals
18
* and is licensed under the LGPL. For more information, see
19
* <http://www.phpdoctrine.org>.
23
* Doctrine_Migration_Builder
26
* @subpackage Migration
27
* @author Konsta Vesterinen <kvesteri@cc.hut.fi>
28
* @author Jonathan H. Wage <jwage@mac.com>
29
* @license http://www.opensource.org/licenses/lgpl-license.php LGPL
30
* @link www.phpdoctrine.org
32
* @version $Revision: 2939 $
34
class Doctrine_Migration_Builder extends Doctrine_Builder
39
* The path to your migration classes directory
43
private $migrationsPath = '';
48
* File suffix to use when writing class definitions
52
private $suffix = '.class.php';
64
* Class template used for writing classes
75
public function __construct($migrationsPath = null)
77
if ($migrationsPath) {
78
$this->setMigrationsPath($migrationsPath);
79
$this->migration = new Doctrine_Migration($migrationsPath);
82
$this->loadTemplate();
88
* @param string path the path where migration classes are stored and being generated
91
public function setMigrationsPath($path)
93
Doctrine_Lib::makeDirectories($path);
95
$this->migrationsPath = $path;
101
* @return string the path where migration classes are stored and being generated
103
public function getMigrationsPath()
105
return $this->migrationsPath;
111
* Loads the class template used for generating classes
115
protected function loadTemplate()
117
if (isset(self::$tpl)) {
123
* This class has been auto-generated by the Doctrine ORM Framework
132
public function down()
141
* generateMigrationsFromDb
145
public function generateMigrationsFromDb()
147
$directory = sys_get_temp_dir() . DIRECTORY_SEPARATOR . 'tmp_doctrine_models';
149
Doctrine::generateModelsFromDb($directory);
151
$result = $this->generateMigrationsFromModels($directory, Doctrine::MODEL_LOADING_CONSERVATIVE);
153
Doctrine_Lib::removeDirectories($directory);
159
* generateMigrationsFromModels
161
* @param string $modelsPath
164
public function generateMigrationsFromModels($modelsPath = null, $modelLoading = null)
166
if ($modelsPath !== null) {
167
$models = Doctrine::filterInvalidModels(Doctrine::loadModels($modelsPath, $modelLoading));
169
$models = Doctrine::getLoadedModels();
172
$models = Doctrine::initializeModels($models);
174
$foreignKeys = array();
176
foreach ($models as $model) {
177
$table = Doctrine::getTable($model);
178
if ($table->getTableName() !== $this->migration->getTableName()) {
179
$export = $table->getExportableFormat();
181
$foreignKeys[$export['tableName']] = $export['options']['foreignKeys'];
183
$up = $this->buildCreateTable($export);
184
$down = $this->buildDropTable($export);
186
$className = 'Add' . Doctrine_Inflector::classify($export['tableName']);
188
$this->generateMigrationClass($className, array(), $up, $down);
192
if ( ! empty($foreignKeys)) {
193
$className = 'ApplyForeignKeyConstraints';
197
foreach ($foreignKeys as $tableName => $definitions) {
198
$tableForeignKeyNames[$tableName] = array();
200
foreach ($definitions as $definition) {
201
$definition['name'] = $tableName . '_' .implode('_', (array)$definition['local']);
203
$up .= $this->buildCreateForeignKey($tableName, $definition);
204
$down .= $this->buildDropForeignKey($tableName, $definition);
208
$this->generateMigrationClass($className, array(), $up, $down);
215
* buildCreateForeignKey
217
* @param string $tableName
218
* @param string $definition
221
public function buildCreateForeignKey($tableName, $definition)
223
return "\t\t\$this->createForeignKey('" . $tableName . "', " . $this->varExport($definition, true) . ");";
227
* buildDropForeignKey
229
* @param string $tableName
230
* @param string $definition
233
public function buildDropForeignKey($tableName, $definition)
235
return "\t\t\$this->dropForeignKey('" . $tableName . "', '" . $definition['name'] . "');\n";
241
* @param string $tableData
244
public function buildCreateTable($tableData)
246
$code = "\t\t\$this->createTable('" . $tableData['tableName'] . "', ";
248
$code .= $this->varExport($tableData['columns'], true) . ", ";
250
$code .= $this->varExport(array('indexes' => $tableData['options']['indexes'], 'primary' => $tableData['options']['primary']), true);
260
* @param string $tableData
263
public function buildDropTable($tableData)
265
return "\t\t\$this->dropTable('" . $tableData['tableName'] . "');";
269
* generateMigrationClass
273
public function generateMigrationClass($className, $options = array(), $up = null, $down = null, $return = false)
275
$className = Doctrine_Inflector::urlize($className);
276
$className = str_replace('-', '_', $className);
277
$className = Doctrine_Inflector::classify($className);
279
if ($return || ! $this->getMigrationsPath()) {
280
return $this->buildMigrationClass($className, null, $options, $up, $down);
282
if ( ! $this->getMigrationsPath()) {
283
throw new Doctrine_Migration_Exception('You must specify the path to your migrations.');
286
$next = (string) $this->migration->getNextVersion();
288
$fileName = str_repeat('0', (3 - strlen($next))) . $next . '_' . Doctrine_Inflector::tableize($className) . $this->suffix;
290
$class = $this->buildMigrationClass($className, $fileName, $options, $up, $down);
292
$path = $this->getMigrationsPath() . DIRECTORY_SEPARATOR . $fileName;
294
if ( class_exists($className) || file_exists($path)) {
298
file_put_contents($path, $class);
305
* buildMigrationClass
309
public function buildMigrationClass($className, $fileName = null, $options = array(), $up = null, $down = null)
311
$extends = isset($options['extends']) ? $options['extends']:'Doctrine_Migration';
313
$content = '<?php' . PHP_EOL;
315
$content .= sprintf(self::$tpl, $className,
b'\\ No newline at end of file'