Class TreeBehavior
Makes the table to which this is attached to behave like a nested set and provides methods for managing and retrieving information out of the derived hierarchical structure.
Tables attaching this behavior are required to have a column referencing the parent row, and two other numeric columns (lft and rght) where the implicit order will be cached.
For more information on what is a nested set and a how it works refer to http://www.sitepoint.com/hierarchical-data-database-2/
Property Summary
- 
        $_config protectedarrayRuntime config 
- 
        $_configInitialized protectedboolWhether the config property has already been configured with defaults 
- 
        $_defaultConfig protectedarrayDefault config 
- 
        $_primaryKey protectedstringCached copy of the first column in a table's primary key. 
- 
        $_reflectionCache protected staticarrayReflection method cache for behaviors. 
- 
        $_table protectedCake\ORM\TableTable instance. 
Method Summary
- 
          __construct() publicConstructor 
- 
          _configDelete() protectedDelete a single config key 
- 
          _configRead() protectedRead a config variable 
- 
          _configWrite() protectedWrite a config variable 
- 
          _ensureFields() protectedEnsures that the provided entity contains non-empty values for the left and right fields 
- 
          _getMax() protectedReturns the maximum index value in the table. 
- 
          _getNode() protectedReturns a single node from the tree from its primary key 
- 
          _getPrimaryKey() protectedReturns a single string value representing the primary key of the attached table 
- 
          _moveDown() protectedHelper function used with the actual code for moveDown 
- 
          _moveUp() protectedHelper function used with the actual code for moveUp 
- 
          _recoverTree() protectedRecursive method used to recover a single level of the tree 
- 
          _reflectionCache() protectedGets the methods implemented by this behavior 
- 
          _removeFromTree() protectedHelper function containing the actual code for removeFromTree 
- 
          _resolveMethodAliases() protectedRemoves aliased methods that would otherwise be duplicated by userland configuration. 
- 
          _scope() protectedAlters the passed query so that it only returns scoped records as defined in the tree configuration. 
- 
          _setAsRoot() protectedUpdates the left and right column for the passed entity so it can be set as a new root in the tree. It also modifies the ordering in the rest of the tree so the structure remains valid 
- 
          _setChildrenLevel() protectedSet level for descendants. 
- 
          _setParent() protectedSets the correct left and right values for the passed entity so it can be updated to a new parent. It also makes the hole in the tree so the node move can be done without corrupting the structure. 
- 
          _sync() protectedAuxiliary function used to automatically alter the value of both the left and right columns by a certain amount that match the passed conditions 
- 
          _unmarkInternalTree() protectedHelper method used to invert the sign of the left and right columns that are less than 0. They were set to negative values before so their absolute value wouldn't change while performing other tree transformations. 
- 
          afterSave() publicAfter save listener. 
- 
          beforeDelete() publicAlso deletes the nodes in the subtree of the entity to be delete 
- 
          beforeSave() publicBefore save listener. Transparently manages setting the lft and rght fields if the parent field is included in the parameters to be saved. 
- 
          childCount() publicGet the number of children nodes. 
- 
          config() publicUsage
- 
          configShallow() publicMerge provided config with existing config. Unlike config()which does a recursive merge for nested keys, this method does a simple merge.
- 
          findChildren() publicGet the children nodes of the current model 
- 
          findPath() publicCustom finder method which can be used to return the list of nodes from the root to a specific node in the tree. This custom finder requires that the key 'for' is passed in the options containing the id of the node to get its path for. 
- 
          findTreeList() publicGets a representation of the elements in the tree as a flat list where the keys are the primary key for the table and the values are the display field for the table. Values are prefixed to visually indicate relative depth in the tree. 
- 
          formatTreeList() publicFormats query as a flat list where the keys are the primary key for the table and the values are the display field for the table. Values are prefixed to visually indicate relative depth in the tree. 
- 
          getLevel() publicReturns the depth level of a node in the tree. 
- 
          implementedEvents() publicGets the Model callbacks this behavior is interested in. 
- 
          implementedFinders() publicimplementedFinders 
- 
          implementedMethods() publicimplementedMethods 
- 
          initialize() publicConstructor hook method. 
