<?php
/*
* This file is part of Sulu.
*
* (c) Sulu GmbH
*
* This source file is subject to the MIT license that is bundled
* with this source code in the file LICENSE.
*/
namespace Sulu\Component\DocumentManager;
use PHPCR\NodeInterface;
use PHPCR\RepositoryException;
use PHPCR\SessionInterface;
use PHPCR\Util\NodeHelper;
use PHPCR\Util\UUIDHelper;
use Sulu\Component\DocumentManager\Exception\DocumentNotFoundException;
/**
* The node manager is responsible for talking to the PHPCR implementation.
*/
class NodeManager
{
/**
* @var SessionInterface
*/
private $session;
public function __construct(SessionInterface $session)
{
$this->session = $session;
}
/**
* Find a document with the given path or UUID.
*
* @param string $identifier UUID or path
*
* @return NodeInterface
*
* @throws DocumentNotFoundException
*/
public function find($identifier)
{
try {
if (UUIDHelper::isUUID($identifier)) {
return $this->session->getNodeByIdentifier($identifier);
}
return $this->session->getNode($identifier);
} catch (RepositoryException $e) {
throw new DocumentNotFoundException(\sprintf(
'Could not find document with ID or path "%s"', $identifier
), null, $e);
}
}
/**
* Determine if a node exists at the specified path or if a UUID is given,
* then if a node with the UUID exists.
*
* @param string $identifier
*
* @return bool
*/
public function has($identifier)
{
$this->normalizeToPath($identifier);
try {
$this->find($identifier);
return true;
} catch (DocumentNotFoundException $e) {
return false;
}
}
/**
* Remove the document with the given path or UUID.
*
* @param string $identifier ID or path
*/
public function remove($identifier)
{
$identifier = $this->normalizeToPath($identifier);
$this->session->removeItem($identifier);
}
/**
* Move the document with the given path or ID to the path
* of the destination document (as a child).
*
* @param string $srcId
* @param string $destId
* @param string $name
*
* @deprecated Use NodeHelper::move instead
*/
public function move($srcId, $destId, $name)
{
$srcPath = $this->normalizeToPath($srcId);
$parentDestPath = $this->normalizeToPath($destId);
$destPath = $parentDestPath . '/' . $name;
$this->session->move($srcPath, $destPath);
}
/**
* Copy the document with the given path or ID to the path
* of the destination document (as a child).
*
* @param string $srcId
* @param string $destId
* @param string $name
*
* @return string
*
* @deprecated Use NodeHelper::copy instead
*/
public function copy($srcId, $destId, $name)
{
$workspace = $this->session->getWorkspace();
$srcPath = $this->normalizeToPath($srcId);
$parentDestPath = $this->normalizeToPath($destId);
$destPath = $parentDestPath . '/' . $name;
$workspace->copy($srcPath, $destPath);
return $destPath;
}
/**
* Save all pending changes currently recorded in this Session.
*/
public function save()
{
$this->session->save();
}
/**
* Clear the current session.
*/
public function clear()
{
$this->session->refresh(false);
}
/**
* Create a path.
*
* @param string $path
*
* @return NodeInterface
*/
public function createPath($path)
{
$current = $this->session->getRootNode();
$segments = \preg_split('#/#', $path, null, \PREG_SPLIT_NO_EMPTY);
foreach ($segments as $segment) {
if ($current->hasNode($segment)) {
$current = $current->getNode($segment);
} else {
$current = $current->addNode($segment);
$current->addMixin('mix:referenceable');
$current->setProperty('jcr:uuid', UUIDHelper::generateUUID());
}
}
return $current;
}
/**
* Purge the workspace.
*/
public function purgeWorkspace()
{
NodeHelper::purgeWorkspace($this->session);
}
/**
* Normalize the given path or ID to a path.
*
* @param string $identifier
*
* @return string
*/
private function normalizeToPath($identifier)
{
if (UUIDHelper::isUUID($identifier)) {
$identifier = $this->session->getNodeByIdentifier($identifier)->getPath();
}
return $identifier;
}
}