Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
100.00% covered (success)
100.00%
5 / 5
100.00% covered (success)
100.00%
3 / 3
CRAP
100.00% covered (success)
100.00%
1 / 1
TreenodeOrdered
100.00% covered (success)
100.00%
5 / 5
100.00% covered (success)
100.00%
3 / 3
3
100.00% covered (success)
100.00%
1 / 1
 hydrate
100.00% covered (success)
100.00%
3 / 3
100.00% covered (success)
100.00%
1 / 1
1
 getIndex
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 setIndex
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
1<?php
2
3/**
4 * @author: Doug Wilbourne (dougwilbourne@gmail.com)
5 */
6
7declare (strict_types=1);
8
9namespace pvc\struct\tree\node;
10
11use pvc\interfaces\struct\collection\IndexedElementInterface;
12use pvc\interfaces\struct\tree\dto\TreenodeDtoInterface;
13use pvc\struct\collection\CollectionOrdered;
14use pvc\struct\tree\err\AlreadySetNodeidException;
15use pvc\struct\tree\err\CircularGraphException;
16use pvc\struct\tree\err\InvalidNodeIdException;
17use pvc\struct\tree\err\InvalidParentNodeIdException;
18use pvc\struct\tree\err\InvalidValueException;
19use pvc\struct\tree\err\NodeNotEmptyHydrationException;
20use pvc\struct\tree\err\RootCannotBeMovedException;
21use pvc\struct\tree\err\SetTreeException;
22use pvc\struct\tree\tree\TreeOrdered;
23
24/**
25 *  The nodeid property is immutable - the only way to set the nodeid is at hydration.  The same applies to the tree property,
26 *  which is set at construction time.
27 *
28 *  This means that there are no setters for these properties.  Together, these two design points ensure that nodes
29 *  cannot be hydrated except in the context of belonging to a tree.  That in turn makes it a bit easier to enforce the
30 *  design point that all nodeids in a tree must be unique.
31 *
32 *  The same is almost true for the parent property, but the difference is that the nodes are allowed to move around
33 *  within the same tree, e.g. you can change a node's parent as long as the new parent is in the same tree. It is
34 *  important to know that not only does a node keep a reference to its parent, but it also keeps a list of its
35 *  children.  So the setParent method is responsible not only for setting the parent property, but it also takes
36 *  the parent and adds a node to its child list.
37 *
38 * @extends Treenode<TreenodeOrdered, CollectionOrdered, TreeOrdered>
39 */
40class TreenodeOrdered extends Treenode implements IndexedElementInterface
41{
42    /**
43     * @var non-negative-int
44     */
45    protected int $index;
46
47    /**
48     * @param  TreenodeDtoInterface  $dto
49     *
50     * @return void
51     * @throws AlreadySetNodeidException
52     * @throws CircularGraphException
53     * @throws InvalidNodeIdException
54     * @throws InvalidParentNodeIdException
55     * @throws NodeNotEmptyHydrationException
56     * @throws RootCannotBeMovedException
57     * @throws SetTreeException
58     * @throws InvalidValueException
59     */
60    public function hydrate(TreenodeDtoInterface $dto): void
61    {
62        assert(!is_null($dto->getIndex()));
63        $this->setIndex($dto->getIndex());
64        parent::hydrate($dto);
65    }
66
67    /**
68     * @function getIndex returns the ordinal position of this node in its list of siblings
69     * @return non-negative-int
70     */
71    public function getIndex(): int
72    {
73        return $this->index;
74    }
75
76    /**
77     * sets this node's index property.  This method should never be called
78     * by any other class than the collection which contains the node.  The collection bears the responsibility
79     * of rationalizing/ordering the indices within the collection.  Nodes are unaware of their siblings in
80     * a direct way - they need to ask the parent for the sibling collection
81     *
82     * @function setIndex
83     *
84     * @param  non-negative-int  $index
85     */
86    public function setIndex(int $index): void
87    {
88        $this->index = $index;
89    }
90}