class Cron in Drupal 9
Same name in this branch
- 9 core/lib/Drupal/Core/Cron.php \Drupal\Core\Cron
- 9 core/lib/Drupal/Core/ProxyClass/Cron.php \Drupal\Core\ProxyClass\Cron
Same name and namespace in other branches
- 8 core/lib/Drupal/Core/Cron.php \Drupal\Core\Cron
The Drupal core Cron service.
Hierarchy
- class \Drupal\Core\Cron implements CronInterface
Expanded class hierarchy of Cron
1 file declares its use of Cron
- CronTest.php in core/
tests/ Drupal/ Tests/ Core/ CronTest.php
8 string references to 'Cron'
- core.services.yml in core/
core.services.yml - core/core.services.yml
- MenuLinkTest::providerSource in core/
modules/ menu_link_content/ tests/ src/ Kernel/ Plugin/ migrate/ source/ MenuLinkTest.php - The data provider.
- router_test.routing.yml in core/
modules/ system/ tests/ modules/ router_test_directory/ router_test.routing.yml - core/modules/system/tests/modules/router_test_directory/router_test.routing.yml
- ShortcutCacheTagsTest::testToolbar in core/
modules/ shortcut/ tests/ src/ Functional/ ShortcutCacheTagsTest.php - Tests visibility and cacheability of shortcuts in the toolbar.
- ShortcutLinksTest::testAccessShortcutsPermission in core/
modules/ shortcut/ tests/ src/ Functional/ ShortcutLinksTest.php - Tests that the 'access shortcuts' permissions works properly.
1 service uses Cron
- cron in core/
core.services.yml - Drupal\Core\Cron
File
- core/
lib/ Drupal/ Core/ Cron.php, line 25
Namespace
Drupal\CoreView source
class Cron implements CronInterface {
/**
* The module handler service.
*
* @var \Drupal\Core\Extension\ModuleHandlerInterface
*/
protected $moduleHandler;
/**
* The lock service.
*
* @var \Drupal\Core\Lock\LockBackendInterface
*/
protected $lock;
/**
* The queue service.
*
* @var \Drupal\Core\Queue\QueueFactory
*/
protected $queueFactory;
/**
* The state service.
*
* @var \Drupal\Core\State\StateInterface
*/
protected $state;
/**
* The account switcher service.
*
* @var \Drupal\Core\Session\AccountSwitcherInterface
*/
protected $accountSwitcher;
/**
* A logger instance.
*
* @var \Psr\Log\LoggerInterface
*/
protected $logger;
/**
* The queue plugin manager.
*
* @var \Drupal\Core\Queue\QueueWorkerManagerInterface
*/
protected $queueManager;
/**
* The time service.
*
* @var \Drupal\Component\Datetime\TimeInterface
*/
protected $time;
/**
* Constructs a cron object.
*
* @param \Drupal\Core\Extension\ModuleHandlerInterface $module_handler
* The module handler
* @param \Drupal\Core\Lock\LockBackendInterface $lock
* The lock service.
* @param \Drupal\Core\Queue\QueueFactory $queue_factory
* The queue service.
* @param \Drupal\Core\State\StateInterface $state
* The state service.
* @param \Drupal\Core\Session\AccountSwitcherInterface $account_switcher
* The account switching service.
* @param \Psr\Log\LoggerInterface $logger
* A logger instance.
* @param \Drupal\Core\Queue\QueueWorkerManagerInterface $queue_manager
* The queue plugin manager.
* @param \Drupal\Component\Datetime\TimeInterface $time
* The time service.
*/
public function __construct(ModuleHandlerInterface $module_handler, LockBackendInterface $lock, QueueFactory $queue_factory, StateInterface $state, AccountSwitcherInterface $account_switcher, LoggerInterface $logger, QueueWorkerManagerInterface $queue_manager, TimeInterface $time = NULL) {
$this->moduleHandler = $module_handler;
$this->lock = $lock;
$this->queueFactory = $queue_factory;
$this->state = $state;
$this->accountSwitcher = $account_switcher;
$this->logger = $logger;
$this->queueManager = $queue_manager;
$this->time = $time ?: \Drupal::service('datetime.time');
}
/**
* {@inheritdoc}
*/
public function run() {
// Allow execution to continue even if the request gets cancelled.
@ignore_user_abort(TRUE);
// Force the current user to anonymous to ensure consistent permissions on
// cron runs.
$this->accountSwitcher
->switchTo(new AnonymousUserSession());
// Try to allocate enough time to run all the hook_cron implementations.
Environment::setTimeLimit(240);
$return = FALSE;
// Try to acquire cron lock.
if (!$this->lock
->acquire('cron', 900.0)) {
// Cron is still running normally.
$this->logger
->warning('Attempting to re-run cron while it is already running.');
}
else {
$this
->invokeCronHandlers();
$this
->setCronLastTime();
// Release cron lock.
$this->lock
->release('cron');
// Return TRUE so other functions can check if it did run successfully
$return = TRUE;
}
// Process cron queues.
$this
->processQueues();
// Restore the user.
$this->accountSwitcher
->switchBack();
return $return;
}
/**
* Records and logs the request time for this cron invocation.
*/
protected function setCronLastTime() {
// Record cron time.
$request_time = $this->time
->getRequestTime();
$this->state
->set('system.cron_last', $request_time);
$this->logger
->info('Cron run completed.');
}
/**
* Processes cron queues.
*/
protected function processQueues() {
// Grab the defined cron queues.
foreach ($this->queueManager
->getDefinitions() as $queue_name => $info) {
if (isset($info['cron'])) {
// Make sure every queue exists. There is no harm in trying to recreate
// an existing queue.
$this->queueFactory
->get($queue_name)
->createQueue();
$queue_worker = $this->queueManager
->createInstance($queue_name);
$end = time() + (isset($info['cron']['time']) ? $info['cron']['time'] : 15);
$queue = $this->queueFactory
->get($queue_name);
$lease_time = isset($info['cron']['time']) ?: NULL;
while (time() < $end && ($item = $queue
->claimItem($lease_time))) {
try {
$queue_worker
->processItem($item->data);
$queue
->deleteItem($item);
} catch (DelayedRequeueException $e) {
// The worker requested the task not be immediately re-queued.
// - If the queue doesn't support ::delayItem(), we should leave the
// item's current expiry time alone.
// - If the queue does support ::delayItem(), we should allow the
// queue to update the item's expiry using the requested delay.
if ($queue instanceof DelayableQueueInterface) {
// This queue can handle a custom delay; use the duration provided
// by the exception.
$queue
->delayItem($item, $e
->getDelay());
}
} catch (RequeueException $e) {
// The worker requested the task be immediately requeued.
$queue
->releaseItem($item);
} catch (SuspendQueueException $e) {
// If the worker indicates there is a problem with the whole queue,
// release the item and skip to the next queue.
$queue
->releaseItem($item);
watchdog_exception('cron', $e);
// Skip to the next queue.
continue 2;
} catch (\Exception $e) {
// In case of any other kind of exception, log it and leave the item
// in the queue to be processed again later.
watchdog_exception('cron', $e);
}
}
}
}
}
/**
* Invokes any cron handlers implementing hook_cron.
*/
protected function invokeCronHandlers() {
$module_previous = '';
// If detailed logging isn't enabled, don't log individual execution times.
$time_logging_enabled = \Drupal::config('system.cron')
->get('logging');
$logger = $time_logging_enabled ? $this->logger : new NullLogger();
// Iterate through the modules calling their cron handlers (if any):
foreach ($this->moduleHandler
->getImplementations('cron') as $module) {
if (!$module_previous) {
$logger
->info('Starting execution of @module_cron().', [
'@module' => $module,
]);
}
else {
$logger
->info('Starting execution of @module_cron(), execution of @module_previous_cron() took @time.', [
'@module' => $module,
'@module_previous' => $module_previous,
'@time' => Timer::read('cron_' . $module_previous) . 'ms',
]);
}
Timer::start('cron_' . $module);
// Do not let an exception thrown by one module disturb another.
try {
$this->moduleHandler
->invoke($module, 'cron');
} catch (\Exception $e) {
watchdog_exception('cron', $e);
}
Timer::stop('cron_' . $module);
$module_previous = $module;
}
if ($module_previous) {
$logger
->info('Execution of @module_previous_cron() took @time.', [
'@module_previous' => $module_previous,
'@time' => Timer::read('cron_' . $module_previous) . 'ms',
]);
}
}
}
Members
Name | Modifiers | Type | Description | Overrides |
---|---|---|---|---|
Cron:: |
protected | property | The account switcher service. | |
Cron:: |
protected | property | The lock service. | |
Cron:: |
protected | property | A logger instance. | |
Cron:: |
protected | property | The module handler service. | |
Cron:: |
protected | property | The queue service. | |
Cron:: |
protected | property | The queue plugin manager. | |
Cron:: |
protected | property | The state service. | |
Cron:: |
protected | property | The time service. | |
Cron:: |
protected | function | Invokes any cron handlers implementing hook_cron. | |
Cron:: |
protected | function | Processes cron queues. | |
Cron:: |
public | function |
Executes a cron run. Overrides CronInterface:: |
|
Cron:: |
protected | function | Records and logs the request time for this cron invocation. | |
Cron:: |
public | function | Constructs a cron object. |