- 
          moveDown() publicReorders the node without changing the parent. 
- 
          moveUp() publicReorders the node without changing its parent. 
- 
          recover() publicRecovers the lft and right column values out of the hierarchy defined by the parent column. 
- 
          removeFromTree() publicRemoves the current node from the tree, by positioning it as a new root and re-parents all children up one level. 
- 
          verifyConfig() publicverifyConfig 
Method Detail
__construct() ¶ public
__construct(Cake\ORM\Table $table, array $config = [])Constructor
Merges config with the default and store in the config property
Parameters
- 
                Cake\ORM\Table$table
- The table this behavior is attached to. 
- 
                array$config optional
- The config for this behavior. 
_configDelete() ¶ protected
_configDelete(string $key): voidDelete a single config key
Parameters
- 
                string$key
- Key to delete. 
Returns
voidThrows
Cake\Core\Exception\Exceptionif attempting to clobber existing config
_configRead() ¶ protected
_configRead(string|null $key): mixedRead a config variable
Parameters
- 
                string|null$key
- Key to read. 
Returns
mixed_configWrite() ¶ protected
_configWrite(string|array $key, mixed $value, bool|string $merge = false): voidWrite a config variable
Parameters
- 
                string|array$key
- Key to write to. 
- 
                mixed$value
- Value to write. 
- 
                bool|string$merge optional
- True to merge recursively, 'shallow' for simple merge, false to overwrite, defaults to false. 
Returns
voidThrows
Cake\Core\Exception\Exceptionif attempting to clobber existing config
_ensureFields() ¶ protected
_ensureFields(Cake\Datasource\EntityInterface $entity): voidEnsures that the provided entity contains non-empty values for the left and right fields
Parameters
- 
                Cake\Datasource\EntityInterface$entity
- The entity to ensure fields for 
Returns
void_getNode() ¶ protected
_getNode(mixed $id): Cake\ORM\EntityReturns a single node from the tree from its primary key
Parameters
- 
                mixed$id
- Record id. 
Returns
Cake\ORM\EntityThrows
Cake\Datasource\Exception\RecordNotFoundExceptionWhen node was not found
_getPrimaryKey() ¶ protected
_getPrimaryKey(): stringReturns a single string value representing the primary key of the attached table
Returns
string_moveDown() ¶ protected
_moveDown(Cake\Datasource\EntityInterface $node, int|bool $number): Cake\ORM\Entity|boolHelper function used with the actual code for moveDown
Parameters
- 
                Cake\Datasource\EntityInterface$node
- The node to move 
- 
                int|bool$number
- How many places to move the node, or true to move to last position 
Returns
Cake\ORM\Entity|bool$node The node after being moved or false on failure
Throws
Cake\Datasource\Exception\RecordNotFoundExceptionWhen node was not found
_moveUp() ¶ protected
_moveUp(Cake\Datasource\EntityInterface $node, int|bool $number): Cake\ORM\Entity|boolHelper function used with the actual code for moveUp
Parameters
- 
                Cake\Datasource\EntityInterface$node
- The node to move 
- 
                int|bool$number
- How many places to move the node, or true to move to first position 
Returns
Cake\ORM\Entity|bool$node The node after being moved or false on failure
Throws
Cake\Datasource\Exception\RecordNotFoundExceptionWhen node was not found
_recoverTree() ¶ protected
_recoverTree(int $counter = 0, mixed $parentId = null, int $level = -1): intRecursive method used to recover a single level of the tree
Parameters
- 
                int$counter optional
- The Last left column value that was assigned 
- 
                mixed$parentId optional
- the parent id of the level to be recovered 
- 
                int$level optional
- Node level 
Returns
intThe next value to use for the left column
_reflectionCache() ¶ protected
_reflectionCache(): arrayGets the methods implemented by this behavior
Uses the implementedEvents() method to exclude callback methods.
Methods starting with _ will be ignored, as will methods
declared on Cake\ORM\Behavior
Returns
array_removeFromTree() ¶ protected
_removeFromTree(Cake\Datasource\EntityInterface $node): Cake\ORM\Entity|falseHelper function containing the actual code for removeFromTree
Parameters
- 
                Cake\Datasource\EntityInterface$node
- The node to remove from the tree 
Returns
Cake\ORM\Entity|falsethe node after being removed from the tree or false on error
_resolveMethodAliases() ¶ protected
_resolveMethodAliases(string $key, array $defaults, array $config): arrayRemoves aliased methods that would otherwise be duplicated by userland configuration.
Parameters
- 
                string$key
- The key to filter. 
- 
                array$defaults
- The default method mappings. 
- 
                array$config
- The customized method mappings. 
Returns
arrayA de-duped list of config data.
_scope() ¶ protected
_scope(Cake\ORM\Query $query): Cake\ORM\QueryAlters the passed query so that it only returns scoped records as defined in the tree configuration.
Parameters
- 
                Cake\ORM\Query$query
- the Query to modify 
Returns
Cake\ORM\Query_setAsRoot() ¶ protected
_setAsRoot(Cake\Datasource\EntityInterface $entity): voidUpdates the left and right column for the passed entity so it can be set as a new root in the tree. It also modifies the ordering in the rest of the tree so the structure remains valid
Parameters
- 
                Cake\Datasource\EntityInterface$entity
- The entity to set as a new root 
Returns
void_setChildrenLevel() ¶ protected
_setChildrenLevel(Cake\Datasource\EntityInterface $entity): voidSet level for descendants.
Parameters
- 
                Cake\Datasource\EntityInterface$entity
- The entity whose descendants need to be updated. 
Returns
void_setParent() ¶ protected
_setParent(Cake\Datasource\EntityInterface $entity, mixed $parent): voidSets the correct left and right values for the passed entity so it can be updated to a new parent. It also makes the hole in the tree so the node move can be done without corrupting the structure.
Parameters
- 
                Cake\Datasource\EntityInterface$entity
- The entity to re-parent 
- 
                mixed$parent
- the id of the parent to set 
Returns
voidThrows
RuntimeExceptionif the parent to set to the entity is not valid
_sync() ¶ protected
_sync(int $shift, string $dir, string $conditions, bool $mark = false): voidAuxiliary function used to automatically alter the value of both the left and right columns by a certain amount that match the passed conditions
Parameters
- 
                int$shift
- the value to use for operating the left and right columns 
- 
                string$dir
- The operator to use for shifting the value (+/-) 
- 
                string$conditions
- a SQL snipped to be used for comparing left or right against it. 
- 
                bool$mark optional
- whether to mark the updated values so that they can not be modified by future calls to this function. 
Returns
void_unmarkInternalTree() ¶ protected
_unmarkInternalTree(): voidHelper method used to invert the sign of the left and right columns that are less than 0. They were set to negative values before so their absolute value wouldn't change while performing other tree transformations.
Returns
voidafterSave() ¶ public
afterSave(Cake\Event\Event $event, Cake\Datasource\EntityInterface $entity): voidAfter save listener.
Manages updating level of descendants of currently saved entity.
Parameters
- 
                Cake\Event\Event$event
- The afterSave event that was fired 
- 
                Cake\Datasource\EntityInterface$entity
- the entity that is going to be saved 
Returns
voidbeforeDelete() ¶ public
beforeDelete(Cake\Event\Event $event, Cake\Datasource\EntityInterface $entity): voidAlso deletes the nodes in the subtree of the entity to be delete
Parameters
- 
                Cake\Event\Event$event
- The beforeDelete event that was fired 
- 
                Cake\Datasource\EntityInterface$entity
- The entity that is going to be saved 
Returns
voidbeforeSave() ¶ public
beforeSave(Cake\Event\Event $event, Cake\Datasource\EntityInterface $entity): voidBefore save listener. Transparently manages setting the lft and rght fields if the parent field is included in the parameters to be saved.
Parameters
- 
                Cake\Event\Event$event
- The beforeSave event that was fired 
- 
                Cake\Datasource\EntityInterface$entity
- the entity that is going to be saved 
Returns
voidThrows
RuntimeExceptionif the parent to set for the node is invalid
childCount() ¶ public
childCount(Cake\Datasource\EntityInterface $node, bool $direct = false): intGet the number of children nodes.
Parameters
- 
                Cake\Datasource\EntityInterface$node
