記事を書くきっかけ
表題の通りで、例えばfizz_buzz_fizzbuzzという名前のテーブルのmodelを fromdb
で生成すると、 fuel/app/classes/model/fizz/buzz/fizzbuzz.php
というファイルが生成され、クラス名は Model_Fizz_Buzz_Fizzbuzz
となる。
これを、 fuel/app/classes/model/fizzbuzzfizzbuzz.php
というファイルが生成され、クラス名は Model_Fizzbuzzfizzbuzz
となるようにしたかった。
対応にあたって
同じ事で悩んだ方で、生成されたファイルを mv
して rm
して bootstrap.php
で Autoloader::add_classes
する解決策があったが、 fromdb
の便利さを享受したかったため、この方法は見送った。FuelPHPなので、ファイル名にアンダースコアを使用したくなかった、というのも見送った事の遠因ではある。
fromdb
が利用している packages/oil/classes/generate.php
の model
の処理で、ファイル名を決定する際に、アンダースコアとハイフンをdirectory separatorに置換するため、前述のような状態となる。
generate.php
も fromdb.php
も修正したくなかったので、 fromdb
を元にした fromdbunderscore
を作成した。
コード
使用方法は基本的にfromdbと同じです(ヘルプ変更していません...)
-
--singular
を指定しないと動作しないようにした。 -
--crud
が指定された場合動作しないようにした。 - ` -us-model-dir'で
fuel/app/classes/model
の下にディレクトリーを指定出来るようにした。 -
-us-base-model
で基底クラスを指定出来るようにした。 - 動作未検証なので
-no-migration
を必ず指定する事。
<?php
namespace Fuel\Tasks;
require_once(PKGPATH . 'oil/tasks/fromdb.php');
class Fromdbunderscore extends Fromdb
{
const ORIGINAL_PARENT_CLASS_NAME = '\Orm\Model';
private static $_model_dir = '';
private static $_parent_class_name = '';
public static function crud($tables = '')
{
\Cli::write('fromdbunderscore does not support crud.', 'red');
exit();
}
public static function model($tables = '')
{
// do we have any tables defined?
if (empty($tables))
{
// do we want to generate for all tables?
if ( ! \Cli::option('all', false))
{
\Cli::write('No table names specified to generate a model on.', 'red');
exit();
}
// get the list of all available tables
try
{
$list = \DB::list_tables(null, \Cli::option('db', null));
}
catch (\FuelException $e)
{
\Cli::write('The database driver configured does not support listing tables. Please specify them manually.', 'red');
exit();
}
$prefix = \DB::table_prefix();
$migration = \Config::get('migrations.table', 'migration');
$tables = array();
// create the table list
foreach ($list as $table)
{
// strip any defined table prefix from the table name
if ( ! empty($prefix) and strpos($table, $prefix) === 0)
{
$table = substr($table, strlen($prefix));
}
// skip the migration table
$table == $migration or $tables[] = $table;
}
}
// make sure we have an array to work with
is_array($tables) or $tables = explode(',', $tables);
static::_preprocess_for_generate();
// generate for each table defined
foreach ($tables as $table)
{
static::generate_model_under_score($table);
}
}
protected static function _preprocess_for_generate()
{
if(empty(\Cli::option('singular', ''))){
\Cli::write('You must specify the -singular option.', 'red');
exit();
}
static::$_model_dir = \Cli::option('us-model-dir', '');
static::$_parent_class_name = empty(\Cli::option('us-base-model', '')) ?
static::ORIGINAL_PARENT_CLASS_NAME : \Cli::option('us-base-model');
}
protected static function generate_model_under_score($table)
{
// start with an empty list
\Oil\Generate::$create_files = array();
$args = static::arguments($table);
// underscores are erased from table name
$table_name_which_has_not_underscores = str_replace('_', '', $args[0]);
$args[0] = $table_name_which_has_not_underscores;
// and generate, but doesn't create a file.
call_user_func('Oil\Generate::model', $args, false);
$filename = \Oil\Generate::$create_files[0]['path'];
// restore a table name in generated content
$search = array(sprintf('$_table_name = \'%s\'', $table_name_which_has_not_underscores));
$replace = array(sprintf('$_table_name = \'%s\'', $table));
// normalize a class name in generated content
$search[] = sprintf('Model_%s', ucfirst($table_name_which_has_not_underscores));
$replace[] = sprintf('Model_%s', ucfirst(\Inflector::camelize($table)));
// replace parent class name if neededed
if(!empty(static::$_parent_class_name)){
$search[] = static::ORIGINAL_PARENT_CLASS_NAME;
$replace[] = static::$_parent_class_name;
}
$contents = str_replace($search, $replace, \Oil\Generate::$create_files[0]['contents']);
$type = \Oil\Generate::$create_files[0]['type'];
$model_dir = empty(static::$_model_dir) ?
dirname($filename) : sprintf('%s/%s', dirname($filename), static::$_model_dir);
is_dir($model_dir) or mkdir($model_dir, 0755, TRUE);
$filename = sprintf('%s/%s', $model_dir, basename($filename));
// easy way
\Cli::write("\tCreating $type: $filename", 'green');
@file_put_contents($filename, $contents);
@chmod($filename, 0666);
}
}