RoundingWell 最重要的系統之一是評估引擎,或者我們通常所說的「評估」。該系統負責處理特定於客戶的配置事件偵聽器,這使我們能夠為每個組織提供高度獨特的使用者體驗。不用說,這個系統對我們的應用程式非常重要,並且能夠準確地知道它對於給定事件做了什麼,或將要做什麼至關重要。
今天,我正在努力將我們的一位客戶從一些舊事件過渡到較新的事件,並且需要確保其中一個步驟能夠正確處理事件。我們有很多關於評估的日誌記錄,我知道我需要的資訊就在日誌中。但擁有大量日誌記錄的問題是,有很多日誌。另外,我只需要運行每個觸發器的第一部分來驗證遷移是否有效。
我心想,「如果我們能為評估引擎提供一個類似 Xdebug 的單步調試器,這不是很聰明嗎?我知道 Symfony Console 擁有我需要的所有功能......」
而這正是我所做的。因為我們的應用程式是完全依賴注入的,所以我能夠創建一個新類別來包裝 StepFactory,它負責讀取配置並創建構成評估的「步驟」。
use RoundingWell\Framework\DebugVar; use RuntimeException; use Symfony\Component\Console\Style\SymfonyStyle; readonly class StepFactoryWithConsoleConfirmation implements StepFactory { public function __construct( private StepFactory $stepFactory, private SymfonyStyle $style, private bool $confirmCreatedStep = true, private bool $showCreatedStep = true, private bool $showStepDefinition = false, ) { } public function create(object $subject, StepDefinition $definition): Step { if ($this->showStepDefinition) { $debug = new DebugVar($definition->parameters); $this->style->info( message: <<<TEXT Next step is $definition->name with parameters: $debug TEXT, ); } $step = $this->stepFactory->create($subject, $definition); if ($this->showCreatedStep) { $debug = new DebugVar($step); $this->style->info( message: <<<TEXT Step $definition->name created as: $debug TEXT, ); } if ($this->confirmCreatedStep && ! $this->style->confirm(question: "Continue with evaluation?")) { throw new RuntimeException( message: "Evaluation aborted at step {$definition->name}", ); } return $step; } }
並且,透過我的控制台命令中的一些容器操作,我們有一個互動式評估偵錯器:
use DI\Container; use RoundingWell\Common\Command\CommandBus; use RoundingWell\Common\Command\CommandBusComposed; use RoundingWell\Common\Command\Middleware\LoggingMiddleware; use RoundingWell\Evaluation\Command\EvaluateEvent; use RoundingWell\Evaluation\Command\EvaluateEventHandler; use RoundingWell\Evaluation\Step\StepFactory; use RoundingWell\Evaluation\Step\StepFactoryWithConsoleConfirmation; use Symfony\Component\Console\Style\SymfonyStyle; readonly class EvaluationDebug { public function __construct( private Container $container, ) { } public function __invoke( SymfonyStyle $symfonyStyle, string $eventType, string $eventId, string|null $evaluationId = null, ): void { // The command bus MUST ONLY log executed commands. $commandBus = new CommandBusComposed( $this->container->get(LoggingMiddleware::class), ); // The step factory MUST be wrapped to step through the evaluation. $stepFactory = new StepFactoryWithConsoleConfirmation( stepFactory: $this->container->get(StepFactory::class), style: $symfonyStyle, ); $this->container->set(CommandBus::class, $commandBus); $this->container->set(StepFactory::class, $stepFactory); $command = new EvaluateEvent( eventClass: $eventType, eventId: $eventId, evaluationId: $evaluationId, ); $this->container->get(EvaluateEventHandler::class)->handle($command); $symfonyStyle->success('Evaluation complete'); } }
今天就這樣!
以上是使用 Symfony Console 進行互動式調試的詳細內容。更多資訊請關注PHP中文網其他相關文章!