Skip to content

Commit

Permalink
Added verbose mode and timeout to cache generation
Browse files Browse the repository at this point in the history
  • Loading branch information
bencroker committed Mar 19, 2024
1 parent 4a4d1b5 commit 097dfc0
Show file tree
Hide file tree
Showing 7 changed files with 84 additions and 31 deletions.
3 changes: 3 additions & 0 deletions CHANGELOG.md
Expand Up @@ -6,12 +6,15 @@

- Added batchable generate cache jobs ([#537](https://github.com/putyourlightson/craft-blitz/issues/537)).
- Added a new `injectScriptPosition` config setting that determines the position in the HTML in which to output the injected script ([#636](https://github.com/putyourlightson/craft-blitz/issues/636)).
- Added a verbose output mode to `blitz/cache` console commands that can be activated by adding a `--verbose` flag ([#642](https://github.com/putyourlightson/craft-blitz/issues/642)).
- Added a default timeout of 60 seconds to the Local Generator.

### Changed

- Campaign now requires Craft CMS 4.4.0 or later.
- The Local Generator now uses the `bootstrap.php` file in the project root, if it exists.
- The Local Generator now sets the server port according to the HTTP protocol.
- Changed the default timeout of the HTTP Generator to 60 seconds.

### Fixed

Expand Down
2 changes: 2 additions & 0 deletions src/Blitz.php
Expand Up @@ -195,6 +195,8 @@ public function debug(string $message, array $params = [], string $url = ''): vo
$message = Craft::t('blitz', $message, $params);

if ($url) {
$tokenParam = Craft::$app->getConfig()->getGeneral()->tokenParam;
$url = preg_replace('/[?&]' . $tokenParam . '.*/', '', $url);
$message .= ' [' . $url . ']';
}

Expand Down
25 changes: 20 additions & 5 deletions src/console/controllers/CacheController.php
Expand Up @@ -18,17 +18,23 @@
class CacheController extends Controller
{
/**
* @var bool Whether jobs should be queued only and not run
* @var bool Whether jobs should be only queued and not run.
*/
public bool $queue = false;

/**
* @var bool Whether verbose output should be enabled.
*/
public bool $verbose = false;

/**
* @inheritdoc
*/
public function options($actionID): array
{
$options = parent::options($actionID);
$options[] = 'queue';
$options[] = 'verbose';

return $options;
}
Expand Down Expand Up @@ -431,7 +437,9 @@ public function actionGenerateExpiryDates(): int
*/
public function setProgressHandler(int $count, int $total): void
{
Console::updateProgress($count, $total);
if ($this->verbose === false) {
Console::updateProgress($count, $total);
}
}

private function clearCache(array $siteUris = null): void
Expand Down Expand Up @@ -514,15 +522,22 @@ private function generateCache(array $siteUris): void

$this->stdout(Craft::t('blitz', 'Generating Blitz cache...') . PHP_EOL, BaseConsole::FG_YELLOW);

Console::startProgress(0, count($siteUris), '', 0.8);
if ($this->verbose === false) {
Console::startProgress(0, count($siteUris), '', 0.8);
}

Blitz::$plugin->cacheGenerator->verbose = $this->verbose;
Blitz::$plugin->cacheGenerator->generateUris($siteUris, [$this, 'setProgressHandler'], false);
Console::endProgress();

if ($this->verbose === false) {
Console::endProgress();
}

$generated = Blitz::$plugin->cacheGenerator->generated;
$total = count($siteUris);

if ($generated < $total) {
$this->stdout(Craft::t('blitz', 'Generated {generated} of {total} total possible pages and includes. To see why some pages were not cached, enable the `debug` config setting and then open the `storage/logs/blitz.log` file.', ['generated' => $generated, 'total' => $total]) . PHP_EOL, BaseConsole::FG_CYAN);
$this->stdout(Craft::t('blitz', 'Generated {generated} of {total} total possible pages and includes. To see why some pages were not cached, enable the `debug` config setting or use the `debug` flag and then open the Blitz log (in `storage/logs/blitz-****.log`, for example).', ['generated' => $generated, 'total' => $total]) . PHP_EOL, BaseConsole::FG_CYAN);
}

$this->output('Blitz cache generation complete.');
Expand Down
31 changes: 26 additions & 5 deletions src/drivers/generators/BaseCacheGenerator.php
Expand Up @@ -8,13 +8,15 @@
use Amp\MultiReasonException;
use Craft;
use craft\base\SavableComponent;
use craft\helpers\Console;
use putyourlightson\blitz\Blitz;
use putyourlightson\blitz\events\RefreshCacheEvent;
use putyourlightson\blitz\helpers\CacheGeneratorHelper;
use putyourlightson\blitz\helpers\SiteUriHelper;
use putyourlightson\blitz\models\SiteUriModel;
use putyourlightson\blitz\services\CacheRequestService;
use Throwable;
use yii\helpers\BaseConsole;

/**
* @property-read array $siteOptions
Expand Down Expand Up @@ -71,10 +73,15 @@ abstract class BaseCacheGenerator extends SavableComponent implements CacheGener
*/
public const GENERATE_ACTION_ROUTE = 'blitz/generator/generate';

/**
* @var bool Whether to output verbose messages.
*/
public bool $verbose = false;

/**
* @inheritdoc
*/
public function generateUris(array $siteUris, callable $setProgressHandler = null, bool $queue = true): void
public function generateUris(array $siteUris, callable $setProgressHandler = null, bool $queue = true, bool $verbose = false): void
{
$event = new RefreshCacheEvent(['siteUris' => $siteUris]);
$this->trigger(self::EVENT_BEFORE_GENERATE_CACHE, $event);
Expand Down Expand Up @@ -108,7 +115,7 @@ public function generateUrisWithProgress(array $siteUris, callable $setProgressH
/**
* @inheritdoc
*/
public function generateSite(int $siteId, callable $setProgressHandler = null, bool $queue = true): void
public function generateSite(int $siteId, callable $setProgressHandler = null, bool $queue = true, bool $verbose = false): void
{
// Get custom site URIs for the provided site only
$groupedSiteUris = SiteUriHelper::getSiteUrisGroupedBySite(Blitz::$plugin->settings->getCustomSiteUris());
Expand All @@ -119,13 +126,13 @@ public function generateSite(int $siteId, callable $setProgressHandler = null, b
$customSiteUris
);

$this->generateUris($siteUris, $setProgressHandler, $queue);
$this->generateUris($siteUris, $setProgressHandler, $queue, $verbose);
}

/**
* @inheritdoc
*/
public function generateAll(callable $setProgressHandler = null, bool $queue = true): void
public function generateAll(callable $setProgressHandler = null, bool $queue = true, bool $verbose = false): void
{
$event = new RefreshCacheEvent();
$this->trigger(self::EVENT_BEFORE_GENERATE_ALL_CACHE, $event);
Expand All @@ -139,7 +146,7 @@ public function generateAll(callable $setProgressHandler = null, bool $queue = t
Blitz::$plugin->settings->getCustomSiteUris()
);

$this->generateUris($siteUris, $setProgressHandler, $queue);
$this->generateUris($siteUris, $setProgressHandler, $queue, $verbose);

if ($this->hasEventHandlers(self::EVENT_AFTER_GENERATE_ALL_CACHE)) {
$this->trigger(self::EVENT_AFTER_GENERATE_ALL_CACHE, $event);
Expand Down Expand Up @@ -235,4 +242,18 @@ protected function isPageUrl(string $url): bool
{
return !str_contains($url, CacheRequestService::CACHED_INCLUDE_PATH . '?action=' . CacheRequestService::CACHED_INCLUDE_ACTION);
}

protected function outputVerbose(string $url, bool $success = true): void
{
if (Craft::$app->getRequest()->getIsConsoleRequest() && $this->verbose) {
$tokenParam = Craft::$app->getConfig()->getGeneral()->tokenParam;
$url = preg_replace('/[?&]' . $tokenParam . '.*/', '', $url);

if ($success) {
Console::stdout($url . PHP_EOL);
} else {
Console::stdout($url . PHP_EOL, BaseConsole::FG_RED);
}
}
}
}
8 changes: 5 additions & 3 deletions src/drivers/generators/HttpGenerator.php
Expand Up @@ -12,7 +12,6 @@
use Craft;
use putyourlightson\blitz\Blitz;
use Throwable;
use yii\log\Logger;

use function Amp\Iterator\fromIterable;
use function Amp\Promise\wait;
Expand All @@ -39,7 +38,7 @@ class HttpGenerator extends BaseCacheGenerator
/**
* @var int The timeout for requests in milliseconds.
*/
public int $timeout = 120000;
public int $timeout = 60000;

/**
* @inheritdoc
Expand Down Expand Up @@ -76,18 +75,21 @@ function(string $url) use ($setProgressHandler, &$count, $total, $client) {

if ($response->getStatus() === 200) {
$this->generated++;
$this->outputVerbose($url);
} else {
Blitz::$plugin->debug('{status} error: {reason}', [
'status' => $response->getStatus(),
'reason' => $response->getReason(),
], $url);
$this->outputVerbose($url, false);
}

if (is_callable($setProgressHandler)) {
$this->callProgressHandler($setProgressHandler, $count, $total);
}
} catch (HttpException $exception) {
Blitz::$plugin->log($exception->getMessage() . ' [' . $url . ']', [], Logger::LEVEL_ERROR);
Blitz::$plugin->debug($exception->getMessage());
$this->outputVerbose($url, false);
}
}
);
Expand Down
31 changes: 27 additions & 4 deletions src/drivers/generators/LocalGenerator.php
Expand Up @@ -6,6 +6,7 @@
namespace putyourlightson\blitz\drivers\generators;

use Amp\Sync\LocalSemaphore;
use Amp\TimeoutCancellationToken;
use Craft;
use putyourlightson\blitz\Blitz;
use Throwable;
Expand Down Expand Up @@ -39,10 +40,9 @@ class LocalGenerator extends BaseCacheGenerator
public int $concurrency = 3;

/**
* @var int The timeout for requests in milliseconds. This has no effect
* except to prevent errors when the cache generator config setting exists.
* @var int The timeout for requests in milliseconds.
*/
public int $timeout = 0;
public int $timeout = 60000;

/**
* @inheritdoc
Expand Down Expand Up @@ -82,12 +82,35 @@ function(string $url) use ($setProgressHandler, &$count, $total, $config) {
// Create a context to send data between the parent and child processes
// https://amphp.org/parallel/processes#parent-process
$context = create(__DIR__ . '/local-generator-script.php');

// Create and subscribe a timeout.
$canceller = new TimeoutCancellationToken($this->timeout);
$cancellerId = $canceller->subscribe(function() use ($url, $context) {
$message = 'Local generator request timed out.';
Blitz::$plugin->debug($message, [], $url);
$this->outputVerbose($url, false);

$context->kill();
});

yield $context->start();
yield $context->send($config);
$result = yield $context->receive();

try {
$result = yield $context->receive();
} catch (Throwable $exception) {
Blitz::$plugin->debug($this->getAllExceptionMessages($exception), [], $url);
$result = false;
}

// Unsubscribe the timeout.
$canceller->unsubscribe($cancellerId);

if ($result) {
$this->generated++;
$this->outputVerbose($url);
} else {
$this->outputVerbose($url, false);
}

if (is_callable($setProgressHandler)) {
Expand Down
15 changes: 1 addition & 14 deletions src/drivers/generators/local-generator-script.php
Expand Up @@ -4,12 +4,9 @@
*/

use Amp\Parallel\Sync\Channel;
use Amp\Parallel\Sync\ContextPanicError;
use craft\services\Plugins;
use craft\web\View;
use putyourlightson\blitz\Blitz;
use yii\base\Event;
use yii\log\Logger;

/**
* This script bootstraps a web app and mocks a web request. It is called by the
Expand Down Expand Up @@ -102,17 +99,7 @@ function() {
*/
$app = require $root . '/vendor/craftcms/cms/bootstrap/web.php';

try {
$success = $app->run() == 0;
} catch (ContextPanicError $error) {
Blitz::$plugin->log($error->getMessage());
Blitz::$plugin->log($error->getTraceAsString());
Blitz::$plugin->log($error->getOriginalTraceAsString());
$success = 1;
} catch (Throwable $exception) {
Blitz::$plugin->log($exception->getMessage(), [], Logger::LEVEL_ERROR);
$success = 1;
}
$success = $app->run() === 0;

yield $channel->send($success);
};

0 comments on commit 097dfc0

Please sign in to comment.