diff --git a/cli-config.php.dist b/cli-config.php.dist index 9b77be5..f605ee1 100644 --- a/cli-config.php.dist +++ b/cli-config.php.dist @@ -1,6 +1,11 @@ getRepository(array("jackalope.jackrabbit_uri" => $jackrabbit_url)); -$credentials = new \PHPCR\SimpleCredentials($user, $pass); -$session = $repository->login($credentials, $workspace); +if (isset($argv[1]) + && $argv[1] != 'list' + && $argv[1] != 'help' +) { + /* bootstrapping the repository implementation. for jackalope with jackrabbit, do this: */ + $factory = new \Jackalope\RepositoryFactoryJackrabbit; + $repository = $factory->getRepository(array("jackalope.jackrabbit_uri" => $jackrabbit_url)); + $credentials = new \PHPCR\SimpleCredentials($user, $pass); + $session = $repository->login($credentials, $workspace); -$helperSet = new \Symfony\Component\Console\Helper\HelperSet(array( - 'session' => new \PHPCR\Util\Console\Helper\PhpcrHelper($session) -)); + $helperSet = new \Symfony\Component\Console\Helper\HelperSet(array( + 'dialog' => new \Symfony\Component\Console\Helper\DialogHelper(), + 'phpcr' => new \PHPCR\Util\Console\Helper\PhpcrHelper($session), + 'phpcr_console_dumper' => new \PHPCR\Util\Console\Helper\PhpcrConsoleDumperHelper(), + )); +} diff --git a/composer.json b/composer.json index 9db8184..e918125 100644 --- a/composer.json +++ b/composer.json @@ -38,7 +38,7 @@ }, "extra": { "branch-alias": { - "dev-master": "1.0-dev" + "dev-master": "1.1-dev" } } } diff --git a/src/PHPCR/Util/CND/Parser/CndParser.php b/src/PHPCR/Util/CND/Parser/CndParser.php index 21e42fe..6173cc9 100644 --- a/src/PHPCR/Util/CND/Parser/CndParser.php +++ b/src/PHPCR/Util/CND/Parser/CndParser.php @@ -31,7 +31,7 @@ * @license http://opensource.org/licenses/MIT MIT License * * @author Daniel Barsotti - * @author David Buchmann + * @author David Buchmann */ class CndParser extends AbstractParser { diff --git a/src/PHPCR/Util/CND/Writer/CndWriter.php b/src/PHPCR/Util/CND/Writer/CndWriter.php index 6761174..ef8ce79 100644 --- a/src/PHPCR/Util/CND/Writer/CndWriter.php +++ b/src/PHPCR/Util/CND/Writer/CndWriter.php @@ -23,7 +23,7 @@ * @license http://www.apache.org/licenses Apache License Version 2.0, January 2004 * @license http://opensource.org/licenses/MIT MIT License * - * @author David Buchmann + * @author David Buchmann */ class CndWriter { diff --git a/src/PHPCR/Util/Console/Command/BaseCommand.php b/src/PHPCR/Util/Console/Command/BaseCommand.php index 81ec9ed..d579c95 100644 --- a/src/PHPCR/Util/Console/Command/BaseCommand.php +++ b/src/PHPCR/Util/Console/Command/BaseCommand.php @@ -2,10 +2,13 @@ namespace PHPCR\Util\Console\Command; -use PHPCR\SessionInterface; use Symfony\Component\Console\Command\Command; +use Symfony\Component\Console\Input\InputInterface; use Symfony\Component\Console\Input\InputOption; -use PHPCR\Util\Console\Helper\PhpcrCliHelper; +use Symfony\Component\Console\Output\OutputInterface; + +use PHPCR\SessionInterface; +use PHPCR\Util\Console\Helper\PhpcrHelper; use PHPCR\Util\Console\Helper\PhpcrConsoleDumperHelper; /** @@ -24,19 +27,15 @@ abstract class BaseCommand extends Command */ protected function getPhpcrSession() { - return $this->getHelper('phpcr')->getSession(); + return $this->getPhpcrHelper()->getSession(); } /** - * @return PhpcrCliHelper + * @return PhpcrHelper */ - protected function getPhpcrCliHelper() + protected function getPhpcrHelper() { - if (!$this->phpcrCliHelper) { - $this->phpcrCliHelper = new PhpcrCliHelper($this->getPhpcrSession()); - } - - return $this->phpcrCliHelper; + return $this->getHelperSet()->get('phpcr'); } /** @@ -44,47 +43,6 @@ protected function getPhpcrCliHelper() */ protected function getPhpcrConsoleDumperHelper() { - if (!$this->phpcrConsoleDumperHelper) { - $this->phpcrConsoleDumperHelper = new PhpcrConsoleDumperHelper(); - } - - return $this->phpcrConsoleDumperHelper; - } - - public function setPhpcrConsoleDumperHelper($consoleDumperHelper) - { - $this->phpcrConsoleDumperHelper = $consoleDumperHelper; - } - - /** - * Hack to enable overriding for unit tests. - */ - public function setPhpcrCliHelper(PhpcrCliHelper $helper) - { - $this->phpcrCliHelper = $helper; - } - - public function configureNodeManipulationInput() - { - $this->addOption('set-prop', 'p', - InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, - 'Set node property on nodes use foo=bar' - ); - $this->addOption('remove-prop', 'r', - InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, - 'Remove property from nodes' - ); - $this->addOption('add-mixin', null, - InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, - 'Add a mixin to the nodes' - ); - $this->addOption('remove-mixin', null, - InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, - 'Remove mixin from the nodes' - ); - $this->addOption('apply-closure', null, - InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, - 'Apply a closure to each node, closures are passed PHPCR\Session and PHPCR\NodeInterface' - ); + return $this->getHelperSet()->get('phpcr_console_dumper'); } } diff --git a/src/PHPCR/Util/Console/Command/BaseNodeManipulationCommand.php b/src/PHPCR/Util/Console/Command/BaseNodeManipulationCommand.php new file mode 100644 index 0000000..6531f12 --- /dev/null +++ b/src/PHPCR/Util/Console/Command/BaseNodeManipulationCommand.php @@ -0,0 +1,41 @@ +addOption('set-prop', 'p', + InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, + 'Set node property on nodes use foo=bar' + ); + $this->addOption('remove-prop', 'r', + InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, + 'Remove property from nodes' + ); + $this->addOption('add-mixin', null, + InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, + 'Add a mixin to the nodes' + ); + $this->addOption('remove-mixin', null, + InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, + 'Remove mixin from the nodes' + ); + $this->addOption('apply-closure', null, + InputOption::VALUE_REQUIRED | InputOption::VALUE_IS_ARRAY, + 'Apply a closure to each node, closures are passed PHPCR\Session and PHPCR\NodeInterface' + ); + } +} diff --git a/src/PHPCR/Util/Console/Command/NodeMoveCommand.php b/src/PHPCR/Util/Console/Command/NodeMoveCommand.php index 2f6f524..36fbf59 100644 --- a/src/PHPCR/Util/Console/Command/NodeMoveCommand.php +++ b/src/PHPCR/Util/Console/Command/NodeMoveCommand.php @@ -15,7 +15,7 @@ * * @author Daniel Leech */ -class NodeMoveCommand extends Command +class NodeMoveCommand extends BaseCommand { /** * {@inheritDoc} @@ -45,7 +45,7 @@ protected function configure() */ protected function execute(InputInterface $input, OutputInterface $output) { - $session = $this->getHelper('phpcr')->getSession(); + $session = $this->getPhpcrSession(); $sourcePath = $input->getArgument('source'); $destPath = $input->getArgument('destination'); @@ -57,6 +57,8 @@ protected function execute(InputInterface $input, OutputInterface $output) $session->move($sourcePath, $destPath); $session->save(); + + return 0; } } diff --git a/src/PHPCR/Util/Console/Command/NodeRemoveCommand.php b/src/PHPCR/Util/Console/Command/NodeRemoveCommand.php index d98cc1f..a32b96d 100644 --- a/src/PHPCR/Util/Console/Command/NodeRemoveCommand.php +++ b/src/PHPCR/Util/Console/Command/NodeRemoveCommand.php @@ -21,7 +21,7 @@ * @author Daniel Barsotti * @author Daniel Leech */ -class NodeRemoveCommand extends Command +class NodeRemoveCommand extends BaseCommand { /** * {@inheritDoc} @@ -57,8 +57,7 @@ protected function configure() */ protected function execute(InputInterface $input, OutputInterface $output) { - /** @var $session SessionInterface*/ - $session = $this->getHelper('phpcr')->getSession(); + $session = $this->getPhpcrSession(); $path = $input->getArgument('path'); $force = $input->getOption('force'); @@ -74,7 +73,8 @@ protected function execute(InputInterface $input, OutputInterface $output) } if (!$force) { - $dialog = new DialogHelper(); + /** @var $dialog DialogHelper */ + $dialog = $this->getHelperSet()->get('dialog'); $workspaceName = $session->getWorkspace()->getName(); if ($onlyChildren) { diff --git a/src/PHPCR/Util/Console/Command/NodeTouchCommand.php b/src/PHPCR/Util/Console/Command/NodeTouchCommand.php index 804f402..6901b7a 100644 --- a/src/PHPCR/Util/Console/Command/NodeTouchCommand.php +++ b/src/PHPCR/Util/Console/Command/NodeTouchCommand.php @@ -19,7 +19,7 @@ * * @author Daniel Leech */ -class NodeTouchCommand extends BaseCommand +class NodeTouchCommand extends BaseNodeManipulationCommand { /** * {@inheritDoc} @@ -71,7 +71,7 @@ protected function configure() */ protected function execute(InputInterface $input, OutputInterface $output) { - $helper = $this->getPhpcrCliHelper(); + $helper = $this->getPhpcrHelper(); $session = $this->getPhpcrSession(); $path = $input->getArgument('path'); @@ -98,13 +98,14 @@ protected function execute(InputInterface $input, OutputInterface $output) )); if ($nodeType != $type) { - throw new \Exception(sprintf( - 'You have specified node type "%s" but the existing node is of type "%s"', + $output->writeln(sprintf( + 'You have specified node type "%s" but the existing node is of type "%s"', $type, $nodeType )); + + return 1; } } else { - $nodeName = PathHelper::getNodeName($path); $parentPath = PathHelper::getParentPath($path); @@ -116,7 +117,7 @@ protected function execute(InputInterface $input, OutputInterface $output) $parentPath )); - return; + return 2; } $output->writeln(sprintf( @@ -135,5 +136,7 @@ protected function execute(InputInterface $input, OutputInterface $output) )); $session->save(); + + return 0; } } diff --git a/src/PHPCR/Util/Console/Command/NodesUpdateCommand.php b/src/PHPCR/Util/Console/Command/NodesUpdateCommand.php index e1ac50b..26d5076 100644 --- a/src/PHPCR/Util/Console/Command/NodesUpdateCommand.php +++ b/src/PHPCR/Util/Console/Command/NodesUpdateCommand.php @@ -6,7 +6,6 @@ use Symfony\Component\Console\Input\InputInterface; use Symfony\Component\Console\Output\OutputInterface; use Symfony\Component\Console\Helper\DialogHelper; -use PHPCR\Util\Console\Command\BaseCommand; /** * Command which can update the properties of nodes found @@ -17,7 +16,7 @@ * * @author Daniel Leech */ -class NodesUpdateCommand extends BaseCommand +class NodesUpdateCommand extends BaseNodeManipulationCommand { /** * {@inheritDoc} @@ -82,8 +81,6 @@ protected function configure() */ protected function execute(InputInterface $input, OutputInterface $output) { - $this->dialog = new DialogHelper(); - $query = $input->getOption('query'); $queryLanguage = strtoupper($input->getOption('query-language')); $persistCounter = intval($input->getOption('persist-counter')); @@ -93,7 +90,7 @@ protected function execute(InputInterface $input, OutputInterface $output) $removeMixins = $input->getOption('remove-mixin'); $applyClosures = $input->getOption('apply-closure'); $noInteraction = $input->getOption('no-interaction'); - $helper = $this->getPhpcrCliHelper(); + $helper = $this->getPhpcrHelper(); $session = $this->getPhpcrSession(); if (!$query) { @@ -154,7 +151,9 @@ protected function execute(InputInterface $input, OutputInterface $output) protected function getAction($output, $result) { - $response = strtoupper($this->dialog->ask($output, sprintf( + /** @var $dialog DialogHelper */ + $dialog = $this->getHelperSet()->get('dialog'); + $response = strtoupper($dialog->ask($output, sprintf( 'About to update %d nodes. Enter "Y" to continue, "N" to cancel or "L" to list.', count($result->getRows()) ), false)); diff --git a/src/PHPCR/Util/Console/Command/WorkspaceCreateCommand.php b/src/PHPCR/Util/Console/Command/WorkspaceCreateCommand.php index 62ea531..465ef9a 100644 --- a/src/PHPCR/Util/Console/Command/WorkspaceCreateCommand.php +++ b/src/PHPCR/Util/Console/Command/WorkspaceCreateCommand.php @@ -16,9 +16,9 @@ * @license http://opensource.org/licenses/MIT MIT License * * @author Lukas Kahwe Smith - * @author David Buchmann + * @author David Buchmann */ -class WorkspaceCreateCommand extends Command +class WorkspaceCreateCommand extends BaseCommand { /** * {@inheritDoc} @@ -43,8 +43,7 @@ protected function configure() */ protected function execute(InputInterface $input, OutputInterface $output) { - /** @var $session SessionInterface */ - $session = $this->getHelper('phpcr')->getSession(); + $session = $this->getPhpcrSession(); $workspaceName = $input->getArgument('name'); @@ -61,9 +60,17 @@ protected function execute(InputInterface $input, OutputInterface $output) return 1; } + if (array_search($workspaceName, $workspace->getAccessibleWorkspaceNames())) { + $output->writeln( + sprintf('This repository already has a workspace called "%s"', $workspaceName) + ); + + return 2; + } + $workspace->createWorkspace($workspaceName); - $output->writeln("Created workspace '$workspaceName'."); + $output->writeln(sprintf('Created workspace "%s".', $workspaceName)); return 0; } diff --git a/src/PHPCR/Util/Console/Command/WorkspaceDeleteCommand.php b/src/PHPCR/Util/Console/Command/WorkspaceDeleteCommand.php index 3136c51..42ebc01 100644 --- a/src/PHPCR/Util/Console/Command/WorkspaceDeleteCommand.php +++ b/src/PHPCR/Util/Console/Command/WorkspaceDeleteCommand.php @@ -19,7 +19,7 @@ * * @author David Buchmann */ -class WorkspaceDeleteCommand extends Command +class WorkspaceDeleteCommand extends BaseCommand { /** * {@inheritDoc} @@ -46,8 +46,7 @@ protected function configure() */ protected function execute(InputInterface $input, OutputInterface $output) { - /** @var $session SessionInterface */ - $session = $this->getHelper('phpcr')->getSession(); + $session = $this->getPhpcrSession(); $workspaceName = $input->getArgument('name'); @@ -72,7 +71,8 @@ protected function execute(InputInterface $input, OutputInterface $output) $force = $input->getOption('force'); if (!$force) { - $dialog = new DialogHelper(); + /** @var $dialog DialogHelper */ + $dialog = $this->getHelperSet()->get('dialog'); $force = $dialog->askConfirmation($output, sprintf( 'Are you sure you want to delete workspace "%s" Y/N ?', $workspaceName diff --git a/src/PHPCR/Util/Console/Command/WorkspaceExportCommand.php b/src/PHPCR/Util/Console/Command/WorkspaceExportCommand.php index f5d9816..654126a 100644 --- a/src/PHPCR/Util/Console/Command/WorkspaceExportCommand.php +++ b/src/PHPCR/Util/Console/Command/WorkspaceExportCommand.php @@ -16,9 +16,9 @@ * @license http://www.apache.org/licenses Apache License Version 2.0, January 2004 * @license http://opensource.org/licenses/MIT MIT License * - * @author David Buchmann + * @author David Buchmann */ -class WorkspaceExportCommand extends Command +class WorkspaceExportCommand extends BaseCommand { /** * {@inheritDoc} @@ -50,7 +50,7 @@ protected function configure() */ protected function execute(InputInterface $input, OutputInterface $output) { - $session = $this->getHelper('phpcr')->getSession(); + $session = $this->getPhpcrSession(); $repo = $session->getRepository(); if (!$repo->getDescriptor(RepositoryInterface::OPTION_XML_EXPORT_SUPPORTED)) { @@ -60,9 +60,22 @@ protected function execute(InputInterface $input, OutputInterface $output) } $path = $input->getOption('path'); - $stream = fopen($input->getArgument('filename'), 'w'); + $filename = $input->getArgument('filename'); + $stream = fopen($filename, 'w'); + if (!$stream) { + $output->writeln(sprintf('Failed to create file "%s" for writing.', $filename)); + + return 2; + } $session->exportSystemView($path, $stream, $input->getOption('skip_binary') === 'yes', $input->getOption('recurse') === 'no'); + $output->writeln(sprintf( + 'Successfully exported workspace "%s", path "%s" to file "%s".', + $session->getWorkspace()->getName(), + $path, + realpath($filename) + )); + return 0; } } diff --git a/src/PHPCR/Util/Console/Command/WorkspaceImportCommand.php b/src/PHPCR/Util/Console/Command/WorkspaceImportCommand.php index 27cf38c..ea537dc 100644 --- a/src/PHPCR/Util/Console/Command/WorkspaceImportCommand.php +++ b/src/PHPCR/Util/Console/Command/WorkspaceImportCommand.php @@ -16,9 +16,9 @@ * @license http://www.apache.org/licenses Apache License Version 2.0, January 2004 * @license http://opensource.org/licenses/MIT MIT License * - * @author David Buchmann + * @author David Buchmann */ -class WorkspaceImportCommand extends Command +class WorkspaceImportCommand extends BaseCommand { /** * {@inheritDoc} @@ -53,7 +53,7 @@ protected function execute(InputInterface $input, OutputInterface $output) { $filename = $input->getArgument('filename'); $parentPath = $input->getOption('parentpath'); - $session = $this->getHelper('phpcr')->getSession(); + $session = $this->getPhpcrSession(); $repo = $session->getRepository(); if (!$repo->getDescriptor(RepositoryInterface::OPTION_XML_IMPORT_SUPPORTED)) { @@ -69,6 +69,13 @@ protected function execute(InputInterface $input, OutputInterface $output) ); $session->save(); + $output->writeln(sprintf( + 'Successfully imported file "%s" to path "%s" in workspace "%s".', + realpath($filename), + $parentPath, + $session->getWorkspace()->getName() + )); + return 0; } } diff --git a/src/PHPCR/Util/Console/Command/WorkspaceListCommand.php b/src/PHPCR/Util/Console/Command/WorkspaceListCommand.php index 07fb5cb..2b4a996 100644 --- a/src/PHPCR/Util/Console/Command/WorkspaceListCommand.php +++ b/src/PHPCR/Util/Console/Command/WorkspaceListCommand.php @@ -14,7 +14,7 @@ * * @author Lukas Kahwe Smith */ -class WorkspaceListCommand extends Command +class WorkspaceListCommand extends BaseCommand { /** * {@inheritDoc} @@ -36,7 +36,7 @@ protected function configure() */ protected function execute(InputInterface $input, OutputInterface $output) { - $session = $this->getHelper('phpcr')->getSession(); + $session = $this->getPhpcrSession(); $workspaces = $session->getWorkspace()->getAccessibleWorkspaceNames(); diff --git a/src/PHPCR/Util/Console/Command/WorkspacePurgeCommand.php b/src/PHPCR/Util/Console/Command/WorkspacePurgeCommand.php index 5afbb00..43c627b 100644 --- a/src/PHPCR/Util/Console/Command/WorkspacePurgeCommand.php +++ b/src/PHPCR/Util/Console/Command/WorkspacePurgeCommand.php @@ -20,7 +20,7 @@ * * @author Daniel Leech */ -class WorkspacePurgeCommand extends Command +class WorkspacePurgeCommand extends BaseCommand { /** * {@inheritDoc} @@ -46,13 +46,13 @@ protected function configure() */ protected function execute(InputInterface $input, OutputInterface $output) { - /** @var $session SessionInterface */ - $session = $this->getHelper('phpcr')->getSession(); + $session = $this->getPhpcrSession(); $force = $input->getOption('force'); $workspaceName = $session->getWorkspace()->getName(); if (!$force) { - $dialog = new DialogHelper(); + /** @var $dialog DialogHelper */ + $dialog = $this->getHelperSet()->get('dialog'); $force = $dialog->askConfirmation($output, sprintf( 'Are you sure you want to purge workspace "%s" Y/N ?', $workspaceName diff --git a/src/PHPCR/Util/Console/Command/WorkspaceQueryCommand.php b/src/PHPCR/Util/Console/Command/WorkspaceQueryCommand.php index 91e9345..c1ee06f 100644 --- a/src/PHPCR/Util/Console/Command/WorkspaceQueryCommand.php +++ b/src/PHPCR/Util/Console/Command/WorkspaceQueryCommand.php @@ -46,9 +46,7 @@ protected function execute(InputInterface $input, OutputInterface $output) $limit = $input->getOption('limit'); $offset = $input->getOption('offset'); - $helper = $this->getPhpcrCliHelper(); - $session = $this->getPhpcrSession(); - + $helper = $this->getPhpcrHelper(); $query = $helper->createQuery($language, $sql); if ($limit) { diff --git a/src/PHPCR/Util/Console/Helper/PhpcrCliHelper.php b/src/PHPCR/Util/Console/Helper/PhpcrCliHelper.php deleted file mode 100644 index 5527296..0000000 --- a/src/PHPCR/Util/Console/Helper/PhpcrCliHelper.php +++ /dev/null @@ -1,176 +0,0 @@ -session = $session; - } - - /** - * Get the session - * - * @return SessionInterface - */ - public function getSession() - { - return $this->session; - } - - /** - * {@inheritDoc} - */ - public function getName() - { - return 'phpcr_cli'; - } - - /** - * Process - or update - a given node. - * Provides common processing for both touch - * and update commands. - */ - public function processNode(OutputInterface $output, $node, $options) - { - $options = array_merge(array( - 'setProp' => array(), - 'removeProp' => array(), - 'addMixins' => array(), - 'removeMixins' => array(), - 'applyClosures' => array(), - 'dump' => false, - ), $options); - - foreach ($options['setProp'] as $set) { - $parts = explode('=', $set); - $output->writeln(sprintf( - ' > Setting property %s to %s', - $parts[0], $parts[1] - )); - $node->setProperty($parts[0], $parts[1]); - } - - foreach ($options['removeProp'] as $unset) { - $output->writeln(sprintf( - ' > Unsetting property %s', - $unset - )); - $node->setProperty($unset, null); - } - - foreach ($options['addMixins'] as $addMixin) { - $output->writeln(sprintf( - ' > Adding mixin %s', - $addMixin - )); - - $node->addMixin($addMixin); - } - - foreach ($options['removeMixins'] as $removeMixin) { - $output->writeln(sprintf( - ' > Removing mixin %s', - $removeMixin - )); - - $node->removeMixin($removeMixin); - } - - foreach ($options['applyClosures'] as $closure) { - if ($closure instanceof \Closure) { - $output->writeln( - ' > Applying closure' - ); - } else { - $closureString = $closure; - $closure = create_function('$session, $node', $closure); - $output->writeln(sprintf( - ' > Applying closure: %s', - strlen($closureString) > 75 ? substr($closureString, 0, 72).'...' : $closureString - )); - } - - $closure($this->session, $node); - } - - if ($options['dump']) { - $output->writeln('Node dump: '); - /** @var $property PropertyInterface */ - foreach ($node->getProperties() as $property) { - $value = $property->getValue(); - if (!is_string($value)) { - $value = print_r($value, true); - } - $output->writeln(sprintf(' - %s = %s', - $property->getName(), - $value - )); - } - } - } - - /** - * Create a PHPCR query using the given language and - * query string. - * - * @param string Language type - SQL, SQL2 - * @param string JCR Query - * - * @return PHPCR/QueryInterface - */ - public function createQuery($language, $sql) - { - $this->validateQueryLanguage($language); - - $session = $this->getSession(); - $qm = $session->getWorkspace()->getQueryManager(); - $language = strtoupper($language); - $query = $qm->createQuery($sql, $language); - - return $query; - } - - /** - * Validate the given query language. - * - * @param string Language type - * - * @return null - */ - protected function validateQueryLanguage($language) - { - $qm = $this->getSession()->getWorkspace()->getQueryManager(); - $langs = $qm->getSupportedQueryLanguages(); - if (!in_array($language, $langs)) { - throw new \Exception(sprintf( - 'Query language "%s" not supported, available query languages: %s', - $language, implode(',', $langs) - )); - } - } -} diff --git a/src/PHPCR/Util/Console/Helper/PhpcrHelper.php b/src/PHPCR/Util/Console/Helper/PhpcrHelper.php index 06d1f07..67ae461 100644 --- a/src/PHPCR/Util/Console/Helper/PhpcrHelper.php +++ b/src/PHPCR/Util/Console/Helper/PhpcrHelper.php @@ -2,7 +2,11 @@ namespace PHPCR\Util\Console\Helper; +use Symfony\Component\Console\Output\OutputInterface; use Symfony\Component\Console\Helper\Helper; + +use PHPCR\NodeInterface; +use PHPCR\PropertyInterface; use PHPCR\SessionInterface; /** @@ -48,4 +52,132 @@ public function getName() { return 'phpcr'; } + + /** + * Process - or update - a given node. + * + * Provides common processing for both touch and update commands. + * + * @param OutputInterface $output used for status updates. + * @param NodeInterface $node the node to manipulate. + * @param array $operations to execute on that node. + */ + public function processNode(OutputInterface $output, NodeInterface $node, array $operations) + { + $operations = array_merge(array( + 'setProp' => array(), + 'removeProp' => array(), + 'addMixins' => array(), + 'removeMixins' => array(), + 'applyClosures' => array(), + 'dump' => false, + ), $operations); + + foreach ($operations['setProp'] as $set) { + $parts = explode('=', $set); + $output->writeln(sprintf( + ' > Setting property %s to %s', + $parts[0], $parts[1] + )); + $node->setProperty($parts[0], $parts[1]); + } + + foreach ($operations['removeProp'] as $unset) { + $output->writeln(sprintf( + ' > Unsetting property %s', + $unset + )); + $node->setProperty($unset, null); + } + + foreach ($operations['addMixins'] as $addMixin) { + $output->writeln(sprintf( + ' > Adding mixin %s', + $addMixin + )); + + $node->addMixin($addMixin); + } + + foreach ($operations['removeMixins'] as $removeMixin) { + $output->writeln(sprintf( + ' > Removing mixin %s', + $removeMixin + )); + + $node->removeMixin($removeMixin); + } + + foreach ($operations['applyClosures'] as $closure) { + if ($closure instanceof \Closure) { + $output->writeln( + ' > Applying closure' + ); + } else { + $closureString = $closure; + $closure = create_function('$session, $node', $closure); + $output->writeln(sprintf( + ' > Applying closure: %s', + strlen($closureString) > 75 ? substr($closureString, 0, 72).'...' : $closureString + )); + } + + $closure($this->session, $node); + } + + if ($operations['dump']) { + $output->writeln('Node dump: '); + /** @var $property PropertyInterface */ + foreach ($node->getProperties() as $property) { + $value = $property->getValue(); + if (!is_string($value)) { + $value = print_r($value, true); + } + $output->writeln(sprintf(' - %s = %s', + $property->getName(), + $value + )); + } + } + } + + /** + * Create a PHPCR query using the given language and + * query string. + * + * @param string $language Language type - SQL, SQL2 + * @param string $sql JCR Query string + * + * @return \PHPCR\Query\QueryInterface + */ + public function createQuery($language, $sql) + { + $this->validateQueryLanguage($language); + + $session = $this->getSession(); + $qm = $session->getWorkspace()->getQueryManager(); + $language = strtoupper($language); + $query = $qm->createQuery($sql, $language); + + return $query; + } + + /** + * Check if this is a supported query language. + * + * @param string $language Language name. + * + * @throws \Exception if the language is not supported. + */ + protected function validateQueryLanguage($language) + { + $qm = $this->getSession()->getWorkspace()->getQueryManager(); + $langs = $qm->getSupportedQueryLanguages(); + if (!in_array($language, $langs)) { + throw new \Exception(sprintf( + 'Query language "%s" not supported, available query languages: %s', + $language, implode(',', $langs) + )); + } + } } diff --git a/src/PHPCR/Util/NodeHelper.php b/src/PHPCR/Util/NodeHelper.php index 8bcf63b..be8922c 100644 --- a/src/PHPCR/Util/NodeHelper.php +++ b/src/PHPCR/Util/NodeHelper.php @@ -17,7 +17,7 @@ * @license http://opensource.org/licenses/MIT MIT License * * @author Daniel Barsotti - * @author David Buchmann + * @author David Buchmann */ class NodeHelper { diff --git a/src/PHPCR/Util/PathHelper.php b/src/PHPCR/Util/PathHelper.php index 363b288..2a8009e 100644 --- a/src/PHPCR/Util/PathHelper.php +++ b/src/PHPCR/Util/PathHelper.php @@ -10,7 +10,7 @@ * @license http://www.apache.org/licenses Apache License Version 2.0, January 2004 * @license http://opensource.org/licenses/MIT MIT License * - * @author David Buchmann + * @author David Buchmann */ class PathHelper { @@ -49,10 +49,10 @@ public static function assertValidAbsolutePath($path, $destination = false, $thr || strlen($path) > 1 && '/' === $path[strlen($path) - 1] || preg_match('-//|/\./|/\.\./-', $path) ) { - return self::error("Invalid path $path", $throw); + return self::error("Invalid path '$path'", $throw); } if ($destination && ']' === $path[strlen($path) - 1]) { - return self::error("Destination path may not end with index $path", $throw); + return self::error("Destination path may not end with index: '$path'", $throw); } return true; diff --git a/tests/PHPCR/Tests/Util/Console/Command/BaseCommandTest.php b/tests/PHPCR/Tests/Util/Console/Command/BaseCommandTest.php index c9e4979..bcd37c6 100644 --- a/tests/PHPCR/Tests/Util/Console/Command/BaseCommandTest.php +++ b/tests/PHPCR/Tests/Util/Console/Command/BaseCommandTest.php @@ -81,13 +81,10 @@ public function setUp() )->disableOriginalConstructor()->getMock(); $this->helperSet = new HelperSet(array( - 'session' => new PhpcrHelper($this->session), + 'phpcr' => new PhpcrHelper($this->session), + 'phpcr_console_dumper' => $this->dumperHelper, )); - $this->phpcrCliHelper = $this->getMockBuilder('PHPCR\Util\Console\Helper\PhpcrCliHelper') - ->disableOriginalConstructor() - ->getMock(); - $this->session->expects($this->any()) ->method('getWorkspace') ->will($this->returnValue($this->workspace)); diff --git a/tests/PHPCR/Tests/Util/Console/Command/NodeDumpCommandTest.php b/tests/PHPCR/Tests/Util/Console/Command/NodeDumpCommandTest.php index 518ceaa..229a19c 100644 --- a/tests/PHPCR/Tests/Util/Console/Command/NodeDumpCommandTest.php +++ b/tests/PHPCR/Tests/Util/Console/Command/NodeDumpCommandTest.php @@ -20,12 +20,8 @@ public function setUp() $this->treeWalker = $this->getMockBuilder( 'PHPCR\Util\TreeWalker' )->disableOriginalConstructor()->getMock(); - } - protected function addCommand() - { $ndCommand = new NodeDumpCommand(); - $ndCommand->setPhpcrConsoleDumperHelper($this->dumperHelper); $this->application->add($ndCommand); } @@ -48,7 +44,6 @@ public function testCommand() ->with($this->node1) ; - $this->addCommand(); $this->executeCommand('phpcr:node:dump', array()); } @@ -73,14 +68,11 @@ public function testCommandIdentifier() ->with($this->node1) ; - $this->addCommand(); $this->executeCommand('phpcr:node:dump', array('identifier' => $uuid)); } public function testInvalidRefFormat() { - $this->addCommand(); - try { $this->executeCommand('phpcr:node:dump', array('--ref-format' => 'xy')); $this->fail('invalid ref-format did not produce exception'); @@ -98,8 +90,6 @@ public function testNotFound() ->will($this->throwException(new ItemNotFoundException())) ; - $this->addCommand(); - $ct = $this->executeCommand('phpcr:node:dump', array(), 1); $this->assertContains('does not exist', $ct->getDisplay()); } diff --git a/tests/PHPCR/Tests/Util/Console/Command/NodeMoveCommandTest.php b/tests/PHPCR/Tests/Util/Console/Command/NodeMoveCommandTest.php index cf121da..487b2f7 100644 --- a/tests/PHPCR/Tests/Util/Console/Command/NodeMoveCommandTest.php +++ b/tests/PHPCR/Tests/Util/Console/Command/NodeMoveCommandTest.php @@ -26,6 +26,6 @@ public function testCommand($args) ->method('save'); $this->application->add(new NodeMoveCommand()); - $ct = $this->executeCommand('phpcr:node:move', $args); + $this->executeCommand('phpcr:node:move', $args); } } diff --git a/tests/PHPCR/Tests/Util/Console/Command/NodeTouchCommandTest.php b/tests/PHPCR/Tests/Util/Console/Command/NodeTouchCommandTest.php index cafe8f1..5a4c63d 100644 --- a/tests/PHPCR/Tests/Util/Console/Command/NodeTouchCommandTest.php +++ b/tests/PHPCR/Tests/Util/Console/Command/NodeTouchCommandTest.php @@ -2,6 +2,8 @@ namespace PHPCR\Tests\Util\Console\Command; +use PHPCR\PathNotFoundException; +use PHPCR\Util\Console\Helper\PhpcrHelper; use Symfony\Component\Console\Application; use PHPCR\Util\Console\Command\NodeTouchCommand; @@ -10,20 +12,37 @@ */ class NodeTouchCommandTest extends BaseCommandTest { + /** + * @var PhpcrHelper|\PHPUnit_Framework_MockObject_MockObject + */ + public $phpcrHelper; + public function setUp() { parent::setUp(); - $this->command = new NodeTouchCommand; + $command = new NodeTouchCommand; + $this->application->add($command); // override default concrete instance with mock - $this->command->setPhpcrCliHelper($this->phpcrCliHelper); - $this->application->add($this->command); - $this->nodeType = $this->getMock('PHPCR\NodeType\NodeTypeInterface'); + $this->phpcrHelper = $this->getMockBuilder('PHPCR\Util\Console\Helper\PhpcrHelper') + ->disableOriginalConstructor() + ->getMock() + ; + $this->phpcrHelper->expects($this->any()) + ->method('getSession') + ->will($this->returnValue($this->session)) + ; + $this->phpcrHelper->expects($this->any()) + ->method('getName') + ->will($this->returnValue('phpcr')) + ; + $this->helperSet->set($this->phpcrHelper); } public function testTouch() { $node = $this->node1; + $child = $this->getMock('PHPCR\Tests\Stubs\MockNode'); $this->session->expects($this->exactly(2)) ->method('getNode') @@ -32,36 +51,46 @@ public function testTouch() case '/': return $node; case '/cms': - return null; + throw new PathNotFoundException(); } + throw new \Exception('Unexpected ' . $path); })); $this->node1->expects($this->once()) - ->method('addNode'); + ->method('addNode') + ->with('cms') + ->will($this->returnValue($child)) + ; $this->session->expects($this->once()) ->method('save'); - $ct = $this->executeCommand('phpcr:node:touch', array( + $this->executeCommand('phpcr:node:touch', array( 'path' => '/cms', )); } public function testUpdate() { + $nodeType = $this->getMock('PHPCR\NodeType\NodeTypeInterface'); + $nodeType->expects($this->once()) + ->method('getName') + ->will($this->returnValue('nt:unstructured')) + ; + $this->session->expects($this->exactly(1)) ->method('getNode') ->with('/cms') - ->will($this->returnValue($this->node1)); + ->will($this->returnValue($this->node1)) + ; $this->node1->expects($this->once()) ->method('getPrimaryNodeType') - ->will($this->returnValue($this->nodeType)); - $this->nodeType->expects($this->once()) - ->method('getName') - ->will($this->returnValue('nt:unstructured')); + ->will($this->returnValue($nodeType)) + ; $me = $this; - $this->phpcrCliHelper->expects($this->once()) + + $this->phpcrHelper->expects($this->once()) ->method('processNode') ->will($this->returnCallback(function ($output, $node, $options) use ($me) { $me->assertEquals($me->node1, $node); @@ -74,7 +103,7 @@ public function testUpdate() ), $options); })); - $ct = $this->executeCommand('phpcr:node:touch', array( + $this->executeCommand('phpcr:node:touch', array( 'path' => '/cms', '--set-prop' => array('foo=bar'), '--remove-prop' => array('bar'), diff --git a/tests/PHPCR/Tests/Util/Console/Command/NodesUpdateCommandTest.php b/tests/PHPCR/Tests/Util/Console/Command/NodesUpdateCommandTest.php index bc9cb36..db523a2 100644 --- a/tests/PHPCR/Tests/Util/Console/Command/NodesUpdateCommandTest.php +++ b/tests/PHPCR/Tests/Util/Console/Command/NodesUpdateCommandTest.php @@ -2,6 +2,7 @@ namespace PHPCR\Tests\Util\Console\Command; +use PHPCR\Util\Console\Helper\PhpcrHelper; use Symfony\Component\Console\Application; use PHPCR\Util\Console\Command\NodesUpdateCommand; diff --git a/tests/PHPCR/Tests/Util/Console/Command/WorkspaceCreateCommandTest.php b/tests/PHPCR/Tests/Util/Console/Command/WorkspaceCreateCommandTest.php index 0a00efa..1181b43 100644 --- a/tests/PHPCR/Tests/Util/Console/Command/WorkspaceCreateCommandTest.php +++ b/tests/PHPCR/Tests/Util/Console/Command/WorkspaceCreateCommandTest.php @@ -34,6 +34,10 @@ public function testCreate() ->method('createWorkspace') ->with('test_workspace') ; + $this->workspace->expects($this->once()) + ->method('getAccessibleWorkspaceNames') + ->will($this->returnValue(array('default'))) + ; $this->executeCommand('phpcr:workspace:create', array( 'name' => 'test_workspace' @@ -41,10 +45,7 @@ public function testCreate() } /** - * The real console catches this exception. - * - * @expectedException \PHPCR\RepositoryException - * @expectedExceptionMessage Workspace exists + * Handle trying to create existing workspace. */ public function testCreateExisting() { @@ -61,13 +62,16 @@ public function testCreateExisting() ->will($this->returnValue(true)) ; $this->workspace->expects($this->once()) - ->method('createWorkspace') - ->with('test_workspace') - ->will($this->throwException(new RepositoryException('Workspace exists'))) + ->method('getAccessibleWorkspaceNames') + ->will($this->returnValue(array('default', 'test'))) ; - $this->executeCommand('phpcr:workspace:create', array( - 'name' => 'test_workspace' - )); + $tester = $this->executeCommand( + 'phpcr:workspace:create', + array('name' => 'test'), + 2 + ); + + $this->assertContains('already has a workspace called "test"', $tester->getDisplay()); } } diff --git a/tests/PHPCR/Tests/Util/Console/Command/WorkspaceImportCommandTest.php b/tests/PHPCR/Tests/Util/Console/Command/WorkspaceImportCommandTest.php index e85bb78..d4641a5 100644 --- a/tests/PHPCR/Tests/Util/Console/Command/WorkspaceImportCommandTest.php +++ b/tests/PHPCR/Tests/Util/Console/Command/WorkspaceImportCommandTest.php @@ -30,6 +30,6 @@ public function testNodeTypeList() 'filename' => 'test_import.xml' )); - $this->assertEmpty($ct->getDisplay()); + $this->assertContains('Successfully imported', $ct->getDisplay()); } } diff --git a/tests/PHPCR/Tests/Util/Console/Helper/PhpcrConsoleDumperHelperTest.php b/tests/PHPCR/Tests/Util/Console/Helper/PhpcrConsoleDumperHelperTest.php index e253219..54d40f5 100644 --- a/tests/PHPCR/Tests/Util/Console/Helper/PhpcrConsoleDumperHelperTest.php +++ b/tests/PHPCR/Tests/Util/Console/Helper/PhpcrConsoleDumperHelperTest.php @@ -4,9 +4,15 @@ class PhpcrConsoleDumperHelperTest extends PHPUnit_Framework_TestCase { + private $outputMock; + /** + * @var PhpcrConsoleDumperHelper + */ + private $helper; + public function setUp() { - $this->output = $this->getMock('Symfony\Component\Console\Output\OutputInterface'); + $this->outputMock = $this->getMock('Symfony\Component\Console\Output\OutputInterface'); $this->helper = new PhpcrConsoleDumperHelper; } @@ -32,7 +38,7 @@ public function testGetTreeWalker($options) 'show_sys_nodes' => false, ), $options); - $tw = $this->helper->getTreeWalker($this->output, $options); + $tw = $this->helper->getTreeWalker($this->outputMock, $options); $this->assertInstanceOf( 'PHPCR\Util\TreeWalker', $tw