Get the associations collection for this table.
public associations ( ) : Cake\ORM\AssociationCollection | ||
return | Cake\ORM\AssociationCollection | The collection of association objects. |
/** * Get the array of junction aliases for all the BelongsToMany associations * * @param Table $table Table * @return array junction aliases of all the BelongsToMany associations */ public function belongsToManyJunctionAliases(Table $table) { $extractor = function ($val) { return $val->junction()->alias(); }; return array_map($extractor, $table->associations()->type('BelongsToMany')); }
/** * Extract the aliases for associations * * @param \Cake\ORM\Table $table object to find associations on * @param string $assoc association to extract * @return array */ public function aliasExtractor($table, $assoc) { $extractor = function ($val) { return $val->target()->alias(); }; return array_map($extractor, $table->associations()->type($assoc)); }
/** * @param \Cake\Event\Event $event * @param \Cake\ORM\Query $query * @param \ArrayObject $options * @param bool $primary * @return void */ public function beforeFind(Event $event, Query $query, ArrayObject $options, $primary) { if (!$primary && !$this->_config['recursive']) { return; } $field = $this->_config['field']; if (!$field) { return; } $query->find('hashed'); $idField = $this->_primaryKey; if ($primary && $field === $idField) { $query->traverseExpressions(function ($expression) { if (method_exists($expression, 'getField') && ($expression->getField() === $this->_primaryKey || $expression->getField() === $this->_table->alias() . '.' . $this->_primaryKey)) { $expression->setValue($this->decodeHashid($expression->getValue())); } return $expression; }); } if (!$this->_config['recursive']) { return; } foreach ($this->_table->associations() as $association) { if ($association->target()->hasBehavior('Hashid') && $association->finder() === 'all') { $association->finder('hashed'); } } }
/** * Get instance of FileStorage association. * * @return void */ protected function _getFileStorageAssociationInstance() { foreach ($this->_table->associations() as $association) { if ($association->className() == self::FILES_STORAGE_NAME) { $this->_fileStorageAssociation = $association; break; } } }
/** * Returns association object for all versions or single field version. * * @param string|null $field Field name for per-field association. * @param array $options Association options. * @return \Cake\ORM\Association */ public function versionAssociation($field = null, $options = []) { $name = $this->_associationName($field); if (!$this->_table->associations()->has($name)) { $model = $this->_config['referenceName']; if ($field) { $this->_table->hasOne($name, $options + ['className' => $this->_config['versionTable'], 'foreignKey' => $this->_config['foreignKey'], 'joinType' => 'LEFT', 'conditions' => [$name . '.model' => $model, $name . '.field' => $field], 'propertyName' => $field . '_version']); } else { $this->_table->hasMany($name, $options + ['className' => $this->_config['versionTable'], 'foreignKey' => $this->_config['foreignKey'], 'strategy' => 'subquery', 'conditions' => ["{$name}.model" => $model], 'propertyName' => '__version', 'dependent' => true]); } } return $this->_table->association($name); }
/** * @param \ArrayObject $data * @param \Cake\ORM\Table $table * @return \ArrayObject */ protected function _process($data, Table $table) { $associations = []; /* @var \Cake\ORM\Association $association */ foreach ($table->associations() as $association) { $associations[$association->property()] = $association->name(); } foreach ($data as $key => $value) { if (array_key_exists($key, $associations)) { $data[$key] = $this->_process($data[$key], $table->association($associations[$key])->target()); continue; } $nullable = Hash::get((array) $table->schema()->column($key), 'null'); if ($nullable !== true) { continue; } if ($value !== '') { continue; } $default = Hash::get((array) $table->schema()->column($key), 'default'); $data[$key] = $default; } return $data; }
/** * Get parent model association's foreign key. * * @param \Cake\ORM\Table $table Table instance * @param string $modelName Model name * @return string */ protected function _getForeignKey(Table $table, $modelName) { $result = null; foreach ($table->associations() as $association) { if ($modelName === $association->className()) { $result = $association->foreignKey(); } } return $result; }
/** * Extract the aliases for associations, filters hasMany associations already extracted as * belongsToMany * * @param \Cake\ORM\Table $table object to find associations on * @param string $assoc association to extract * @return array */ public function aliasExtractor($table, $assoc) { $extractor = function ($val) { return $val->target()->alias(); }; $aliases = array_map($extractor, $table->associations()->type($assoc)); if ($assoc === 'HasMany') { return $this->_filterHasManyAssociationsAliases($table, $aliases); } return $aliases; }
/** * Returns an entity property "schema". * * The schema is an associative array, using the property names * as keys, and information about the property as the value. * * The value part consists of at least two keys: * * - `kind`: The kind of property, either `column`, which indicates * that the property stems from a database column, or `association`, * which identifies a property that is generated for an associated * table. * - `type`: The type of the property value. For the `column` kind * this is the database type associated with the column, and for the * `association` type it's the FQN of the entity class for the * associated table. * * For `association` properties an additional key will be available * * - `association`: Holds an instance of the corresponding association * class. * * @param \Cake\ORM\Table $model The model to introspect. * @return array The property schema */ public function getEntityPropertySchema(Table $model) { $properties = []; $schema = $model->schema(); foreach ($schema->columns() as $column) { $properties[$column] = ['kind' => 'column', 'type' => $schema->columnType($column)]; } foreach ($model->associations() as $association) { $entityClass = '\\' . ltrim($association->target()->entityClass(), '\\'); if ($entityClass === '\\Cake\\ORM\\Entity') { $namespace = Configure::read('App.namespace'); list($plugin, ) = pluginSplit($association->target()->registryAlias()); if ($plugin !== null) { $namespace = $plugin; } $namespace = str_replace('/', '\\', trim($namespace, '\\')); $entityClass = $this->_entityName($association->target()->alias()); $entityClass = '\\' . $namespace . '\\Model\\Entity\\' . $entityClass; } $properties[$association->property()] = ['kind' => 'association', 'association' => $association, 'type' => $entityClass]; } return $properties; }
/** * Test addAssociations() * * @return void */ public function testAddAssociations() { $params = ['belongsTo' => ['users' => ['foreignKey' => 'fake_id', 'conditions' => ['a' => 'b']]], 'hasOne' => ['profiles'], 'hasMany' => ['authors'], 'belongsToMany' => ['tags' => ['joinTable' => 'things_tags']]]; $table = new Table(['table' => 'dates']); $table->addAssociations($params); $associations = $table->associations(); $belongsTo = $associations->get('users'); $this->assertInstanceOf('Cake\\ORM\\Association\\BelongsTo', $belongsTo); $this->assertEquals('users', $belongsTo->name()); $this->assertEquals('fake_id', $belongsTo->foreignKey()); $this->assertEquals(['a' => 'b'], $belongsTo->conditions()); $this->assertSame($table, $belongsTo->source()); $hasOne = $associations->get('profiles'); $this->assertInstanceOf('Cake\\ORM\\Association\\HasOne', $hasOne); $this->assertEquals('profiles', $hasOne->name()); $hasMany = $associations->get('authors'); $this->assertInstanceOf('Cake\\ORM\\Association\\hasMany', $hasMany); $this->assertEquals('authors', $hasMany->name()); $belongsToMany = $associations->get('tags'); $this->assertInstanceOf('Cake\\ORM\\Association\\BelongsToMany', $belongsToMany); $this->assertEquals('tags', $belongsToMany->name()); $this->assertSame('things_tags', $belongsToMany->junction()->table()); }
/** * Returns a map of property names where the association results should be injected * in the top level entities. * * @param Cake\ORM\Table $source The table having the top level associations * @param array $associations The name of the top level associations * @return array */ protected function _getPropertyMap($source, $associations) { $map = []; $container = $source->associations(); foreach ($associations as $assoc) { $map[$assoc] = $container->get($assoc)->property(); } return $map; }
/** * Returns associations for controllers models. * * @param Table $model The model to build associations for. * @return array associations */ protected function _associations(Table $model) { $keys = ['BelongsTo', 'HasOne', 'HasMany', 'BelongsToMany']; $associations = []; foreach ($keys as $type) { foreach ($model->associations()->type($type) as $assoc) { $target = $assoc->target(); $assocName = $assoc->name(); $alias = $target->alias(); $targetClass = get_class($target); list(, $className) = namespaceSplit($targetClass); $modelClass = get_class($model); if ($modelClass !== 'Cake\\ORM\\Table' && $targetClass === $modelClass) { continue; } $className = preg_replace('/(.*)Table$/', '\\1', $className); if ($className === '') { $className = $alias; } $associations[$type][$assocName] = ['property' => $assoc->property(), 'variable' => Inflector::variable($assocName), 'primaryKey' => (array) $target->primaryKey(), 'displayField' => $target->displayField(), 'foreignKey' => $assoc->foreignKey(), 'alias' => $alias, 'controller' => $className, 'fields' => $target->schema()->columns()]; } } return $associations; }
/** * Method that retrieves and returns Table's assignation fields. These are fields * that dictate assigment, usually foreign key associated with a Users tables. (example: assigned_to) * * @param \Cake\ORM\Table $table Table instance * @return array */ protected function _getTableAssignationFields(Table $table) { $fields = []; foreach ($table->associations() as $association) { // skip non-assignation models if (!in_array($association->className(), $this->_assignationModels)) { continue; } $fields[] = $association->foreignKey(); } return $fields; }
/** * getAssignedAssociations * * gets all Entities associated with the record * * @param \Cake\ORM\Table $table of the record * @param \Cake\Datasource\EntityInterface $entity extra options * @param array $fields Attendees fields * @return array $entities */ public function getAssignedAssociations(Table $table, EntityInterface $entity, array $fields) { $entities = []; foreach ($table->associations() as $association) { if (!in_array($association->foreignKey(), $fields)) { continue; } $query = $association->target()->find('all', ['conditions' => [$association->primaryKey() => $entity->{$association->foreignKey()}]]); $result = $query->first(); if ($result) { $entities[] = $result; } } return $entities; }
/** * Checks if an association exists. * * @throws \RuntimeException If no such association exists for the given table. * @param \Cake\ORM\Table $table Table object. * @param string $association Association name. * @return void */ protected function _checkAssociation(Table $table, $association) { if (!$table->associations()->has($association)) { throw new RuntimeException(sprintf('Table `%s` is not associated with `%s`', get_class($table), $association)); } }
/** * Returns associations for controllers models. * * @param Table $model * @return array associations */ protected function _associations(Table $model) { $keys = ['BelongsTo', 'HasOne', 'HasMany', 'BelongsToMany']; $associations = []; foreach ($keys as $type) { foreach ($model->associations()->type($type) as $assoc) { $target = $assoc->target(); $assocName = $assoc->name(); $alias = $target->alias(); $associations[$type][$assocName] = ['property' => $assoc->property(), 'variable' => Inflector::variable($assocName), 'primaryKey' => (array) $target->primaryKey(), 'displayField' => $target->displayField(), 'foreignKey' => $assoc->foreignKey(), 'controller' => Inflector::underscore($alias), 'fields' => $target->schema()->columns()]; } } return $associations; }