protected static function applyCreateRestrictions(&$id, &$parentId) { $id = Assert::expectIntegerPositive($id, '$id'); $parentId = Assert::expectIntegerNonNegative($parentId, '$parentId'); // parent id might be equal to 0 if (static::checkLinkExists($id, $parentId)) { throw new Tree\LinkExistsException(false, array('NODES' => array($id, $parentId))); } }
/** * Moves subtree. Low-level method. */ public static function moveLink($id, $parentId, $behaviour = array('CREATE_PARENT_NODE_ON_NOTFOUND' => true)) { $id = Assert::expectIntegerPositive($id, '$id'); $parentId = Assert::expectIntegerNonNegative($parentId, '$parentId'); // 0 allowed - means "detach into a separate branch" if (!is_array($behaviour)) { $behaviour = array(); } if (!isset($behaviour['CREATE_PARENT_NODE_ON_NOTFOUND'])) { $behaviour['CREATE_PARENT_NODE_ON_NOTFOUND'] = true; } $parentColName = static::getPARENTIDColumnName(); $idColName = static::getIDColumnName(); if (!static::checkNodeExists($id)) { throw new Tree\TargetNodeNotFoundException('Node not found: ' . $id); } $dbConnection = Main\HttpApplication::getConnection(); if ($parentId > 0) { if (!static::checkNodeExists($parentId)) { if ($behaviour['CREATE_PARENT_NODE_ON_NOTFOUND']) { if (!static::add(array($parentColName => $parentId, $idColName => $parentId))->isSuccess()) { throw new Tree\Exception('Can not create node: ' . $parentId); } } else { throw new Tree\ParentNodeNotFoundException('Node not found: ' . $parentId); } } if (static::checkLinkExists($id, $parentId)) { throw new Tree\LinkExistsException('Link already exists between ' . $id . ' and ' . $parentId . '(p)'); } $check = $dbConnection->query("select " . $idColName . " from " . static::getTableName() . " where " . $parentColName . " = '" . intval($id) . "' and " . $idColName . " = '" . intval($parentId) . "'")->fetch(); if (is_array($check)) { throw new Main\ArgumentException('Can not move tree inside itself'); } } // detach subtree $dbConnection->query("delete \n\t\t\tfrom " . static::getTableName() . " \n\t\t\twhere \n\t\t\t\t" . $idColName . " in (\n\t\t\t\t\t" . Helper::getTemporaryTableSubQuerySql(static::getSubTreeSql($id), $idColName) . "\n\t\t\t\t) \n\t\t\t\tand\n\t\t\t\t" . $parentColName . " in (\n\t\t\t\t\t" . Helper::getTemporaryTableSubQuerySql(static::getPathToNodeSql($id), $parentColName) . "\n\t\t\t\t)\n\t\t\t\tand \n\t\t\t\t" . $idColName . " != " . $parentColName . "\n\t\t\t\tand\n\t\t\t\t" . $parentColName . " != '" . intval($id) . "'\n\t\t"); if ($parentId > 0) { // reattach subtree to other path $res = static::getPathToNode($parentId, array('select' => array('ID' => $parentColName))); while ($item = $res->fetch()) { $dbConnection->query("insert into " . static::getTableName() . " \n\t\t\t\t\t\t\n\t\t\t\t\t\t(" . $parentColName . ", " . $idColName . ", DIRECT) \n\t\t\t\t\t\t\n\t\t\t\t\t\tselect \n\t\t\t\t\t\t\t'" . $item['ID'] . "',\n\t\t\t\t\t\t\tT." . $idColName . ",\n\n\t\t\t\t\t\t\t" . ($item['ID'] == $parentId ? "\n\t\t\t\t\t\t\t\tCASE \n\t\t\t\t\t\t\t\t\tWHEN \n\t\t\t\t\t\t\t\t\t\tT." . $idColName . " = '" . $id . "'\n\t\t\t\t\t\t\t\t\tTHEN\n\t\t\t\t\t\t\t\t\t\t'1'\n\t\t\t\t\t\t\t\t\tELSE\n\t\t\t\t\t\t\t\t\t\t'0'\n\t\t\t\t\t\t\t\tEND\n\t\t\t\t\t\t\t\t" : "'0'") . "\n\t\t\t\t\t\tfrom \n\t\t\t\t\t\t\t" . static::getTableName() . " T \n\t\t\t\t\t\twhere \n\t\t\t\t\t\t\t" . $parentColName . " = '" . intval($id) . "'"); } } return true; }