- The entity to count children for 
- 
                bool$direct optional
- whether to count all nodes in the subtree or just direct children 
Returns
intNumber of children nodes.
config() ¶ public
config(string|array|null $key = null, mixed|null $value = null, bool $merge = true): mixedUsage
Reading the whole config:
$this->config();Reading a specific value:
$this->config('key');Reading a nested value:
$this->config('some.nested.key');Setting a specific value:
$this->config('key', $value);Setting a nested value:
$this->config('some.nested.key', $value);Updating multiple config settings at the same time:
$this->config(['one' => 'value', 'another' => 'value']);Parameters
- 
                string|array|null$key optional
- The key to get/set, or a complete array of configs. 
- 
                mixed|null$value optional
- The value to set. 
- 
                bool$merge optional
- Whether to recursively merge or overwrite existing config, defaults to true. 
Returns
mixedConfig value being read, or the object itself on write operations.
Throws
Cake\Core\Exception\ExceptionWhen trying to set a key that is invalid.
configShallow() ¶ public
configShallow(string|array $key, mixed|null $value = null): $thisMerge provided config with existing config. Unlike config() which does
a recursive merge for nested keys, this method does a simple merge.
Setting a specific value:
$this->config('key', $value);Setting a nested value:
$this->config('some.nested.key', $value);Updating multiple config settings at the same time:
$this->config(['one' => 'value', 'another' => 'value']);Parameters
- 
                string|array$key
- The key to set, or a complete array of configs. 
- 
                mixed|null$value optional
- The value to set. 
Returns
$thisThe object itself.
findChildren() ¶ public
findChildren(Cake\ORM\Query $query, array $options): Cake\ORM\QueryGet the children nodes of the current model
Available options are:
- for: The id of the record to read.
- direct: Boolean, whether to return only the direct (true), or all (false) children, defaults to false (all children).
If the direct option is set to true, only the direct children are returned (based upon the parent_id field)
Parameters
- 
                Cake\ORM\Query$query
- Query. 
- 
                array$options
- Array of options as described above 
Returns
Cake\ORM\QueryThrows
InvalidArgumentExceptionWhen the 'for' key is not passed in $options
findPath() ¶ public
findPath(Cake\ORM\Query $query, array $options): Cake\ORM\QueryCustom finder method which can be used to return the list of nodes from the root to a specific node in the tree. This custom finder requires that the key 'for' is passed in the options containing the id of the node to get its path for.
Parameters
- 
                Cake\ORM\Query$query
- The constructed query to modify 
- 
                array$options
- the list of options for the query 
Returns
Cake\ORM\QueryThrows
InvalidArgumentExceptionIf the 'for' key is missing in options
findTreeList() ¶ public
findTreeList(Cake\ORM\Query $query, array $options): Cake\ORM\QueryGets a representation of the elements in the tree as a flat list where the keys are the primary key for the table and the values are the display field for the table. Values are prefixed to visually indicate relative depth in the tree.
Options
- keyPath: A dot separated path to fetch the field to use for the array key, or a closure to return the key out of the provided row.
- valuePath: A dot separated path to fetch the field to use for the array value, or a closure to return the value out of the provided row.
- spacer: A string to be used as prefix for denoting the depth in the tree for each item
Parameters
- 
                Cake\ORM\Query$query
- Query. 
- 
                array$options
- Array of options as described above. 
Returns
Cake\ORM\QueryformatTreeList() ¶ public
formatTreeList(Cake\ORM\Query $query, array $options = []): Cake\ORM\QueryFormats query as a flat list where the keys are the primary key for the table and the values are the display field for the table. Values are prefixed to visually indicate relative depth in the tree.
Options
- keyPath: A dot separated path to the field that will be the result array key, or a closure to return the key from the provided row.
- valuePath: A dot separated path to the field that is the array's value, or a closure to return the value from the provided row.
- spacer: A string to be used as prefix for denoting the depth in the tree for each item.
Parameters
- 
                Cake\ORM\Query$query
- The query object to format. 
- 
                array$options optional
