Skip to content
Snippets Groups Projects
Commit 7c5e93ad authored by Adam G-H's avatar Adam G-H
Browse files

Issue #3277211 by phenaproxima: Update Composer Stager to 0.5.0

parent 805c4cd2
No related branches found
No related tags found
No related merge requests found
Showing
with 220 additions and 106 deletions
......@@ -26,6 +26,7 @@ services:
- '@event_dispatcher'
- '@tempstore.shared'
- '@datetime.time'
- '@PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface'
automatic_updates.cron_updater:
class: Drupal\automatic_updates\CronUpdater
arguments:
......@@ -40,6 +41,7 @@ services:
- '@event_dispatcher'
- '@tempstore.shared'
- '@datetime.time'
- '@PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface'
automatic_updates.staged_projects_validator:
class: Drupal\automatic_updates\Validator\StagedProjectsValidator
arguments:
......
......@@ -11,6 +11,7 @@ services:
- '@event_dispatcher'
- '@tempstore.shared'
- '@datetime.time'
- '@PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface'
automatic_updates_extensions.validator.target_release:
class: Drupal\automatic_updates_extensions\Validator\UpdateReleaseValidator
tags:
......
......@@ -13,7 +13,7 @@
"require": {
"ext-json": "*",
"drupal/core": "^9.2",
"php-tuf/composer-stager": "0.3.0",
"php-tuf/composer-stager": "0.5.0",
"composer/composer": "^2.2.12 || ^2.3.5",
"composer-runtime-api": "^2.0.9"
},
......
......@@ -11,7 +11,7 @@
function package_manager_requirements(string $phase) {
$requirements = [];
if (!class_exists('PhpTuf\ComposerStager\Domain\Beginner')) {
if (!class_exists('\PhpTuf\ComposerStager\Domain\Core\Beginner\Beginner')) {
$requirements['package_manager_composer_dependencies'] = [
'title' => 'Missing dependency',
'description' => t('External dependencies for Package Manager are not available. Composer must be used to download the module with dependencies.'),
......
......@@ -11,7 +11,7 @@ services:
- '@file_system'
- '@config.factory'
public: false
PhpTuf\ComposerStager\Infrastructure\Filesystem\Filesystem:
PhpTuf\ComposerStager\Infrastructure\Service\Filesystem\Filesystem:
autowire: true
public: false
Drupal\package_manager\ExecutableFinder:
......@@ -19,47 +19,114 @@ services:
$config_factory: '@config.factory'
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Process\ProcessFactoryInterface:
PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactory:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Factory\Process\ProcessFactoryInterface:
alias: 'Drupal\package_manager\ProcessFactory'
PhpTuf\ComposerStager\Domain\Filesystem\FilesystemInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Filesystem\Filesystem'
PhpTuf\ComposerStager\Infrastructure\Process\ExecutableFinderInterface:
PhpTuf\ComposerStager\Domain\Service\Filesystem\FilesystemInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\Filesystem\Filesystem'
PhpTuf\ComposerStager\Infrastructure\Service\Finder\ExecutableFinderInterface:
alias: 'Drupal\package_manager\ExecutableFinder'
PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactory'
# Executable runners for Composer Stager.
PhpTuf\ComposerStager\Infrastructure\Process\Runner\RsyncRunner:
PhpTuf\ComposerStager\Infrastructure\Service\ProcessRunner\RsyncRunner:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Process\Runner\ComposerRunner:
PhpTuf\ComposerStager\Infrastructure\Service\ProcessRunner\ComposerRunner:
autowire: true
public: false
PhpTuf\ComposerStager\Domain\Process\Runner\RsyncRunnerInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Process\Runner\RsyncRunner'
PhpTuf\ComposerStager\Domain\Process\Runner\ComposerRunnerInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Process\Runner\ComposerRunner'
PhpTuf\ComposerStager\Domain\Service\ProcessRunner\RsyncRunnerInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\ProcessRunner\RsyncRunner'
PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ComposerRunnerInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\ProcessRunner\ComposerRunner'
# File syncers for Composer Stager.
PhpTuf\ComposerStager\Infrastructure\FileSyncer\RsyncFileSyncer:
PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\RsyncFileSyncer:
autowire: true
PhpTuf\ComposerStager\Infrastructure\FileSyncer\PhpFileSyncer:
PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\PhpFileSyncer:
autowire: true
Drupal\package_manager\FileSyncerFactory:
arguments:
$config_factory: '@config.factory'
autowire: true
public: false
PhpTuf\ComposerStager\Domain\FileSyncer\FileSyncerInterface:
PhpTuf\ComposerStager\Domain\Service\FileSyncer\FileSyncerInterface:
factory: ['@Drupal\package_manager\FileSyncerFactory', 'create']
# Composer Stager preconditions.
PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\CommonPreconditions:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\BeginnerPreconditions:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\StagerPreconditions:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\CommitterPreconditions:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\StagingDirIsReady:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Service\Precondition\ComposerIsAvailable:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Service\Precondition\ActiveDirExists:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Service\Precondition\ActiveDirIsWritable:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Service\Precondition\ActiveAndStagingDirsAreDifferent:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Service\Precondition\StagingDirExists:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Service\Precondition\StagingDirIsWritable:
autowire: true
public: false
PhpTuf\ComposerStager\Infrastructure\Service\Precondition\StagingDirDoesNotExist:
autowire: true
public: false
PhpTuf\ComposerStager\Domain\Aggregate\PreconditionsTree\CommitterPreconditionsInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\CommitterPreconditions'
PhpTuf\ComposerStager\Domain\Aggregate\PreconditionsTree\BeginnerPreconditionsInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\BeginnerPreconditions'
PhpTuf\ComposerStager\Domain\Aggregate\PreconditionsTree\StagerPreconditionsInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\StagerPreconditions'
PhpTuf\ComposerStager\Domain\Aggregate\PreconditionsTree\CommonPreconditionsInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\CommonPreconditions'
PhpTuf\ComposerStager\Domain\Aggregate\PreconditionsTree\StagingDirIsReadyInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Aggregate\PreconditionsTree\StagingDirIsReady'
PhpTuf\ComposerStager\Domain\Service\Precondition\ComposerIsAvailableInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\Precondition\ComposerIsAvailable'
PhpTuf\ComposerStager\Domain\Service\Precondition\ActiveDirExistsInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\Precondition\ActiveDirExists'
PhpTuf\ComposerStager\Domain\Service\Precondition\ActiveDirIsWritableInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\Precondition\ActiveDirIsWritable'
PhpTuf\ComposerStager\Domain\Service\Precondition\ActiveAndStagingDirsAreDifferentInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\Precondition\ActiveAndStagingDirsAreDifferent'
PhpTuf\ComposerStager\Domain\Service\Precondition\StagingDirExistsInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\Precondition\StagingDirExists'
PhpTuf\ComposerStager\Domain\Service\Precondition\StagingDirIsWritableInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\Precondition\StagingDirIsWritable'
PhpTuf\ComposerStager\Domain\Service\Precondition\StagingDirDoesNotExistInterface:
alias: 'PhpTuf\ComposerStager\Infrastructure\Service\Precondition\StagingDirDoesNotExist'
# Services provided to Drupal by Package Manager.
package_manager.beginner:
class: PhpTuf\ComposerStager\Domain\Beginner
class: PhpTuf\ComposerStager\Domain\Core\Beginner\Beginner
autowire: true
package_manager.stager:
class: PhpTuf\ComposerStager\Domain\Stager
class: PhpTuf\ComposerStager\Domain\Core\Stager\Stager
autowire: true
package_manager.committer:
class: PhpTuf\ComposerStager\Domain\Committer
class: PhpTuf\ComposerStager\Domain\Core\Committer\Committer
autowire: true
package_manager.path_locator:
class: Drupal\package_manager\PathLocator
......@@ -70,7 +137,7 @@ services:
package_manager.validator.composer_executable:
class: Drupal\package_manager\Validator\ComposerExecutableValidator
arguments:
- '@PhpTuf\ComposerStager\Domain\Process\Runner\ComposerRunnerInterface'
- '@PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ComposerRunnerInterface'
- '@module_handler'
- '@string_translation'
tags:
......
......@@ -3,8 +3,8 @@
namespace Drupal\package_manager;
use Drupal\Core\Config\ConfigFactoryInterface;
use PhpTuf\ComposerStager\Infrastructure\Process\ExecutableFinderInterface;
use PhpTuf\ComposerStager\Infrastructure\Process\ExecutableFinder as StagerExecutableFinder;
use PhpTuf\ComposerStager\Infrastructure\Service\Finder\ExecutableFinder as StagerExecutableFinder;
use PhpTuf\ComposerStager\Infrastructure\Service\Finder\ExecutableFinderInterface;
use Symfony\Component\Process\ExecutableFinder as SymfonyExecutableFinder;
/**
......@@ -15,7 +15,7 @@ class ExecutableFinder implements ExecutableFinderInterface {
/**
* The decorated executable finder.
*
* @var \PhpTuf\ComposerStager\Infrastructure\Process\ExecutableFinder
* @var \PhpTuf\ComposerStager\Infrastructure\Service\Finder\ExecutableFinder
*/
private $decorated;
......
......@@ -3,36 +3,35 @@
namespace Drupal\package_manager;
use Drupal\Core\Config\ConfigFactoryInterface;
use PhpTuf\ComposerStager\Domain\FileSyncer\FileSyncerFactoryInterface;
use PhpTuf\ComposerStager\Domain\FileSyncer\FileSyncerInterface;
use PhpTuf\ComposerStager\Infrastructure\FileSyncer\FileSyncerFactory as StagerFileSyncerFactory;
use PhpTuf\ComposerStager\Infrastructure\FileSyncer\PhpFileSyncer;
use PhpTuf\ComposerStager\Infrastructure\FileSyncer\RsyncFileSyncer;
use PhpTuf\ComposerStager\Domain\Service\FileSyncer\FileSyncerInterface;
use PhpTuf\ComposerStager\Infrastructure\Factory\FileSyncer\FileSyncerFactory as StagerFileSyncerFactory;
use PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\PhpFileSyncer;
use PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\RsyncFileSyncer;
use Symfony\Component\Process\ExecutableFinder;
/**
* A file syncer factory which creates a file syncer according to configuration.
*/
class FileSyncerFactory implements FileSyncerFactoryInterface {
class FileSyncerFactory {
/**
* The decorated file syncer factory.
*
* @var \PhpTuf\ComposerStager\Domain\FileSyncer\FileSyncerFactoryInterface
* @var \PhpTuf\ComposerStager\Infrastructure\Factory\FileSyncer\FileSyncerFactory
*/
protected $decorated;
/**
* The PHP file syncer service.
*
* @var \PhpTuf\ComposerStager\Infrastructure\FileSyncer\PhpFileSyncer
* @var \PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\PhpFileSyncer
*/
protected $phpFileSyncer;
/**
* The rsync file syncer service.
*
* @var \PhpTuf\ComposerStager\Infrastructure\FileSyncer\RsyncFileSyncer
* @var \PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\RsyncFileSyncer
*/
protected $rsyncFileSyncer;
......@@ -48,9 +47,9 @@ class FileSyncerFactory implements FileSyncerFactoryInterface {
*
* @param \Symfony\Component\Process\ExecutableFinder $executable_finder
* The Symfony executable finder.
* @param \PhpTuf\ComposerStager\Infrastructure\FileSyncer\PhpFileSyncer $php_file_syncer
* @param \PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\PhpFileSyncer $php_file_syncer
* The PHP file syncer service.
* @param \PhpTuf\ComposerStager\Infrastructure\FileSyncer\RsyncFileSyncer $rsync_file_syncer
* @param \PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\RsyncFileSyncer $rsync_file_syncer
* The rsync file syncer service.
* @param \Drupal\Core\Config\ConfigFactoryInterface $config_factory
* The config factory service.
......
......@@ -4,6 +4,7 @@ namespace Drupal\package_manager;
use Drupal\Core\Extension\ModuleUninstallValidatorInterface;
use Drupal\Core\StringTranslation\StringTranslationTrait;
use PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface;
use Symfony\Component\DependencyInjection\ContainerAwareInterface;
use Symfony\Component\DependencyInjection\ContainerAwareTrait;
......@@ -28,7 +29,8 @@ class PackageManagerUninstallValidator implements ModuleUninstallValidatorInterf
$this->container->get('file_system'),
$this->container->get('event_dispatcher'),
$this->container->get('tempstore.shared'),
$this->container->get('datetime.time')
$this->container->get('datetime.time'),
$this->container->get(PathFactoryInterface::class)
);
if ($stage->isAvailable() || !$stage->isApplying()) {
return [];
......
......@@ -4,8 +4,8 @@ namespace Drupal\package_manager;
use Drupal\Core\Config\ConfigFactoryInterface;
use Drupal\Core\File\FileSystemInterface;
use PhpTuf\ComposerStager\Infrastructure\Process\ProcessFactory as StagerProcessFactory;
use PhpTuf\ComposerStager\Infrastructure\Process\ProcessFactoryInterface;
use PhpTuf\ComposerStager\Infrastructure\Factory\Process\ProcessFactoryInterface;
use PhpTuf\ComposerStager\Infrastructure\Factory\Process\ProcessFactory as StagerProcessFactory;
use Symfony\Component\Process\Process;
/**
......@@ -16,7 +16,7 @@ final class ProcessFactory implements ProcessFactoryInterface {
/**
* The decorated process factory.
*
* @var \PhpTuf\ComposerStager\Infrastructure\Process\ProcessFactoryInterface
* @var \PhpTuf\ComposerStager\Infrastructure\Factory\Process\ProcessFactoryInterface
*/
private $decorated;
......
......@@ -21,9 +21,11 @@ use Drupal\package_manager\Event\StageEvent;
use Drupal\package_manager\Exception\StageException;
use Drupal\package_manager\Exception\StageOwnershipException;
use Drupal\package_manager\Exception\StageValidationException;
use PhpTuf\ComposerStager\Domain\BeginnerInterface;
use PhpTuf\ComposerStager\Domain\CommitterInterface;
use PhpTuf\ComposerStager\Domain\StagerInterface;
use PhpTuf\ComposerStager\Domain\Core\Beginner\BeginnerInterface;
use PhpTuf\ComposerStager\Domain\Core\Committer\CommitterInterface;
use PhpTuf\ComposerStager\Domain\Core\Stager\StagerInterface;
use PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface;
use PhpTuf\ComposerStager\Infrastructure\Value\PathList\PathList;
use Symfony\Contracts\EventDispatcher\EventDispatcherInterface;
/**
......@@ -102,21 +104,21 @@ class Stage {
/**
* The beginner service.
*
* @var \PhpTuf\ComposerStager\Domain\BeginnerInterface
* @var \PhpTuf\ComposerStager\Domain\Core\Beginner\BeginnerInterface
*/
protected $beginner;
/**
* The stager service.
*
* @var \PhpTuf\ComposerStager\Domain\StagerInterface
* @var \PhpTuf\ComposerStager\Domain\Core\Stager\StagerInterface
*/
protected $stager;
/**
* The committer service.
*
* @var \PhpTuf\ComposerStager\Domain\CommitterInterface
* @var \PhpTuf\ComposerStager\Domain\Core\Committer\CommitterInterface
*/
protected $committer;
......@@ -148,6 +150,13 @@ class Stage {
*/
protected $time;
/**
* The path factory service.
*
* @var \PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface
*/
protected $pathFactory;
/**
* The lock info for the stage.
*
......@@ -164,11 +173,11 @@ class Stage {
* The config factory service.
* @param \Drupal\package_manager\PathLocator $path_locator
* The path locator service.
* @param \PhpTuf\ComposerStager\Domain\BeginnerInterface $beginner
* @param \PhpTuf\ComposerStager\Domain\Core\Beginner\BeginnerInterface $beginner
* The beginner service.
* @param \PhpTuf\ComposerStager\Domain\StagerInterface $stager
* @param \PhpTuf\ComposerStager\Domain\Core\Stager\StagerInterface $stager
* The stager service.
* @param \PhpTuf\ComposerStager\Domain\CommitterInterface $committer
* @param \PhpTuf\ComposerStager\Domain\Core\Committer\CommitterInterface $committer
* The committer service.
* @param \Drupal\Core\File\FileSystemInterface $file_system
* The file system service.
......@@ -178,8 +187,10 @@ class Stage {
* The shared tempstore factory.
* @param \Drupal\Component\Datetime\TimeInterface $time
* The time service.
* @param \PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface $path_factory
* The path factory service.
*/
public function __construct(ConfigFactoryInterface $config_factory, PathLocator $path_locator, BeginnerInterface $beginner, StagerInterface $stager, CommitterInterface $committer, FileSystemInterface $file_system, EventDispatcherInterface $event_dispatcher, SharedTempStoreFactory $shared_tempstore, TimeInterface $time) {
public function __construct(ConfigFactoryInterface $config_factory, PathLocator $path_locator, BeginnerInterface $beginner, StagerInterface $stager, CommitterInterface $committer, FileSystemInterface $file_system, EventDispatcherInterface $event_dispatcher, SharedTempStoreFactory $shared_tempstore, TimeInterface $time, PathFactoryInterface $path_factory) {
$this->configFactory = $config_factory;
$this->pathLocator = $path_locator;
$this->beginner = $beginner;
......@@ -189,6 +200,7 @@ class Stage {
$this->eventDispatcher = $event_dispatcher;
$this->time = $time;
$this->tempStore = $shared_tempstore->get('package_manager_stage');
$this->pathFactory = $path_factory;
}
/**
......@@ -275,15 +287,15 @@ class Stage {
$this->tempStore->set(static::TEMPSTORE_LOCK_KEY, [$id, static::class]);
$this->claim($id);
$active_dir = $this->pathLocator->getProjectRoot();
$stage_dir = $this->getStageDirectory();
$active_dir = $this->pathFactory->create($this->pathLocator->getProjectRoot());
$stage_dir = $this->pathFactory->create($this->getStageDirectory());
$event = new PreCreateEvent($this);
// If an error occurs and we won't be able to create the stage, mark it as
// available.
$this->dispatch($event, [$this, 'markAsAvailable']);
$this->beginner->begin($active_dir, $stage_dir, $event->getExcludedPaths(), NULL, $timeout);
$this->beginner->begin($active_dir, $stage_dir, new PathList($event->getExcludedPaths()), NULL, $timeout);
$this->dispatch(new PostCreateEvent($this));
return $id;
}
......@@ -302,23 +314,24 @@ class Stage {
$this->checkOwnership();
$this->dispatch(new PreRequireEvent($this, $runtime, $dev));
$dir = $this->getStageDirectory();
$active_dir = $this->pathFactory->create($this->pathLocator->getProjectRoot());
$stage_dir = $this->pathFactory->create($this->getStageDirectory());
// Change the runtime and dev requirements as needed, but don't update
// the installed packages yet.
if ($runtime) {
$command = array_merge(['require', '--no-update'], $runtime);
$this->stager->stage($command, $dir);
$this->stager->stage($command, $active_dir, $stage_dir);
}
if ($dev) {
$command = array_merge(['require', '--dev', '--no-update'], $dev);
$this->stager->stage($command, $dir);
$this->stager->stage($command, $active_dir, $stage_dir);
}
// If constraints were changed, update those packages.
if ($runtime || $dev) {
$command = array_merge(['update', '--with-all-dependencies'], $runtime, $dev);
$this->stager->stage($command, $dir);
$this->stager->stage($command, $active_dir, $stage_dir);
}
$this->dispatch(new PostRequireEvent($this, $runtime, $dev));
......@@ -335,8 +348,8 @@ class Stage {
public function apply(?int $timeout = 600): void {
$this->checkOwnership();
$active_dir = $this->pathLocator->getProjectRoot();
$stage_dir = $this->getStageDirectory();
$active_dir = $this->pathFactory->create($this->pathLocator->getProjectRoot());
$stage_dir = $this->pathFactory->create($this->getStageDirectory());
// If an error occurs while dispatching the events, ensure that ::destroy()
// doesn't think we're in the middle of applying the staged changes to the
......@@ -349,7 +362,7 @@ class Stage {
$this->tempStore->set(self::TEMPSTORE_APPLY_TIME_KEY, $this->time->getRequestTime());
$this->dispatch($event, $release_apply);
$this->committer->commit($stage_dir, $active_dir, $event->getExcludedPaths(), NULL, $timeout);
$this->committer->commit($stage_dir, $active_dir, new PathList($event->getExcludedPaths()), NULL, $timeout);
// Rebuild the container and clear all caches, to ensure that new services
// are picked up.
......
......@@ -9,14 +9,14 @@ use Drupal\package_manager\Event\PreCreateEvent;
use Drupal\package_manager\Event\PreOperationStageEvent;
use Drupal\Core\StringTranslation\StringTranslationTrait;
use Drupal\Core\StringTranslation\TranslationInterface;
use PhpTuf\ComposerStager\Domain\Process\OutputCallbackInterface;
use PhpTuf\ComposerStager\Domain\Process\Runner\ComposerRunnerInterface;
use PhpTuf\ComposerStager\Exception\ExceptionInterface;
use PhpTuf\ComposerStager\Domain\Exception\ExceptionInterface;
use PhpTuf\ComposerStager\Domain\Service\ProcessOutputCallback\ProcessOutputCallbackInterface;
use PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ComposerRunnerInterface;
/**
* Validates the Composer executable is the correct version.
*/
class ComposerExecutableValidator implements PreOperationStageValidatorInterface, OutputCallbackInterface {
class ComposerExecutableValidator implements PreOperationStageValidatorInterface, ProcessOutputCallbackInterface {
use StringTranslationTrait;
......@@ -30,7 +30,7 @@ class ComposerExecutableValidator implements PreOperationStageValidatorInterface
/**
* The Composer runner.
*
* @var \PhpTuf\ComposerStager\Domain\Process\Runner\ComposerRunnerInterface
* @var \PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ComposerRunnerInterface
*/
protected $composer;
......@@ -51,7 +51,7 @@ class ComposerExecutableValidator implements PreOperationStageValidatorInterface
/**
* Constructs a ComposerExecutableValidator object.
*
* @param \PhpTuf\ComposerStager\Domain\Process\Runner\ComposerRunnerInterface $composer
* @param \PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ComposerRunnerInterface $composer
* The Composer runner.
* @param \Drupal\Core\Extension\ModuleHandlerInterface $module_handler
* The module handler service.
......
......@@ -2,8 +2,11 @@
namespace Drupal\package_manager_bypass;
use PhpTuf\ComposerStager\Domain\BeginnerInterface;
use PhpTuf\ComposerStager\Domain\Process\OutputCallbackInterface;
use PhpTuf\ComposerStager\Domain\Core\Beginner\BeginnerInterface;
use PhpTuf\ComposerStager\Domain\Service\ProcessOutputCallback\ProcessOutputCallbackInterface;
use PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ProcessRunnerInterface;
use PhpTuf\ComposerStager\Domain\Value\Path\PathInterface;
use PhpTuf\ComposerStager\Domain\Value\PathList\PathListInterface;
/**
* Defines an update beginner which doesn't do anything.
......@@ -13,7 +16,7 @@ class Beginner extends InvocationRecorderBase implements BeginnerInterface {
/**
* {@inheritdoc}
*/
public function begin(string $activeDir, string $stagingDir, ?array $exclusions = [], ?OutputCallbackInterface $callback = NULL, ?int $timeout = 120): void {
public function begin(PathInterface $activeDir, PathInterface $stagingDir, ?PathListInterface $exclusions = NULL, ?ProcessOutputCallbackInterface $callback = NULL, ?int $timeout = ProcessRunnerInterface::DEFAULT_TIMEOUT): void {
$this->saveInvocationArguments($activeDir, $stagingDir, $exclusions, $timeout);
}
......
......@@ -2,43 +2,22 @@
namespace Drupal\package_manager_bypass;
use PhpTuf\ComposerStager\Domain\CommitterInterface;
use PhpTuf\ComposerStager\Domain\Process\OutputCallbackInterface;
use PhpTuf\ComposerStager\Domain\Core\Committer\CommitterInterface;
use PhpTuf\ComposerStager\Domain\Service\ProcessOutputCallback\ProcessOutputCallbackInterface;
use PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ProcessRunnerInterface;
use PhpTuf\ComposerStager\Domain\Value\Path\PathInterface;
use PhpTuf\ComposerStager\Domain\Value\PathList\PathListInterface;
/**
* Defines an update committer which doesn't do any actual committing.
*/
class Committer extends InvocationRecorderBase implements CommitterInterface {
/**
* The decorated committer service.
*
* @var \PhpTuf\ComposerStager\Domain\CommitterInterface
*/
private $decorated;
/**
* Constructs a Committer object.
*
* @param \PhpTuf\ComposerStager\Domain\CommitterInterface $decorated
* The decorated committer service.
*/
public function __construct(CommitterInterface $decorated) {
$this->decorated = $decorated;
}
/**
* {@inheritdoc}
*/
public function commit(string $stagingDir, string $activeDir, ?array $exclusions = [], ?OutputCallbackInterface $callback = NULL, ?int $timeout = 120): void {
public function commit(PathInterface $stagingDir, PathInterface $activeDir, ?PathListInterface $exclusions = NULL, ?ProcessOutputCallbackInterface $callback = NULL, ?int $timeout = ProcessRunnerInterface::DEFAULT_TIMEOUT): void {
$this->saveInvocationArguments($stagingDir, $activeDir, $exclusions, $timeout);
}
/**
* {@inheritdoc}
*/
public function directoryExists(string $stagingDir): bool {
return $this->decorated->directoryExists($stagingDir);
}
}
......@@ -2,8 +2,10 @@
namespace Drupal\package_manager_bypass;
use PhpTuf\ComposerStager\Domain\Process\OutputCallbackInterface;
use PhpTuf\ComposerStager\Domain\StagerInterface;
use PhpTuf\ComposerStager\Domain\Core\Stager\StagerInterface;
use PhpTuf\ComposerStager\Domain\Service\ProcessOutputCallback\ProcessOutputCallbackInterface;
use PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ProcessRunnerInterface;
use PhpTuf\ComposerStager\Domain\Value\Path\PathInterface;
/**
* Defines an update stager which doesn't actually do anything.
......@@ -13,7 +15,7 @@ class Stager extends InvocationRecorderBase implements StagerInterface {
/**
* {@inheritdoc}
*/
public function stage(array $composerCommand, string $stagingDir, ?OutputCallbackInterface $callback = NULL, ?int $timeout = 120): void {
public function stage(array $composerCommand, PathInterface $activeDir, PathInterface $stagingDir, ?ProcessOutputCallbackInterface $callback = NULL, ?int $timeout = ProcessRunnerInterface::DEFAULT_TIMEOUT): void {
$this->saveInvocationArguments($composerCommand, $stagingDir);
}
......
......@@ -5,6 +5,7 @@ namespace Drupal\package_manager_test_api;
use Drupal\Core\Controller\ControllerBase;
use Drupal\package_manager\PathLocator;
use Drupal\package_manager\Stage;
use PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface;
use Symfony\Component\DependencyInjection\ContainerInterface;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Component\HttpFoundation\Request;
......@@ -54,7 +55,8 @@ class ApiController extends ControllerBase {
$container->get('file_system'),
$container->get('event_dispatcher'),
$container->get('tempstore.shared'),
$container->get('datetime.time')
$container->get('datetime.time'),
$container->get(PathFactoryInterface::class)
);
return new static(
$stage,
......
......@@ -7,8 +7,8 @@ use Drupal\Core\Url;
use Drupal\package_manager\Event\PreCreateEvent;
use Drupal\package_manager\Validator\ComposerExecutableValidator;
use Drupal\package_manager\ValidationResult;
use PhpTuf\ComposerStager\Domain\Process\Runner\ComposerRunnerInterface;
use PhpTuf\ComposerStager\Exception\IOException;
use PhpTuf\ComposerStager\Domain\Exception\IOException;
use PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ComposerRunnerInterface;
use Prophecy\Argument;
/**
......@@ -21,7 +21,7 @@ class ComposerExecutableValidatorTest extends PackageManagerKernelTestBase {
/**
* The mocked Composer runner.
*
* @var \Prophecy\Prophecy\ObjectProphecy|\PhpTuf\ComposerStager\Domain\Process\Runner\ComposerRunnerInterface
* @var \Prophecy\Prophecy\ObjectProphecy|\PhpTuf\ComposerStager\Domain\Service\ProcessRunner\ComposerRunnerInterface
*/
private $composerRunner;
......
......@@ -4,7 +4,7 @@ namespace Drupal\Tests\package_manager\Kernel;
use Drupal\Core\DependencyInjection\ContainerBuilder;
use Drupal\package_manager\ExecutableFinder;
use PhpTuf\ComposerStager\Infrastructure\Process\ExecutableFinderInterface;
use PhpTuf\ComposerStager\Infrastructure\Service\Finder\ExecutableFinderInterface;
use Symfony\Component\Process\ExecutableFinder as SymfonyExecutableFinder;
/**
......
......@@ -3,9 +3,9 @@
namespace Drupal\Tests\package_manager\Kernel;
use Drupal\KernelTests\KernelTestBase;
use PhpTuf\ComposerStager\Domain\FileSyncer\FileSyncerInterface;
use PhpTuf\ComposerStager\Infrastructure\FileSyncer\PhpFileSyncer;
use PhpTuf\ComposerStager\Infrastructure\FileSyncer\RsyncFileSyncer;
use PhpTuf\ComposerStager\Domain\Service\FileSyncer\FileSyncerInterface;
use PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\PhpFileSyncer;
use PhpTuf\ComposerStager\Infrastructure\Service\FileSyncer\RsyncFileSyncer;
/**
* @covers \Drupal\package_manager\FileSyncerFactory
......
......@@ -16,6 +16,10 @@ use org\bovigo\vfs\vfsStream;
use org\bovigo\vfs\vfsStreamDirectory;
use org\bovigo\vfs\vfsStreamFile;
use org\bovigo\vfs\visitor\vfsStreamAbstractVisitor;
use PhpTuf\ComposerStager\Domain\Value\Path\PathInterface;
use PhpTuf\ComposerStager\Infrastructure\Factory\Path\PathFactoryInterface;
use PhpTuf\ComposerStager\Infrastructure\Value\Path\AbstractPath;
use Symfony\Component\DependencyInjection\Definition;
/**
* Base class for kernel tests of Package Manager's functionality.
......@@ -73,6 +77,13 @@ abstract class PackageManagerKernelTestBase extends KernelTestBase {
public function register(ContainerBuilder $container) {
parent::register($container);
// Ensure that Composer Stager uses the test path factory, which is aware
// of the virtual file system.
$definition = new Definition(TestPathFactory::class);
$class = $definition->getClass();
$container->setDefinition($class, $definition->setPublic(FALSE));
$container->setAlias(PathFactoryInterface::class, $class);
foreach ($this->disableValidators as $service_id) {
if ($container->hasDefinition($service_id)) {
$container->getDefinition($service_id)->clearTag('event_subscriber');
......@@ -96,7 +107,8 @@ abstract class PackageManagerKernelTestBase extends KernelTestBase {
$this->container->get('file_system'),
$this->container->get('event_dispatcher'),
$this->container->get('tempstore.shared'),
$this->container->get('datetime.time')
$this->container->get('datetime.time'),
new TestPathFactory()
);
}
......@@ -284,6 +296,38 @@ trait TestStageTrait {
}
}
/**
* Defines a path value object that is aware of the virtual file system.
*/
class TestPath extends AbstractPath {
/**
* {@inheritdoc}
*/
protected function doResolve(string $basePath): string {
if (str_starts_with($this->path, vfsStream::SCHEME . '://')) {
return $this->path;
}
return implode(DIRECTORY_SEPARATOR, [$basePath, $this->path]);
}
}
/**
* Defines a path factory that is aware of the virtual file system.
*/
class TestPathFactory implements PathFactoryInterface {
/**
* {@inheritdoc}
*/
public static function create(string $path): PathInterface {
return new TestPath($path);
}
}
/**
* Defines a stage specifically for testing purposes.
*/
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment