From: Andrey Kutejko Date: Tue, 9 Jul 2013 22:25:00 +0000 (+0300) Subject: rework building models. allow to refer to models from previous application X-Git-Tag: 0.5~179 X-Git-Url: https://git.andy128k.dev/?a=commitdiff_plain;h=17539f6ca6d617643268fc936dbe99a46ab90773;p=ipf.git rework building models. allow to refer to models from previous application --- diff --git a/ipf/application.php b/ipf/application.php index 58f8835..b913480 100644 --- a/ipf/application.php +++ b/ipf/application.php @@ -82,11 +82,6 @@ abstract class IPF_Application return IPF_ORM::createTablesFromModels($this->path.'models'); } - public function generateModels() - { - IPF_ORM::generateModelsFromYaml($this->path.'models.yml', $this->path.'models'); - } - public function loadModels() { IPF_ORM::loadModels($this->path.'models'); diff --git a/ipf/command/buildcontribmodels.php b/ipf/command/buildcontribmodels.php index 9393be5..e231350 100644 --- a/ipf/command/buildcontribmodels.php +++ b/ipf/command/buildcontribmodels.php @@ -11,8 +11,11 @@ class IPF_Command_BuildContribModels $project = IPF_Project::getInstance(); - foreach ($project->frameworkApps() as $app) - $app->generateModels(); + $extraAllwedReferences = array(); + foreach ($project->frameworkApps() as $app) { + $models = IPF_ORM::generateModelsFromYaml($app->path, $extraAllwedReferences); + $extraAllwedReferences = array_merge($extraAllwedReferences, $models); + } } } diff --git a/ipf/command/buildmodels.php b/ipf/command/buildmodels.php index fed3806..8308ac9 100644 --- a/ipf/command/buildmodels.php +++ b/ipf/command/buildmodels.php @@ -7,17 +7,33 @@ class IPF_Command_BuildModels public function run($args=null) { - print "Build All Model Classes\n"; + print "Build all model classes\n"; $project = IPF_Project::getInstance(); - IPF_ORM::generateModelsFromYaml( - IPF::get('project_path').DIRECTORY_SEPARATOR.'models.yml', - IPF::get('project_path').DIRECTORY_SEPARATOR.'models' - ); + $extraAllwedReferences = $this->frameworkModels($project); + foreach ($this->paths($project) as $path) { + $models = IPF_ORM::generateModelsFromYaml($path, $extraAllwedReferences); + $extraAllwedReferences = array_merge($extraAllwedReferences, $models); + } + } + private function frameworkModels($project) + { + $models = array(); + foreach ($project->frameworkApps() as $app) + $models = array_merge($models, $app->modelList()); + return $models; + } + + private function paths($project) + { + $paths = array( + IPF::get('project_path'), + ); foreach ($project->customApps() as $app) - $app->generateModels(); + $paths[] = $app->path; + return $paths; } } diff --git a/ipf/orm.php b/ipf/orm.php index caef4cd..af280d6 100644 --- a/ipf/orm.php +++ b/ipf/orm.php @@ -185,14 +185,27 @@ final class IPF_ORM { return IPF_ORM_Manager::getInstance()->getConnectionForComponent($componentName)->getTable($componentName); } - - public static function generateModelsFromYaml($yamlPath, $directory, $options = array()) + + public static function generateModelsFromYaml($directory, $extraAllwedReferences=array()) { - $import = new IPF_ORM_Import_Schema(); - $import->setOptions($options); - $import->importSchema($yamlPath, 'yml', $directory); + // load schema + $import = new IPF_ORM_Import_Schema; + $definitions = $import->importSchema($directory . '/models.yml', $extraAllwedReferences); + + // build + $builder = new IPF_ORM_Import_Builder; + $builder->setTargetPath($directory . '/models'); + + $models = array(); + foreach ($definitions as $name => $definition) { + print " $name\n"; + $builder->buildRecord($definition); + $models[] = $name; + } + + return $models; } - + public static function createTablesFromModels($directory) { return IPF_ORM_Manager::connection()->export->exportSchema($directory); diff --git a/ipf/orm/import/schema.php b/ipf/orm/import/schema.php index a17887d..7262e75 100644 --- a/ipf/orm/import/schema.php +++ b/ipf/orm/import/schema.php @@ -4,74 +4,70 @@ class IPF_ORM_Import_Schema { protected $_relations = array(); - protected $_options = array('packagesPrefix' => 'Package', - 'packagesPath' => '', - 'packagesFolderName' => 'packages', - 'suffix' => '.php', - 'generateBaseClasses' => true, - 'generateTableClasses' => false, - 'generateAccessors' => false, - 'baseClassesPrefix' => 'Base', - 'baseClassesDirectory' => IPF_ORM::BASE_CLASSES_DIRECTORY, - 'baseClassName' => 'IPF_ORM_Record'); - - protected $_validation = array('root' => array('abstract', - 'connection', - 'className', - 'tableName', - 'connection', - 'relations', - 'columns', - 'indexes', - 'attributes', - 'templates', - 'actAs', - 'options', - 'package', - 'inheritance', - 'detect_relations', - 'generate_accessors', - 'listeners'), - - 'column' => array('name', - 'format', - 'fixed', - 'primary', - 'autoincrement', - 'type', - 'length', - 'size', - 'default', - 'scale', - 'values', - 'comment', - 'sequence', - 'protected', - 'zerofill', - 'owner', - 'exclude'), - - 'relation' => array('key', - 'class', - 'alias', - 'type', - 'refClass', - 'local', - 'foreign', - 'foreignClass', - 'foreignAlias', - 'foreignType', - 'foreignExclude', - 'autoComplete', - 'onDelete', - 'onUpdate', - 'equal', - 'owningSide'), - - 'inheritance'=> array('type', - 'extends', - 'keyField', - 'keyValue')); + protected $_validation = array( + 'root' => array( + 'abstract', + 'connection', + 'className', + 'tableName', + 'connection', + 'relations', + 'columns', + 'indexes', + 'attributes', + 'templates', + 'actAs', + 'options', + 'package', + 'inheritance', + 'detect_relations', + 'generate_accessors', + 'listeners', + ), + 'column' => array( + 'name', + 'format', + 'fixed', + 'primary', + 'autoincrement', + 'type', + 'length', + 'size', + 'default', + 'scale', + 'values', + 'comment', + 'sequence', + 'protected', + 'zerofill', + 'owner', + 'exclude', + ), + 'relation' => array( + 'key', + 'class', + 'alias', + 'type', + 'refClass', + 'local', + 'foreign', + 'foreignClass', + 'foreignAlias', + 'foreignType', + 'foreignExclude', + 'autoComplete', + 'onDelete', + 'onUpdate', + 'equal', + 'owningSide', + ), + 'inheritance' => array( + 'type', + 'extends', + 'keyField', + 'keyValue', + ), + ); protected $_validators = array(); @@ -83,77 +79,14 @@ class IPF_ORM_Import_Schema return $this->_validators; } - public function getOption($name) + public function importSchema($filename, $extraAllwedReferences) { - if (isset($this->_options[$name])) { - return $this->_options[$name]; - } - } - - public function getOptions() - { - return $this->_options; - } - - public function setOption($name, $value) - { - if (isset($this->_options[$name])) { - $this->_options[$name] = $value; - } - } - - public function setOptions($options) - { - if ( ! empty($options)) { - $this->_options = $options; - } - } - - public function buildSchema($schema, $format) - { - $array = array(); - - foreach ((array) $schema AS $s) { - if (is_file($s)) { - $array = array_merge($array, $this->parseSchema($s, $format)); - } else if (is_dir($s)) { - $it = new RecursiveIteratorIterator(new RecursiveDirectoryIterator($s), - RecursiveIteratorIterator::LEAVES_ONLY); - - foreach ($it as $file) { - $e = explode('.', $file->getFileName()); - if (end($e) === $format) { - $array = array_merge($array, $this->parseSchema($file->getPathName(), $format)); - } - } - } else { - $array = array_merge($array, $this->parseSchema($s, $format)); - } - } - - $array = $this->_buildRelationships($array); + $array = $this->parseSchema($filename, 'yml'); + $array = $this->_buildRelationships($array, $extraAllwedReferences); $array = $this->_processInheritance($array); - return $array; } - public function importSchema($schema, $format = 'yml', $directory = null, $models = array()) - { - $builder = new IPF_ORM_Import_Builder(); - $builder->setTargetPath($directory); - $builder->setOptions($this->getOptions()); - - $array = $this->buildSchema($schema, $format); - - foreach ($array as $name => $definition) { - if (!empty($models) && !in_array($definition['className'], $models)) { - continue; - } - print " $name\n"; - $builder->buildRecord($definition); - } - } - public function parseSchema($schema, $type) { $defaults = array('abstract' => false, @@ -369,7 +302,7 @@ class IPF_ORM_Import_Schema } } - protected function _buildRelationships($array) + protected function _buildRelationships($array, $extraAllwedReferences) { // Handle auto detecting relations by the names of columns // User.contact_id will automatically create User hasOne Contact local => contact_id, foreign => id @@ -399,13 +332,13 @@ class IPF_ORM_Import_Schema if (!isset($properties['relations'])) { continue; } - + $className = $properties['className']; $relations = $properties['relations']; - + foreach ($relations as $alias => $relation) { - $class = isset($relation['class']) ? $relation['class']:$alias; - if (!isset($array[$class])) { + $class = isset($relation['class']) ? $relation['class'] : $alias; + if (!isset($array[$class]) && !in_array($class, $extraAllwedReferences)) { print "Warning: Ignoring relation to unknown model '$class' in model '$className'. \n"; continue; } @@ -436,31 +369,35 @@ class IPF_ORM_Import_Schema } $relation['key'] = $this->_buildUniqueRelationKey($relation); - + $this->_validateSchemaElement('relation', array_keys($relation), $className . '->relation->' . $relation['alias']); $this->_relations[$className][$alias] = $relation; } } - + // Now we auto-complete opposite ends of relationships - $this->_autoCompleteOppositeRelations(); - + $this->_autoCompleteOppositeRelations($extraAllwedReferences); + // Make sure we do not have any duplicate relations $this->_fixDuplicateRelations(); //$array['relations']; // Set the full array of relationships for each class to the final array foreach ($this->_relations as $className => $relations) { - $array[$className]['relations'] = $relations; + if (!in_array($className, $extraAllwedReferences)) + $array[$className]['relations'] = $relations; } - + return $array; } - protected function _autoCompleteOppositeRelations() + protected function _autoCompleteOppositeRelations($extraAllwedReferences) { - foreach($this->_relations as $className => $relations) { + foreach ($this->_relations as $className => $relations) { + if (in_array($className, $extraAllwedReferences)) + continue; + foreach ($relations as $alias => $relation) { if ((isset($relation['equal']) && $relation['equal']) || (isset($relation['autoComplete']) && $relation['autoComplete'] === false)) { continue;