diff --git a/core/core.services.yml b/core/core.services.yml index d72d30c..8775546 100644 --- a/core/core.services.yml +++ b/core/core.services.yml @@ -445,6 +445,9 @@ services: arguments: ['@database'] tags: - { name: backend_overridable } + lock.persistent: + class: Drupal\Core\Lock\PersistentDatabaseLockBackend + arguments: ['@database'] router.request_context: class: Symfony\Component\Routing\RequestContext tags: diff --git a/core/lib/Drupal/Core/Config/ConfigImporter.php b/core/lib/Drupal/Core/Config/ConfigImporter.php index b87c76d..5077ad4 100644 --- a/core/lib/Drupal/Core/Config/ConfigImporter.php +++ b/core/lib/Drupal/Core/Config/ConfigImporter.php @@ -1042,7 +1042,7 @@ public function alreadyImporting() { protected function reInjectMe() { $this->eventDispatcher = \Drupal::service('event_dispatcher'); $this->configManager = \Drupal::service('config.manager'); - $this->lock = \Drupal::lock(); + $this->lock = \Drupal::service('lock.persistent'); $this->typedConfigManager = \Drupal::service('config.typed'); $this->moduleHandler = \Drupal::moduleHandler(); $this->themeHandler = \Drupal::service('theme_handler'); diff --git a/core/lib/Drupal/Core/Lock/PersistentDatabaseLockBackend.php b/core/lib/Drupal/Core/Lock/PersistentDatabaseLockBackend.php new file mode 100644 index 0000000..f9c3945 --- /dev/null +++ b/core/lib/Drupal/Core/Lock/PersistentDatabaseLockBackend.php @@ -0,0 +1,34 @@ +database = $database; + // Set the lockId to a fixed string to make the lock ID the same across + // multiple requests. + $this->lockId = 'persistent'; + } +} diff --git a/core/modules/config/src/Form/ConfigSync.php b/core/modules/config/src/Form/ConfigSync.php index f73de96..56174aa 100644 --- a/core/modules/config/src/Form/ConfigSync.php +++ b/core/modules/config/src/Form/ConfigSync.php @@ -144,7 +144,7 @@ public static function create(ContainerInterface $container) { $container->get('config.storage.staging'), $container->get('config.storage'), $container->get('config.storage.snapshot'), - $container->get('lock'), + $container->get('lock.persistent'), $container->get('event_dispatcher'), $container->get('config.manager'), $container->get('url_generator'), diff --git a/core/modules/config/src/Tests/ConfigImportRenameValidationTest.php b/core/modules/config/src/Tests/ConfigImportRenameValidationTest.php index 60aab7f..fc0d0ed 100644 --- a/core/modules/config/src/Tests/ConfigImportRenameValidationTest.php +++ b/core/modules/config/src/Tests/ConfigImportRenameValidationTest.php @@ -55,7 +55,7 @@ protected function setUp() { $storage_comparer->createChangelist(), $this->container->get('event_dispatcher'), $this->container->get('config.manager'), - $this->container->get('lock'), + $this->container->get('lock.persistent'), $this->container->get('config.typed'), $this->container->get('module_handler'), $this->container->get('theme_handler'), diff --git a/core/modules/config/src/Tests/ConfigImportUITest.php b/core/modules/config/src/Tests/ConfigImportUITest.php index f5e4947..f0d9c02 100644 --- a/core/modules/config/src/Tests/ConfigImportUITest.php +++ b/core/modules/config/src/Tests/ConfigImportUITest.php @@ -227,14 +227,14 @@ function testImportLock() { // Acquire a fake-lock on the import mechanism. $config_importer = $this->configImporter(); - $this->container->get('lock')->acquire($config_importer::LOCK_ID); + $this->container->get('lock.persistent')->acquire($config_importer::LOCK_ID); // Attempt to import configuration and verify that an error message appears. $this->drupalPostForm(NULL, array(), t('Import all')); $this->assertText(t('Another request may be synchronizing configuration already.')); // Release the lock, just to keep testing sane. - $this->container->get('lock')->release($config_importer::LOCK_ID); + $this->container->get('lock.persistent')->release($config_importer::LOCK_ID); // Verify site name has not changed. $this->assertNotEqual($new_site_name, \Drupal::config('system.site')->get('name')); diff --git a/core/modules/config/src/Tests/ConfigImporterTest.php b/core/modules/config/src/Tests/ConfigImporterTest.php index e5e760e..b98a772 100644 --- a/core/modules/config/src/Tests/ConfigImporterTest.php +++ b/core/modules/config/src/Tests/ConfigImporterTest.php @@ -527,4 +527,3 @@ function testUpdated() { $this->assertEqual(count($logs), 0); } } - diff --git a/core/modules/system/src/Tests/Lock/LockFunctionalTest.php b/core/modules/system/src/Tests/Lock/LockFunctionalTest.php index 6b1518c..846b44d 100644 --- a/core/modules/system/src/Tests/Lock/LockFunctionalTest.php +++ b/core/modules/system/src/Tests/Lock/LockFunctionalTest.php @@ -59,4 +59,29 @@ public function testLockAcquire() { $this->assertText($lock_acquired_exit, 'Lock acquired by the other request before exit.', 'Lock'); $this->assertTrue($lock->acquire('system_test_lock_exit'), 'Lock acquired by this request after the other request exits.', 'Lock'); } + + /** + * Tests that the persistent lock is persisted between requests. + */ + public function testPersistentLock() { + $persistent_lock = $this->container->get('lock.persistent'); + // Get a persistent lock. + $this->drupalGet('system-test/lock-persist/lock1'); + $this->assertText('TRUE: Lock successfully acquired in SystemTestController::lockPersist()'); + // Ensure that a shutdown function has not released the lock. + $this->assertFalse($persistent_lock->lockMayBeAvailable('lock1')); + $this->drupalGet('system-test/lock-persist/lock1'); + $this->assertText('FALSE: Lock not acquired in SystemTestController::lockPersist()'); + + // Get another persistent lock. + $this->drupalGet('system-test/lock-persist/lock2'); + $this->assertText('TRUE: Lock successfully acquired in SystemTestController::lockPersist()'); + $this->assertFalse($persistent_lock->lockMayBeAvailable('lock2')); + + // Release the first lock and try getting it again. + $persistent_lock->release('lock1'); + $this->drupalGet('system-test/lock-persist/lock1'); + $this->assertText('TRUE: Lock successfully acquired in SystemTestController::lockPersist()'); + } + } diff --git a/core/modules/system/tests/modules/system_test/src/Controller/SystemTestController.php b/core/modules/system/tests/modules/system_test/src/Controller/SystemTestController.php index 0b9290b..70da955 100644 --- a/core/modules/system/tests/modules/system_test/src/Controller/SystemTestController.php +++ b/core/modules/system/tests/modules/system_test/src/Controller/SystemTestController.php @@ -8,6 +8,8 @@ namespace Drupal\system_test\Controller; use Drupal\Core\Controller\ControllerBase; +use Drupal\Core\Lock\LockBackendInterface; +use Symfony\Component\DependencyInjection\ContainerInterface; /** * Controller routines for system_test routes. @@ -15,6 +17,30 @@ class SystemTestController extends ControllerBase { /** + * The persistent lock service. + * + * @var \Drupal\Core\Lock\LockBackendInterface + */ + protected $persistentLock; + + /** + * Constructs the SystemTestController. + * + * @param \Drupal\Core\Lock\LockBackendInterface $persistent_lock + * The persistent lock service. + */ + public function __construct(LockBackendInterface $persistent_lock) { + $this->persistentLock = $persistent_lock; + } + + /** + * {@inheritdoc} + */ + public static function create(ContainerInterface $container) { + return new static($container->get('lock.persistent')); + } + + /** * Tests main content fallback. * * @return string @@ -39,6 +65,24 @@ public function lockExit() { } /** + * Creates a lock that will persist across requests. + * + * @param string $lock_name + * The name of the persistent lock to acquire. + * + * @return string + * The text to display. + */ + public function lockPersist($lock_name) { + if ($this->persistentLock->acquire($lock_name)) { + return 'TRUE: Lock successfully acquired in SystemTestController::lockPersist()'; + } + else { + return 'FALSE: Lock not acquired in SystemTestController::lockPersist()'; + } + } + + /** * Set cache tag on on the returned render array. */ public function system_test_cache_tags_page() { diff --git a/core/modules/system/tests/modules/system_test/system_test.routing.yml b/core/modules/system/tests/modules/system_test/system_test.routing.yml index 520ba37..f025995 100644 --- a/core/modules/system/tests/modules/system_test/system_test.routing.yml +++ b/core/modules/system/tests/modules/system_test/system_test.routing.yml @@ -45,6 +45,14 @@ system_test.lock_exit: requirements: _access: 'TRUE' +system_test.lock_persist: + path: '/system-test/lock-persist/{lock_name}' + defaults: + _title: 'Persistent lock acquire' + _content: '\Drupal\system_test\Controller\SystemTestController::lockPersist' + requirements: + _access: 'TRUE' + system_test.cache_tags_page: path: '/system-test/cache_tags_page' defaults: