Autogenerate model classes with Laravel 4 (aka using an existing database with L4)

前端 未结 3 505
暗喜
暗喜 2021-01-06 11:19

I\'ve designed my database in MySQL Workbench, and have all my foreign keys setup, etc.

I\'m wanting to use this DB schema with Laravel 4, however from the docs ther

相关标签:
3条回答
  • 2021-01-06 11:39

    Hmm I had the same issue and I wrote a little script myself which generates base classes and solves the foreign key issues. It's a basic solution and only determines "hasOne" relations, which you might have to change to hasMany later on. I used a Controller and build my code Template in a view:

    Controller:

    namespace Admin;
    
    /**
     * just a quick helper to generate model classes
     * from mysql to Eloquent style ones..
     * @author Mario
     */
    class ModelController extends \BaseController {
    
        /**
         * save Classes in folder of choice
         *
         * @return void
         */
        public function create($folder)
        {
            $sql = "SELECT * FROM information_schema.tables WHERE table_schema = 'UR_SCHEMA'";
            $tables = \DB::select($sql); 
    
            $sql2 = "select * from information_schema.`KEY_COLUMN_USAGE` where constraint_schema = 'UR_SCHEMA' order by table_name";
            $keys = \DB::select($sql2);
            $meta = $this->sortOutMetadata($keys);
    
            foreach ($tables as $table) {
                $metaData = null;
                if(!empty($meta[$table->TABLE_NAME])){
                    $metaData = $meta[$table->TABLE_NAME];
                }
    
                $code = \View::make('model.start', array('table' => $table, 'meta' => $metaData))->render();
                file_put_contents($folder.DIRECTORY_SEPARATOR.ucfirst(camel_case($table->TABLE_NAME).'.php'), $code);
            }
    
        }
    
        /**
         * provide structure indexed by table
         * 
         * @param type $keys
         * @return type
         */
        private function sortOutMetadata($keys)
        {
            $return = array();
    
            foreach ($keys as $key) {
    
                if ($key->CONSTRAINT_NAME == 'PRIMARY') {
                    $return[$key->TABLE_NAME]['pk'] = $key->COLUMN_NAME;
                } elseif (!empty($key->REFERENCED_TABLE_NAME)) {
                    //one way
                    $return[$key->TABLE_NAME]['fk'][] = array('column' => $key->COLUMN_NAME,
                        'refColumn' => $key->REFERENCED_COLUMN_NAME,
                        'refTable' => $key->REFERENCED_TABLE_NAME,);
                    //and the other
                    $return[$key->REFERENCED_TABLE_NAME]['fk'][] = array('column' => $key->REFERENCED_COLUMN_NAME,
                        'refColumn' => $key->COLUMN_NAME,
                        'refTable' => $key->TABLE_NAME,);
                }
            }
    
            return $return;
        }
    }
    

    My view Template (pretty much my Class Template)

    <?php echo '<?php'; ?>
    
    
    namespace Model\Base;
    
    use Model\Model;
    
    class <?php echo ucfirst(camel_case($table->TABLE_NAME));?> extends Model {
    
        /**
         * @var String
         */
        protected $table = '<?php echo $table->TABLE_NAME;?>';
        <?php if (isset($meta['pk'])):?>
        /**
         * @var String
         */
        protected $primaryKey = '<?php echo $meta['pk'];?>';
    
    
        /**
         * attributes not writable from outside
         * @var mixed
         */
        protected $guarded = array('<?php echo $meta['pk'];?>');
        <?php endif;?>
        /**
         * Timestamps we dont want here
         * @var Boolean
         */
        public $timestamps = false;
    
        <?php if (isset($meta['fk'])):?>
            <?php foreach($meta['fk'] as $keys):?>
        /**
         * @return HasOne
         */
        public function <?php echo camel_case($keys['refTable']);?>()
        {
            return $this->hasOne('Model\<?php echo ucfirst(camel_case($keys['refTable']));?>', '<?php echo $keys['refColumn'];?>', '<?php echo $keys['column'];?>');
        }
            <?php endforeach;?>
        <?php endif;?>
    
    }
    

    Then Simply generate your base classes by giving it the folder: (from wherever you prefer)

    $controller = new \Admin\ModelController();
    $controller->create(__DIR__ . DIRECTORY_SEPARATOR . 'tmpModel');
    

    This gave me some decent way to get my base classes Auto generated the way I needed. Remember you got to be able to see the information_schema schema with your db user.

    Hope this helps

    0 讨论(0)
  • 2021-01-06 11:42

    cakePHP does a great job at fleshing out your whole project from the DB schema already in place. Laravel currently does not support anything like this. One of the minor features still holding me back from adopting laravel.

    0 讨论(0)
  • 2021-01-06 11:46

    The good news is that Antonio just finished his MySQL WorkBench to Eloquent ORM converter This is a beautiful solution but comes a way to late for me but may help you a lot.

    Update: The link isn't working in the moment. The wabpage says "We are redesigning things, will be back soon!". I allready sent antonio an email asking him, when this service will be available again.

    Antonio said that it'll be back but there is no estimated time of arrival. We have to wait..

    0 讨论(0)
提交回复
热议问题