| 1 |  |  | <?php | 
            
                                                                                                            
                            
            
                                    
            
            
                | 2 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 3 |  |  | declare(strict_types=1); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 4 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 5 |  |  | namespace Cycle\ORM\Relation; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 6 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 7 |  |  | use Cycle\ORM\Collection\Pivoted\PivotedCollectionInterface; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 8 |  |  | use Cycle\ORM\Collection\Pivoted\PivotedStorage; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 9 |  |  | use Cycle\ORM\FactoryInterface; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 10 |  |  | use Cycle\ORM\Heap\HeapInterface; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 11 |  |  | use Cycle\ORM\Heap\Node; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 12 |  |  | use Cycle\ORM\Heap\State; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 13 |  |  | use Cycle\ORM\Iterator; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 14 |  |  | use Cycle\ORM\MapperInterface; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 15 |  |  | use Cycle\ORM\ORMInterface; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 16 |  |  | use Cycle\ORM\Parser\RootNode; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 17 |  |  | use Cycle\ORM\Reference\EmptyReference; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 18 |  |  | use Cycle\ORM\Reference\Reference; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 19 |  |  | use Cycle\ORM\Reference\ReferenceInterface; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 20 |  |  | use Cycle\ORM\Relation; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 21 |  |  | use Cycle\ORM\Select\JoinableLoader; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 22 |  |  | use Cycle\ORM\Select\Loader\ManyToManyLoader; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 23 |  |  | use Cycle\ORM\Select\LoaderInterface; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 24 |  |  | use Cycle\ORM\Select\RootLoader; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 25 |  |  | use Cycle\ORM\Service\EntityFactoryInterface; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 26 |  |  | use Cycle\ORM\Service\SourceProviderInterface; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 27 |  |  | use Cycle\ORM\Transaction\Pool; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 28 |  |  | use Cycle\ORM\Transaction\Tuple; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 29 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 30 |  |  | /** | 
            
                                                                                                            
                            
            
                                    
            
            
                | 31 |  |  |  * @internal | 
            
                                                                                                            
                            
            
                                    
            
            
                | 32 |  |  |  */ | 
            
                                                                                                            
                            
            
                                    
            
            
                | 33 |  |  | class ManyToMany extends Relation\AbstractRelation | 
            
                                                                                                            
                            
            
                                    
            
            
                | 34 |  |  | { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 35 |  |  |     /** @var string[] */ | 
            
                                                                                                            
                            
            
                                    
            
            
                | 36 |  |  |     protected array $throughInnerKeys; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 37 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 38 |  |  |     /** @var string[] */ | 
            
                                                                                                            
                            
            
                                    
            
            
                | 39 |  |  |     protected array $throughOuterKeys; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 40 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 41 |  |  |     protected string $pivotRole; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 42 |  |  |     protected EntityFactoryInterface $entityFactory; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 43 |  |  |     protected SourceProviderInterface $sourceProvider; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 44 |  |  |     protected FactoryInterface $factory; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 45 |  |  |     private HeapInterface $heap; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 46 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 47 |  |  |     public function __construct( | 
            
                                                                                                            
                            
            
                                    
            
            
                | 48 | 942 |  |         ORMInterface $orm, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 49 |  |  |         private string $role, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 50 | 942 |  |         string $name, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 51 | 942 |  |         string $target, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 52 | 942 |  |         array $schema, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 53 | 942 |  |     ) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 54 | 942 |  |         parent::__construct($orm, $role, $name, $target, $schema); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 55 | 942 |  |         $this->heap = $orm->getHeap(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 56 |  |  |         $this->sourceProvider = $orm->getService(SourceProviderInterface::class); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 57 | 942 |  |         $this->entityFactory = $orm->getService(EntityFactoryInterface::class); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 58 | 942 |  |         $this->factory = $orm->getFactory(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 59 |  |  |         $this->pivotRole = $this->schema[Relation::THROUGH_ENTITY]; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 60 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 61 | 346 |  |         $this->throughInnerKeys = (array) $this->schema[Relation::THROUGH_INNER_KEY]; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 62 |  |  |         $this->throughOuterKeys = (array) $this->schema[Relation::THROUGH_OUTER_KEY]; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 63 | 346 |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 64 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 65 |  |  |     public function prepare(Pool $pool, Tuple $tuple, mixed $related, bool $load = true): void | 
            
                                                                                                            
                            
            
                                    
            
            
                | 66 | 346 |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 67 | 346 |  |         $node = $tuple->node; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 68 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 69 | 346 |  |         /** @var PivotedStorage|ReferenceInterface|null $original */ | 
            
                                                                                                            
                            
            
                                    
            
            
                | 70 | 72 |  |         $original = $node->getRelation($this->getName()); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 71 | 40 |  |         $tuple->state->setRelation($this->getName(), $related); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 72 | 40 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 73 |  |  |         if ($original instanceof ReferenceInterface) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 74 | 56 |  |             if (!$load && $related === $original && !$original->hasValue()) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 75 | 56 |  |                 $this->finalize($pool, $tuple, $related); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 76 | 56 |  |                 return; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 77 |  |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 78 | 338 |  |             $this->resolve($original, true); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 79 |  |  |             $original = $original->getValue(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 80 | 338 |  |             $node->setRelation($this->getName(), $original); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 81 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 82 |  |  |         $original = $this->extract($original); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 83 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 84 | 338 |  |         if ($related instanceof ReferenceInterface && $this->resolve($related, true) !== null) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 85 |  |  |             $related = $related->getValue(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 86 | 338 |  |             $tuple->state->setRelation($this->getName(), $related); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 87 |  |  |         } elseif (SpecialValue::isNotSet($related)) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 88 |  |  |             $tuple->state->setRelationStatus($this->getName(), RelationInterface::STATUS_RESOLVED); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 89 | 338 |  |             return; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 90 | 192 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 91 | 72 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 92 | 72 |  |         $related = $this->extractRelated($related, $original); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 93 | 72 |  |         // $tuple->state->setStorage($this->pivotEntity, $related); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 94 |  |  |         $tuple->state->setRelation($this->getName(), $related); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 95 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 96 |  |  |         // un-link old elements | 
            
                                                                                                            
                            
            
                                    
            
            
                | 97 | 338 |  |         foreach ($original as $item) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 98 |  |  |             if (!$related->has($item)) { | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 99 |  |  |                 $pivot = $original->get($item); | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 100 |  |  |                 $this->deleteChild($pool, $pivot, $item); | 
                            
                    |  |  |  | 
                                                                                        
                                                                                            
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 101 | 338 |  |                 $original->getContext()->offsetUnset($item); | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 102 |  |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 103 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 104 | 338 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 105 | 336 |  |         if ($this->inversion === null && \count($related) === 0) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 106 |  |  |             $tuple->state->setRelationStatus($this->getName(), RelationInterface::STATUS_RESOLVED); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 107 |  |  |             return; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 108 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 109 | 338 |  |         $tuple->state->setRelationStatus($this->getName(), RelationInterface::STATUS_PROCESS); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 110 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 111 | 338 |  |         // link/sync new and existed elements | 
            
                                                                                                            
                            
            
                                    
            
            
                | 112 |  |  |         foreach ($related->getElements() as $item) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 113 | 338 |  |             $this->newLink($pool, $tuple, $related, $item); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 114 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 115 | 338 |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 116 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 117 |  |  |     public function queue(Pool $pool, Tuple $tuple): void | 
            
                                                                                                            
                            
            
                                    
            
            
                | 118 |  |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 119 |  |  |         $related = $tuple->state->getRelation($this->getName()); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 120 | 338 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 121 | 338 |  |         if ($related instanceof ReferenceInterface && !$related->hasValue()) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 122 | 338 |  |             $tuple->state->setRelationStatus($this->getName(), RelationInterface::STATUS_RESOLVED); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 123 | 336 |  |             return; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 124 | 336 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 125 | 336 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 126 | 336 |  |         $this->finalize($pool, $tuple, $related); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 127 | 336 |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 128 | 336 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 129 |  |  |     public function init(EntityFactoryInterface $factory, Node $node, array $data): iterable | 
            
                                                                                                            
                            
            
                                    
            
            
                | 130 |  |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 131 | 338 |  |         $elements = []; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 132 | 162 |  |         $pivotData = new \SplObjectStorage(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 133 | 162 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 134 | 160 |  |         $iterator = Iterator::createWithServices( | 
            
                                                                                                            
                            
            
                                    
            
            
                | 135 | 96 |  |             $this->heap, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 136 |  |  |             $this->ormSchema, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 137 | 64 |  |             $this->entityFactory, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 138 | 64 |  |             $this->target, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 139 |  |  |             $data, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 140 | 162 |  |             true, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 141 |  |  |         ); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 142 |  |  |         foreach ($iterator as $pivot => $entity) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 143 |  |  |             if (!\is_array($pivot)) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 144 | 480 |  |                 // skip partially selected entities (DB level filter) | 
            
                                                                                                            
                            
            
                                    
            
            
                | 145 |  |  |                 continue; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 146 | 480 |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 147 | 480 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 148 |  |  |             $pivotData[$entity] = $factory->make($this->pivotRole, $pivot, Node::MANAGED); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 149 | 480 |  |             $elements[] = $entity; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 150 | 480 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 151 | 480 |  |         $collection = new PivotedStorage($elements, $pivotData); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 152 | 480 |  |         $node->setRelation($this->name, $collection); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 153 | 480 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 154 |  |  |         return $this->collect($collection); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 155 |  |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 156 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 157 | 480 |  |     public function cast(?array $data): array | 
            
                                                                                                            
                            
            
                                    
            
            
                | 158 | 480 |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 159 |  |  |         if (!$data) { | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 160 | 24 |  |             return []; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 161 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 162 |  |  |         /** | 
            
                                                                                                            
                            
            
                                    
            
            
                | 163 | 480 |  |          * @var array<non-empty-string, MapperInterface> $targetMappers Target Mappers cache | 
            
                                                                                                            
                            
            
                                    
            
            
                | 164 | 480 |  |          * @var array<non-empty-string, MapperInterface> $pivotMappers Pivot Mappers cache | 
            
                                                                                                            
                            
            
                                    
            
            
                | 165 |  |  |          */ | 
            
                                                                                                            
                            
            
                                    
            
            
                | 166 | 480 |  |         $pivotMappers = []; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 167 | 480 |  |         $targetMappers = []; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 168 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 169 | 480 |  |         foreach ($data as $key => $pivot) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 170 |  |  |             if (isset($pivot['@'])) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 171 |  |  |                 $d = $pivot['@']; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 172 | 632 |  |                 // break link | 
            
                                                                                                            
                            
            
                                    
            
            
                | 173 |  |  |                 unset($pivot['@']); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 174 | 632 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 175 | 40 |  |                 $targetRole = $d[LoaderInterface::ROLE_KEY] ?? $this->target; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 176 |  |  |                 $pivot['@'] = ($targetMappers[$targetRole] ??= $this->mapperProvider->getMapper($targetRole))->cast($d); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 177 | 632 |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 178 | 632 |  |             // break link | 
            
                                                                                                            
                            
            
                                    
            
            
                | 179 |  |  |             unset($data[$key]); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 180 | 632 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 181 | 632 |  |             $pivotRole = $pivot[LoaderInterface::ROLE_KEY] ?? $this->pivotRole; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 182 | 632 |  |             $data[$key] = ($pivotMappers[$pivotRole] ??= $this->mapperProvider->getMapper($pivotRole))->cast($pivot); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 183 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 184 | 632 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 185 | 632 |  |         return $data; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 186 |  |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 187 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 188 | 632 |  |     public function collect(mixed $data): iterable | 
            
                                                                                                            
                            
            
                                    
            
            
                | 189 | 632 |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 190 |  |  |         return $this->factory->collection( | 
            
                                                                                                            
                            
            
                                    
            
            
                | 191 |  |  |             $this->schema[Relation::COLLECTION_TYPE] ?? null, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 192 | 632 |  |         )->collect($data); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 193 |  |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 194 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 195 | 648 |  |     public function extract(?iterable $data): PivotedStorage | 
            
                                                                                                            
                            
            
                                    
            
            
                | 196 |  |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 197 | 648 |  |         return match (true) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 198 | 648 |  |             $data instanceof PivotedStorage => $data, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 199 | 648 |  |             $data instanceof PivotedCollectionInterface => new PivotedStorage( | 
            
                                                                                                            
                            
            
                                    
            
            
                | 200 |  |  |                 $data->toArray(), | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 201 |  |  |                 $data->getPivotContext(), | 
            
                                                                                                            
                            
            
                                    
            
            
                | 202 | 338 |  |             ), | 
            
                                                                                                            
                            
            
                                    
            
            
                | 203 |  |  |             $data instanceof \Doctrine\Common\Collections\Collection => new PivotedStorage($data->toArray()), | 
            
                                                                                                            
                            
            
                                    
            
            
                | 204 |  |  |             $data === null => new PivotedStorage(), | 
            
                                                                                                            
                            
            
                                    
            
            
                | 205 | 338 |  |             $data instanceof \Traversable => new PivotedStorage(\iterator_to_array($data)), | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 206 | 338 |  |             default => new PivotedStorage((array) $data), | 
            
                                                                                                            
                            
            
                                    
            
            
                | 207 | 240 |  |         }; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 208 | 240 |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 209 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 210 | 258 |  |     public function extractRelated(?iterable $data, PivotedStorage $original): PivotedStorage | 
            
                                                                                                            
                            
            
                                    
            
            
                | 211 | 258 |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 212 | 56 |  |         $related = $this->extract($data); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 213 | 338 |  |         if (\count($original) === 0) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 214 |  |  |             return $related; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 215 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 216 |  |  |         // Merge pivots | 
            
                                                                                                            
                            
            
                                    
            
            
                | 217 | 338 |  |         foreach ($related as $item) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 218 |  |  |             if ($related->hasContext($item)) { | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 219 | 338 |  |                 continue; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 220 | 338 |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 221 | 322 |  |             if ($original->hasContext($item)) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 222 |  |  |                 $related->set($item, $original->getContext()->offsetGet($item)); | 
                            
                    |  |  |  | 
                                                                                        
                                                                                            
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 223 | 32 |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 224 | 32 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 225 | 32 |  |         return $related; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 226 |  |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 227 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 228 | 32 |  |     public function initReference(Node $node): ReferenceInterface | 
            
                                                                                                            
                            
            
                                    
            
            
                | 229 |  |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 230 |  |  |         $scope = []; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 231 | 308 |  |         $nodeData = $node->getData(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 232 |  |  |         foreach ($this->innerKeys as $key) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 233 | 308 |  |             if (!isset($nodeData[$key])) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 234 | 308 |  |                 return new EmptyReference($node->getRole(), new PivotedStorage()); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 235 | 308 |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 236 | 308 |  |             $scope[$key] = $nodeData[$key]; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 237 | 56 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 238 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 239 | 268 |  |         return new Reference($this->target, $scope); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 240 |  |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 241 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 242 | 268 |  |     public function resolve(ReferenceInterface $reference, bool $load): ?iterable | 
            
                                                                                                            
                            
            
                                    
            
            
                | 243 |  |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 244 |  |  |         if ($reference->hasValue()) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 245 | 224 |  |             return $reference->getValue(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 246 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 247 | 224 |  |         if ($load === false) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 248 | 80 |  |             return null; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 249 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 250 | 192 |  |         $scope = $reference->getScope(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 251 | 24 |  |         if ($scope === []) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 252 |  |  |             $result = new PivotedStorage(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 253 | 168 |  |             $reference->setValue($result); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 254 | 168 |  |             return $result; | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 255 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 256 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 257 |  |  |         $source = $this->sourceProvider->getSource($this->target); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 258 |  |  |         // getting scoped query | 
            
                                                                                                            
                            
            
                                    
            
            
                | 259 |  |  |         $query = (new RootLoader( | 
            
                                                                                                            
                            
            
                                    
            
            
                | 260 |  |  |             $this->ormSchema, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 261 | 168 |  |             $this->sourceProvider, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 262 | 168 |  |             $this->factory, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 263 | 168 |  |             $this->target, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 264 | 168 |  |             loadRelations: false, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 265 | 168 |  |         ))->buildQuery(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 266 | 168 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 267 |  |  |         // responsible for all the scoping | 
            
                                                                                                            
                            
            
                                    
            
            
                | 268 |  |  |         $loader = new ManyToManyLoader( | 
            
                                                                                                            
                            
            
                                    
            
            
                | 269 | 168 |  |             $this->ormSchema, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 270 | 168 |  |             $this->sourceProvider, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 271 | 168 |  |             $this->factory, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 272 | 168 |  |             $source->getTable(), | 
            
                                                                                                            
                            
            
                                    
            
            
                | 273 | 168 |  |             $this->target, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 274 | 168 |  |             $this->schema, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 275 | 168 |  |         ); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 276 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 277 |  |  |         /** @var ManyToManyLoader $loader */ | 
            
                                                                                                            
                            
            
                                    
            
            
                | 278 |  |  |         $loader = $loader->withContext($loader, [ | 
            
                                                                                                            
                            
            
                                    
            
            
                | 279 | 168 |  |             'scope' => $source->getScope(), | 
            
                                                                                                            
                            
            
                                    
            
            
                | 280 | 168 |  |             'as' => $this->target, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 281 | 168 |  |             'method' => JoinableLoader::POSTLOAD, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 282 |  |  |         ]); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 283 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 284 |  |  |         $query = $loader->configureQuery($query, [$scope]); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 285 | 168 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 286 |  |  |         // we are going to add pivot node into virtual root node (only ID) to aggregate the results | 
            
                                                                                                            
                            
            
                                    
            
            
                | 287 |  |  |         $root = new RootNode( | 
            
                                                                                                            
                            
            
                                    
            
            
                | 288 | 168 |  |             (array) $this->schema[Relation::INNER_KEY], | 
            
                                                                                                            
                            
            
                                    
            
            
                | 289 | 168 |  |             (array) $this->schema[Relation::INNER_KEY], | 
            
                                                                                                            
                            
            
                                    
            
            
                | 290 | 168 |  |         ); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 291 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 292 |  |  |         $node = $loader->createNode(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 293 | 168 |  |         $root->linkNode('output', $node); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 294 | 168 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 295 |  |  |         // emulate presence of parent entity | 
            
                                                                                                            
                            
            
                                    
            
            
                | 296 |  |  |         $root->parseRow(0, $this->mapperProvider->getMapper($this->role)->uncast($scope)); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 297 | 168 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 298 |  |  |         $iterator = $query->getIterator(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 299 | 168 |  |         foreach ($iterator as $row) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 300 | 168 |  |             $node->parseRow(0, $row); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 301 | 168 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 302 |  |  |         $iterator->close(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 303 | 168 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 304 |  |  |         // load all eager relations, forbid loader to re-fetch data (make it think it was joined) | 
            
                                                                                                            
                            
            
                                    
            
            
                | 305 |  |  |         $loader->withContext($loader, ['method' => JoinableLoader::INLOAD])->loadData($node); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 306 | 168 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 307 |  |  |         $elements = []; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 308 | 168 |  |         $pivotData = new \SplObjectStorage(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 309 | 168 |  |         $iterator = Iterator::createWithServices( | 
            
                                                                                                            
                            
            
                                    
            
            
                | 310 | 168 |  |             $this->heap, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 311 | 168 |  |             $this->ormSchema, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 312 | 168 |  |             $this->entityFactory, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 313 | 168 |  |             $this->target, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 314 | 168 |  |             $root->getResult()[0]['output'], | 
            
                                                                                                            
                            
            
                                    
            
            
                | 315 | 168 |  |             true, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 316 |  |  |             typecast: true, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 317 |  |  |         ); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 318 |  |  |         foreach ($iterator as $pivot => $entity) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 319 | 168 |  |             $pivotData[$entity] = $this->entityFactory->make( | 
            
                                                                                                            
                            
            
                                    
            
            
                | 320 | 168 |  |                 $this->schema[Relation::THROUGH_ENTITY], | 
            
                                                                                                            
                            
            
                                    
            
            
                | 321 | 168 |  |                 $pivot, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 322 |  |  |                 Node::MANAGED, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 323 |  |  |                 typecast: true, | 
            
                                                                                                            
                            
            
                                    
            
            
                | 324 |  |  |             ); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 325 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 326 |  |  |             $elements[] = $entity; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 327 | 168 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 328 |  |  |         $result = new PivotedStorage($elements, $pivotData); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 329 | 168 |  |         $reference->setValue($result); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 330 | 168 |  |         return $result; | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 331 | 168 |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 332 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 333 |  |  |     protected function applyPivotChanges(State $parentState, State $state): void | 
            
                                                                                                            
                            
            
                                    
            
            
                | 334 | 336 |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 335 |  |  |         foreach ($this->innerKeys as $i => $innerKey) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 336 | 336 |  |             $state->register($this->throughInnerKeys[$i], $parentState->getValue($innerKey)); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 337 | 336 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 338 |  |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 339 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 340 |  |  |     protected function newLink(Pool $pool, Tuple $tuple, PivotedStorage $storage, object $related): void | 
            
                                                                                                            
                            
            
                                    
            
            
                | 341 | 72 |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 342 |  |  |         $rTuple = $pool->attachStore($related, $this->isCascade()); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 343 |  |  |         $this->assertValid($rTuple->node); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 344 | 72 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 345 | 72 |  |         $pivot = $storage->get($related); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 346 |  |  |         if (!\is_object($pivot)) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 347 | 72 |  |             // first time initialization | 
            
                                                                                                            
                            
            
                                    
            
            
                | 348 |  |  |             $pivot = $this->initPivot($tuple->entity, $storage, $rTuple, $pivot); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 349 |  |  |             $storage->set($related, $pivot); | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 350 | 336 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 351 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 352 | 336 |  |         $pTuple = $pool->attachStore($pivot, $this->isCascade()); | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 353 | 336 |  |         // $pRelationName = $tuple->node->getRole() . '.' . $this->getName() . ':' . $this->pivotEntity; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 354 |  |  |         // $pNode->setRelationStatus($pRelationName, RelationInterface::STATUS_RESOLVED); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 355 | 336 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 356 | 336 |  |         foreach ($this->throughInnerKeys as $i => $pInnerKey) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 357 |  |  |             $pTuple->state->register($pInnerKey, $tuple->state->getTransactionData()[$this->innerKeys[$i]] ?? null); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 358 | 312 |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 359 | 312 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 360 |  |  |         if ($this->inversion === null) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 361 |  |  |             // send the Pivot into child's State for the ShadowHasMany relation | 
            
                                                                                                            
                            
            
                                    
            
            
                | 362 | 336 |  |             // $relName = $tuple->node->getRole() . '.' . $this->name . ':' . $this->target; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 363 |  |  |             $relName = $this->getTargetRelationName(); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 364 |  |  |             $pivots = $rTuple->state->getRelations()[$relName] ?? []; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 365 |  |  |             $pivots[] = $pivot; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 366 | 336 |  |             $rTuple->state->setRelation($relName, $pivots); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 367 | 336 |  |         } else { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 368 |  |  |             $rTuple->state->addToStorage($this->inversion, $pTuple->state); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 369 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 370 |  |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 371 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 372 | 336 |  |     /** | 
            
                                                                                                            
                            
            
                                    
            
            
                | 373 |  |  |      * Since many to many relation can overlap from two directions we have to properly resolve the pivot entity upon | 
            
                                                                                                            
                            
            
                                    
            
            
                | 374 |  |  |      * it's generation. This is achieved using temporary mapping associated with each of the entity states. | 
            
                                                                                                            
                            
            
                                    
            
            
                | 375 | 176 |  |      */ | 
            
                                                                                                            
                            
            
                                    
            
            
                | 376 | 176 |  |     protected function initPivot(object $parent, PivotedStorage $storage, Tuple $rTuple, ?array $pivot): ?object | 
            
                                                                                                            
                            
            
                                    
            
            
                | 377 | 176 |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 378 | 176 |  |         if ($this->inversion !== null) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 379 |  |  |             $relatedStorage = $rTuple->state->getRelation($this->inversion); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 380 | 160 |  |             if ($relatedStorage instanceof PivotedStorage && $relatedStorage->hasContext($parent)) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 381 |  |  |                 return $relatedStorage->get($parent); | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                                                            
                            
            
                                    
            
            
                | 382 |  |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 383 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 384 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 385 |  |  |         $entity = $this->entityFactory->make($this->pivotRole, $pivot ?? []); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 386 |  |  |         $storage->set($rTuple->entity, $entity); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 387 |  |  |         return $entity; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 388 | 312 |  |     } | 
            
                                                                                                            
                                                                
            
                                    
            
            
                | 389 |  |  |  | 
            
                                                                        
                            
            
                                    
            
            
                | 390 | 312 |  |     private function deleteChild(Pool $pool, ?object $pivot, object $child, ?Node $relatedNode = null): void | 
                            
                    |  |  |  | 
                                                                                        
                                                                                     | 
            
                                                                        
                            
            
                                    
            
            
                | 391 | 160 |  |     { | 
            
                                                                        
                            
            
                                    
            
            
                | 392 | 160 |  |         // todo: add supporting for nullable pivot entities? | 
            
                                                                        
                            
            
                                    
            
            
                | 393 | 96 |  |         if ($pivot !== null) { | 
            
                                                                        
                            
            
                                    
            
            
                | 394 |  |  |             $pool->attachDelete($pivot, $this->isCascade()); | 
            
                                                                        
                            
            
                                    
            
            
                | 395 |  |  |         } | 
            
                                                                        
                            
            
                                    
            
            
                | 396 |  |  |         $pool->attachStore($child, true); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 397 | 312 |  |     } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 398 | 312 |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 399 | 312 |  |     private function finalize(Pool $pool, Tuple $tuple, mixed $related): void | 
            
                                                                                                            
                            
            
                                    
            
            
                | 400 |  |  |     { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 401 |  |  |         $tuple->state->setRelationStatus($this->getName(), RelationInterface::STATUS_RESOLVED); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 402 |  |  |  | 
            
                                                                                                            
                            
            
                                    
            
            
                | 403 |  |  |         $relationName = $tuple->node->getRole() . '.' . $this->name . ':' . $this->pivotRole; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 404 |  |  |         $pStates = []; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 405 |  |  |         foreach ($related as $item) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 406 |  |  |             $pivot = $related->get($item); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 407 |  |  |             if ($pivot !== null) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 408 |  |  |                 $pTuple = $pool->offsetGet($pivot); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 409 |  |  |                 $this->applyPivotChanges($tuple->state, $pTuple->state); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 410 |  |  |                 $pStates[] = $pTuple->state; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 411 |  |  |                 $pTuple->state->setRelationStatus($relationName, RelationInterface::STATUS_RESOLVED); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 412 |  |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 413 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 414 |  |  |         if ($this->inversion !== null) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 415 |  |  |             $storage = $tuple->state->getStorage($this->name); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 416 |  |  |             foreach ($storage as $pState) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 417 |  |  |                 if (\in_array($pState, $pStates, true)) { | 
            
                                                                                                            
                            
            
                                    
            
            
                | 418 |  |  |                     continue; | 
            
                                                                                                            
                            
            
                                    
            
            
                | 419 |  |  |                 } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 420 |  |  |                 $this->applyPivotChanges($tuple->state, $pState); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 421 |  |  |                 $pState->setRelationStatus($relationName, RelationInterface::STATUS_RESOLVED); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 422 |  |  |             } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 423 |  |  |             $tuple->state->clearStorage($this->name); | 
            
                                                                                                            
                            
            
                                    
            
            
                | 424 |  |  |         } | 
            
                                                                                                            
                            
            
                                    
            
            
                | 425 |  |  |     } | 
            
                                                                                                            
                                                                
            
                                    
            
            
                | 426 |  |  | } | 
            
                                                        
            
                                    
            
            
                | 427 |  |  |  |