- Array of options as described above. 
Returns
Cake\ORM\QueryAugmented query.
getLevel() ¶ public
getLevel(int|string|Cake\Datasource\EntityInterface $entity): int|boolReturns the depth level of a node in the tree.
Parameters
- 
                int|string|Cake\Datasource\EntityInterface$entity
- The entity or primary key get the level of. 
Returns
int|boolInteger of the level or false if the node does not exist.
implementedEvents() ¶ public
implementedEvents(): arrayGets the Model callbacks this behavior is interested in.
By defining one of the callback methods a behavior is assumed to be interested in the related event.
Override this method if you need to add non-conventional event listeners. Or if you want your behavior to listen to non-standard events.
Returns
arrayimplementedFinders() ¶ public
implementedFinders(): arrayimplementedFinders
Provides an alias->methodname map of which finders a behavior implements. Example:
 [
   'this' => 'findThis',
   'alias' => 'findMethodName'
 ]With the above example, a call to $Table->find('this') will call $Behavior->findThis()
and a call to $Table->find('alias') will call $Behavior->findMethodName()
It is recommended, though not required, to define implementedFinders in the config property of child classes such that it is not necessary to use reflections to derive the available method list. See core behaviors for examples
Returns
arrayimplementedMethods() ¶ public
implementedMethods(): arrayimplementedMethods
Provides an alias->methodname map of which methods a behavior implements. Example:
 [
   'method' => 'method',
   'aliasedmethod' => 'somethingElse'
 ]With the above example, a call to $Table->method() will call $Behavior->method()
and a call to $Table->aliasedmethod() will call $Behavior->somethingElse()
It is recommended, though not required, to define implementedFinders in the config property of child classes such that it is not necessary to use reflections to derive the available method list. See core behaviors for examples
Returns
arrayinitialize() ¶ public
initialize(array $config): voidConstructor hook method.
Implement this method to avoid having to overwrite the constructor and call parent.
Parameters
- 
                array$config
Returns
voidmoveDown() ¶ public
moveDown(Cake\Datasource\EntityInterface $node, int|bool $number = 1): Cake\ORM\Entity|boolReorders the node without changing the parent.
If the node is the last child, or is a top level node with no subsequent node this method will return false
Parameters
- 
                Cake\Datasource\EntityInterface$node
- The node to move 
- 
                int|bool$number optional
- How many places to move the node or true to move to last position 
Returns
Cake\ORM\Entity|boolthe entity after being moved or false on failure
Throws
Cake\Datasource\Exception\RecordNotFoundExceptionWhen node was not found
moveUp() ¶ public
moveUp(Cake\Datasource\EntityInterface $node, int|bool $number = 1): Cake\ORM\Entity|boolReorders the node without changing its parent.
If the node is the first child, or is a top level node with no previous node this method will return false
Parameters
- 
                Cake\Datasource\EntityInterface$node
- The node to move 
- 
                int|bool$number optional
- How many places to move the node, or true to move to first position 
Returns
Cake\ORM\Entity|bool$node The node after being moved or false on failure
Throws
Cake\Datasource\Exception\RecordNotFoundExceptionWhen node was not found
recover() ¶ public
recover(): voidRecovers the lft and right column values out of the hierarchy defined by the parent column.
Returns
voidremoveFromTree() ¶ public
removeFromTree(Cake\Datasource\EntityInterface $node): Cake\ORM\Entity|falseRemoves the current node from the tree, by positioning it as a new root and re-parents all children up one level.
Note that the node will not be deleted just moved away from its current position without moving its children with it.
Parameters
- 
                Cake\Datasource\EntityInterface$node
- The node to remove from the tree 
Returns
Cake\ORM\Entity|falsethe node after being removed from the tree or false on error
verifyConfig() ¶ public
verifyConfig(): voidverifyConfig
Checks that implemented keys contain values pointing at callable.
Returns
voidThrows
Cake\Core\Exception\Exceptionif config are invalid
Property Detail
$_configInitialized ¶ protected
Whether the config property has already been configured with defaults
Type
bool$_defaultConfig ¶ protected
Default config
These are merged with user-provided configuration when the behavior is used.
Type
array$_reflectionCache ¶ protected static
Reflection method cache for behaviors.
Stores the reflected method + finder methods per class. This prevents reflecting the same class multiple times in a single process.
Type
array