public function copySubtree(APILocation $subtree, APILocation $targetParentLocation)
{
$loadedSubtree = $this->loadLocation($subtree->id);
$loadedTargetLocation = $this->loadLocation($targetParentLocation->id);
if (stripos($loadedTargetLocation->pathString, $loadedSubtree->pathString) !== false) {
throw new InvalidArgumentException('targetParentLocation', 'target parent location is a sub location of the given subtree');
}
// check create permission on target
if (!$this->repository->canUser('content', 'create', $loadedSubtree->getContentInfo(), $loadedTargetLocation)) {
throw new UnauthorizedException('content', 'create');
}
/** Check read access to whole source subtree
* @var bool|\eZ\Publish\API\Repository\Values\Content\Query\Criterion
*/
$contentReadCriterion = $this->permissionsCriterionHandler->getPermissionsCriterion();
if ($contentReadCriterion === false) {
throw new UnauthorizedException('content', 'read');
} elseif ($contentReadCriterion !== true) {
// Query if there are any content in subtree current user don't have access to
$query = new Query(array('limit' => 0, 'filter' => new CriterionLogicalAnd(array(new CriterionSubtree($loadedSubtree->pathString), new CriterionLogicalNot($contentReadCriterion)))));
$result = $this->repository->getSearchService()->findContent($query, array(), false);
if ($result->totalCount > 0) {
throw new UnauthorizedException('content', 'read');
}
}
$this->repository->beginTransaction();
try {
$newLocation = $this->persistenceHandler->locationHandler()->copySubtree($loadedSubtree->id, $loadedTargetLocation->id);
$content = $this->repository->getContentService()->loadContent($newLocation->contentId);
$urlAliasNames = $this->nameSchemaService->resolveUrlAliasSchema($content);
foreach ($urlAliasNames as $languageCode => $name) {
$this->persistenceHandler->urlAliasHandler()->publishUrlAliasForLocation($newLocation->id, $loadedTargetLocation->id, $name, $languageCode, $content->contentInfo->alwaysAvailable);
}
$this->persistenceHandler->urlAliasHandler()->locationCopied($loadedSubtree->id, $newLocation->id, $loadedTargetLocation->id);
$this->repository->commit();
} catch (Exception $e) {
$this->repository->rollback();
throw $e;
}
return $this->domainMapper->buildLocationDomainObject($newLocation);
}