皆さん、ちゃんとMigrationsファイルは作っていますか?DB設計書は作っていますか?
深遠なる理由で(例えば片手間で作ったシステムが思いっきり使われてしまっていて、そのまま運用してたり)、MigrationsファイルもDB設計書もないときに
_人人人人人人人_
> 突然のDB死 <
 ̄Y^Y^Y^Y^Y^Y ̄
\(^o^)/オワタ
で、どこかに「スキーマ情報残っていないものか」と考えた挙句思いついたのが
スキーマ情報のキャッシュファイル
です。
CakePHPのスキーマキャッシュファイル
CakePHPのデフォルトのキャッシュ対象に、実はデータベースのスキーマ情報情報があります。
さらにデフォルト設定だとファイルキャッシュで app/tmp/cache/models/
に保存されています。
これが、実はただのシリアライズファイル(+タイムスタンプ)なので、ここからスキーマ情報情報のサルベージを試みてみました。
サルベージスキーマ.php
<?php
define('MODEL_CACHE_DIR', __DIR__ . '/app/tmp/cache/models');
// app/Config/Schema/schema.phpのヘッダ行
$header = <<<EOF
<?php
class AppSchema extends CakeSchema {
public function before(\$event = array()) {
return true;
}
public function after(\$event = array()) {
}
EOF;
// app/Config/Schema/schema.phpのフッタ行
$footer = <<<EOF
}
EOF;
$out = $header;
// emptyファイルの削除と*_listファイルからキャッシュファイル名のprefixを取得
$prefix;
$schemaCacheFiles = array();
foreach (glob(MODEL_CACHE_DIR . '/*') as $filePath) {
$fileName = basename($filePath);
if ($fileName === 'empty') {
continue;
}
if (preg_match('/^(.+)_list$/', $fileName, $matches)) {
$prefix = $matches[1];
continue;
}
$schemaCacheFiles[] = $filePath;
}
// 各キャッシュファイルからスキーマ情報をサルベージ
foreach ($schemaCacheFiles as $filePath) {
$fileName = basename($filePath);
$tableName = preg_replace('/^' . $prefix . '_/', '', $fileName);
$out .= ' public $' . $tableName . ' = ';
$contents = explode("\n", file_get_contents($filePath));
$serialized = $contents[1];
$out .= var_export(unserialize($serialized), true);
$out .= ';' . "\n";
}
$out .= $footer;
echo $out;
これを
$ cd /path/to/project_root/
$ cp /path/to/salvage_schema.php ./
こうして
$ php salvage_schema.php > app/Config/Schema/schema.php
こう!
$ ./Vender/bin/cake -app app schema create
復活!!
というわけで
ちゃんとスキーマ情報は記録しておきましょう。