From 5afec7c9931379fb1d2d2a889645ba0ccafdb8c5 Mon Sep 17 00:00:00 2001 From: Andrey Kutejko Date: Thu, 14 Aug 2014 22:01:37 +0300 Subject: [PATCH 1/1] initial version --- .gitignore | 2 ++ composer.json | 24 ++++++++++++++ src/migration.php | 24 ++++++++++++++ src/migrations.php | 83 ++++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 133 insertions(+) create mode 100644 .gitignore create mode 100644 composer.json create mode 100644 src/migration.php create mode 100644 src/migrations.php diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..fcac4a7 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +/vendor + diff --git a/composer.json b/composer.json new file mode 100644 index 0000000..3bc937f --- /dev/null +++ b/composer.json @@ -0,0 +1,24 @@ +{ + "name": "andy128k/migrations", + "description": "Simple DB schema migrations", + "license": "MIT", + "authors": [ + { + "name": "Andrey Kutejko", + "email": "andy128k@gmail.com" + } + ], + "autoload": { + "classmap" : ["src/"] + }, + "require": { + "php": ">=5.3" + }, + "repositories": [ + { + "type": "composer", + "url": "http://packages.andy128k.net/php/" + } + ] +} + diff --git a/src/migration.php b/src/migration.php new file mode 100644 index 0000000..66ea729 --- /dev/null +++ b/src/migration.php @@ -0,0 +1,24 @@ +connection->prepare($query); + $st->execute($params); + + $rows = array(); + foreach ($st->fetchAll(\PDO::FETCH_ASSOC) as $r) + $rows[] = (object)$r; + + $st->closeCursor(); + return $rows; + } +} + diff --git a/src/migrations.php b/src/migrations.php new file mode 100644 index 0000000..0711854 --- /dev/null +++ b/src/migrations.php @@ -0,0 +1,83 @@ +ensureLogExists($connection); + + $files = array(); + foreach ($paths as $path) + $files = array_merge($files, glob($path.'/*.php')); + + sort($files); + foreach ($files as $file) { + $ts = substr(basename($file), 0, 14); + + if ($this->migrationPassed($connection, $ts)) + continue; + + echo "Run migration $file\n"; + require_once $file; + + $connection->beginTransaction(); + try { + $migration = 'Migration_'.$ts; + $migration = new $migration; + $migration->connection = $connection; + $migration->migrate(); + + $this->markMigration($connection, $ts); + } catch (\Exception $e) { + $connection->rollback(); + throw $e; + } + $connection->commit(); + } + } + + public function createMigration($path, $hint='') + { + $ts = date('YmdHis'); + + $name = preg_replace('/[^a-z0-9]+/i', '_', $hint); + $name = preg_replace('/__+/', '_', $name); + $name = preg_replace('/^_/i', '', $name); + $name = preg_replace('/_$/i', '', $name); + if ($name) + $name = '_'.$name; + + $filename = $path.'/'.$ts.$name.'.php'; + + file_put_contents($filename, "query("SHOW TABLES LIKE 'migration_log'"); + $exists = $st->fetch(); + $st->closeCursor(); + + if (!$exists) { + $connection->exec('CREATE TABLE migration_log (ts CHAR(14) NOT NULL PRIMARY KEY) ENGINE = INNODB'); + } + } + + private function migrationPassed($connection, $ts) + { + $st = $connection->query("SELECT 1 FROM migration_log WHERE ts = '$ts'"); + $exists = $st->fetch(); + $st->closeCursor(); + return $exists; + } + + private function markMigration($connection, $ts) + { + $st = $connection->exec("INSERT INTO migration_log (ts) VALUES ('$ts')"); + } +} + -- 2.49.0