protected function doRun()
    {
        $config = $this->config;
        if ($this->target['id'] != $this->head['id']) {
            $this->canMove();

            $movingNodes = $this->getMovingNodes();
            $movingNodesRange = $this->getMovingNodesRange();
            $shiftingNodes = $this->getShiftingNodes();
            $shiftingNodesRange = $this->getShiftingNodesRange();

            // update moving nodes
            $this->updateIndexes($movingNodes, self::INDEX_LFT, $this->head['lft'], $this->head['rgt'], $shiftingNodesRange * -1 * $this->getMoveDirection());
            $this->updateIndexes($movingNodes, self::INDEX_RGT, $this->head['lft'], $this->head['rgt'], $shiftingNodesRange * -1 * $this->getMoveDirection());
            $this->updateDepths($movingNodes, $this->getDepthModifier());
            $this->updateNodeParent($this->head['id'], $this->getHeadNodeNewParent());

            // update shifting nodes
            $limits = $this->getShiftingIndexesLimits();
            $this->updateIndexes($shiftingNodes, self::INDEX_LFT, $limits['min'], $limits['max'], $movingNodesRange * $this->getMoveDirection());
            $this->updateIndexes($shiftingNodes, self::INDEX_RGT, $limits['min'], $limits['max'], $movingNodesRange * $this->getMoveDirection());
        }
    }