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

Issue #3279086 by phenaproxima: StagedDatabaseUpdateValidatorTest should use a virtual project

parent 349ea640
No related branches found
No related tags found
No related merge requests found
{
"packages": [
{
"name": "drupal/core",
"version": "9.8.0"
}
]
}
......@@ -57,12 +57,27 @@ class FixtureStager implements EventSubscriberInterface {
* @see \Drupal\Tests\automatic_updates\Functional\AutomaticUpdatesFunctionalTestBase::tearDown()
*/
public function copyFilesFromFixture(PostRequireEvent $event): void {
$fixturePath = $this->state->get(static::class);
[$fixturePath, $changeLock] = $this->state->get(static::class);
if ($fixturePath && is_dir($fixturePath)) {
$this->fileSystem->mirror($fixturePath, $event->getStage()->getStageDirectory(), NULL, [
$destination = $event->getStage()->getStageDirectory();
$this->fileSystem->mirror($fixturePath, $destination, NULL, [
'override' => TRUE,
'delete' => TRUE,
]);
// Modify the lock file in the staging area, to simulate that a package
// was added, updated, or removed. Otherwise, tests must remember to
// disable the lock file validator.
// @see \Drupal\package_manager\Validator\LockFileValidator
$lock = $destination . '/composer.lock';
if ($changeLock && file_exists($lock)) {
$data = file_get_contents($lock);
$data = json_decode($data);
$data->_time = microtime();
file_put_contents($lock, json_encode($data, JSON_UNESCAPED_SLASHES | JSON_PRETTY_PRINT));
}
}
}
......@@ -80,9 +95,12 @@ class FixtureStager implements EventSubscriberInterface {
*
* @param string $path
* The path of the fixture to copy into the staging area.
* @param bool $change_lock
* (optional) Whether to change the lock file, in order to simulate the
* addition, updating, or removal of a package. Defaults to TRUE.
*/
public static function setFixturePath(string $path): void {
\Drupal::state()->set(static::class, $path);
public static function setFixturePath(string $path, bool $change_lock = TRUE): void {
\Drupal::state()->set(static::class, [$path, $change_lock]);
}
}
......@@ -2,12 +2,12 @@
namespace Drupal\Tests\package_manager\Kernel;
use Drupal\package_manager\Event\PostRequireEvent;
use Drupal\package_manager\Event\PreApplyEvent;
use Drupal\package_manager\Event\PreCreateEvent;
use Drupal\package_manager\Event\PreRequireEvent;
use Drupal\package_manager\Validator\LockFileValidator;
use Drupal\package_manager\ValidationResult;
use Drupal\package_manager_test_fixture\EventSubscriber\FixtureStager;
/**
* @coversDefaultClass \Drupal\package_manager\Validator\LockFileValidator
......@@ -56,7 +56,7 @@ class LockFileValidatorTest extends PackageManagerKernelTestBase {
// Change the lock file to ensure the stored hash of the previous version
// has been deleted.
file_put_contents($this->activeDir . '/composer.lock', 'changed');
file_put_contents($this->activeDir . '/composer.lock', '{"changed": true}');
$this->assertResults([]);
}
......@@ -124,11 +124,11 @@ class LockFileValidatorTest extends PackageManagerKernelTestBase {
* Tests validation when the staged and active lock files are identical.
*/
public function testApplyWithNoChange(): void {
$this->addListener(PostRequireEvent::class, function (PostRequireEvent $event) {
$stage_dir = $event->getStage()->getStageDirectory();
mkdir($stage_dir);
copy("$this->activeDir/composer.lock", "$stage_dir/composer.lock");
});
// Ensure the lock file is not changed when the active directory is copied
// into the virtual staging area.
// @see \Drupal\package_manager_test_fixture\EventSubscriber\FixtureStager
FixtureStager::setFixturePath($this->activeDir, FALSE);
$result = ValidationResult::createError([
'There are no pending Composer operations.',
]);
......
......@@ -10,6 +10,7 @@ use Drupal\package_manager\Exception\StageException;
use Drupal\package_manager\Exception\StageValidationException;
use Drupal\package_manager\PathLocator;
use Drupal\package_manager\Stage;
use Drupal\package_manager_test_fixture\EventSubscriber\FixtureStager;
use Drupal\Tests\package_manager\Traits\ValidationTestTrait;
use org\bovigo\vfs\vfsStream;
use org\bovigo\vfs\vfsStreamDirectory;
......@@ -29,6 +30,7 @@ abstract class PackageManagerKernelTestBase extends KernelTestBase {
protected static $modules = [
'package_manager',
'package_manager_bypass',
'package_manager_test_fixture',
];
/**
......@@ -188,7 +190,12 @@ abstract class PackageManagerKernelTestBase extends KernelTestBase {
$this->vfsRoot->addChild($stage_dir);
static::$testStagingRoot = $stage_dir->url();
$path_locator = $this->mockPathLocator($active_dir->url());
$active_dir = $active_dir->url();
$path_locator = $this->mockPathLocator($active_dir);
// Ensure that the active directory is copied into the virtual staging area,
// even if Package Manager's operations are bypassed.
FixtureStager::setFixturePath($active_dir);
// Since the path locator now points to a virtual file system, we need to
// replace the disk space validator with a test-only version that bypasses
......
......@@ -29,40 +29,37 @@ class StagedDatabaseUpdateValidatorTest extends AutomaticUpdatesKernelTestBase {
* {@inheritdoc}
*/
protected function setUp(): void {
// In this test, we want to disable the lock file validator because, even
// though both the active and stage directories will have a valid lock file,
// this validator will complain because they don't differ at all.
$this->disableValidators[] = 'package_manager.validator.lock_file';
parent::setUp();
static::$testStagingRoot = $this->vfsRoot->url();
$this->createTestProject();
/** @var \Drupal\Tests\automatic_updates\Kernel\TestCronUpdater $updater */
$updater = $this->container->get('automatic_updates.cron_updater');
$updater->begin(['drupal' => '9.8.2']);
$updater->stage();
}
$stage_dir = $updater->getStageDirectory();
mkdir($stage_dir);
/**
* {@inheritdoc}
*/
protected function createTestProject(): void {
parent::createTestProject();
// To satisfy StagedProjectsValidator, copy the active Composer files into
// the staging area.
$active_dir = $this->getDrupalRoot();
@copy("$active_dir/composer.json", "$stage_dir/composer.json");
@copy("$active_dir/composer.lock", "$stage_dir/composer.lock");
mkdir("$stage_dir/vendor/composer", 0777, TRUE);
@copy("$active_dir/vendor/composer/installed.json", "$stage_dir/vendor/composer/installed.json");
$drupal_root = $this->getDrupalRoot();
$virtual_active_dir = $this->container->get('package_manager.path_locator')
->getProjectRoot();
// Copy the .install and .post_update.php files from every installed module
// into the staging directory.
// Copy the .install and .post_update.php files from every installed module,
// in the *actual* Drupal code base that is running this test, into the
// virtual project (i.e., the active directory).
$module_list = $this->container->get('module_handler')->getModuleList();
foreach ($module_list as $name => $module) {
$path = $module->getPath();
@mkdir("$stage_dir/$path", 0777, TRUE);
@mkdir("$virtual_active_dir/$path", 0777, TRUE);
foreach (static::SUFFIXES as $suffix) {
// If the source file doesn't exist, silence the warning it raises.
@copy("$active_dir/$path/$name.$suffix", "$stage_dir/$path/$name.$suffix");
@copy("$drupal_root/$path/$name.$suffix", "$virtual_active_dir/$path/$name.$suffix");
}
}
}
......
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