Skip to content

Commit

Permalink
Fix debug classes and add more tests (#224)
Browse files Browse the repository at this point in the history
  • Loading branch information
vjik authored Nov 9, 2023
1 parent 2a4f200 commit 0892cbe
Show file tree
Hide file tree
Showing 7 changed files with 186 additions and 35 deletions.
11 changes: 4 additions & 7 deletions src/Debug/DebugRoutesCommand.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,6 @@
use Yiisoft\VarDumper\VarDumper;
use Yiisoft\Yii\Debug\Debugger;

/**
* @codeCoverageIgnore
*/
final class DebugRoutesCommand extends Command
{
public const COMMAND_NAME = 'debug:routes';
Expand Down Expand Up @@ -55,8 +52,8 @@ protected function execute(InputInterface $input, OutputInterface $output): int
$data = $route->__debugInfo();
$action = '';
$middlewares = [];
if (!empty($data['middlewareDefinitions'])) {
$middlewareDefinitions = $data['middlewareDefinitions'];
if (!empty($data['enabledMiddlewares'])) {
$middlewareDefinitions = $data['enabledMiddlewares'];
$action = array_pop($middlewareDefinitions);
$middlewares = $middlewareDefinitions;
}
Expand Down Expand Up @@ -94,8 +91,8 @@ protected function execute(InputInterface $input, OutputInterface $output): int
foreach ($this->routeCollection->getRoutes() as $route) {
$data = $route->__debugInfo();
$action = '';
if (!empty($data['middlewareDefinitions'])) {
$middlewareDefinitions = $data['middlewareDefinitions'];
if (!empty($data['enabledMiddlewares'])) {
$middlewareDefinitions = $data['enabledMiddlewares'];
$action = array_pop($middlewareDefinitions);
}
$rows[] = [
Expand Down
16 changes: 4 additions & 12 deletions src/Debug/RouterCollector.php
Original file line number Diff line number Diff line change
Expand Up @@ -12,9 +12,6 @@
use Yiisoft\Yii\Debug\Collector\CollectorTrait;
use Yiisoft\Yii\Debug\Collector\SummaryCollectorInterface;

/**
* @codeCoverageIgnore
*/
final class RouterCollector implements SummaryCollectorInterface
{
use CollectorTrait;
Expand Down Expand Up @@ -134,15 +131,10 @@ private function getMiddlewaresAndAction(?Route $route): array
if ($route === null) {
return [[], null];
}
$reflection = new ReflectionObject($route);

$reflectionProperty = $reflection->getProperty('middlewareDefinitions');
$reflectionProperty->setAccessible(true);
/**
* @var array[]|callable[]|string[] $middlewareDefinitions
*/
$middlewareDefinitions = $reflectionProperty->getValue($route);
$action = array_pop($middlewareDefinitions);
return [$middlewareDefinitions, $action];
$middlewares = $route->getData('enabledMiddlewares');
$action = array_pop($middlewares);

return [$middlewares, $action];
}
}
9 changes: 4 additions & 5 deletions src/Debug/UrlMatcherInterfaceProxy.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,13 +8,12 @@
use Yiisoft\Router\MatchingResult;
use Yiisoft\Router\UrlMatcherInterface;

/**
* @codeCoverageIgnore
*/
final class UrlMatcherInterfaceProxy implements UrlMatcherInterface
{
public function __construct(private UrlMatcherInterface $urlMatcher, private RouterCollector $routerCollector)
{
public function __construct(
private UrlMatcherInterface $urlMatcher,
private RouterCollector $routerCollector
) {
}

public function match(ServerRequestInterface $request): MatchingResult
Expand Down
80 changes: 69 additions & 11 deletions tests/Debug/DebugRoutesCommandTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,26 +7,84 @@
use PHPUnit\Framework\TestCase;
use Symfony\Component\Console\Tester\CommandTester;
use Yiisoft\Router\Debug\DebugRoutesCommand;
use Yiisoft\Router\RouteCollectionInterface;
use Yiisoft\Router\Route;
use Yiisoft\Router\RouteCollection;
use Yiisoft\Router\RouteCollector;
use Yiisoft\Router\Tests\Support\TestController;
use Yiisoft\Router\Tests\Support\TestMiddleware1;
use Yiisoft\Yii\Debug\Debugger;
use Yiisoft\Yii\Debug\DebuggerIdGenerator;
use Yiisoft\Yii\Debug\Storage\StorageInterface;
use Yiisoft\Yii\Debug\Storage\MemoryStorage;

final class DebugRoutesCommandTest extends TestCase
{
public function testCommand()
public function testBase(): void
{
$routeCollection = $this->createMock(RouteCollectionInterface::class);
$routeCollection->method('getRoutes')->willReturn([]);
$idGenerator = new DebuggerIdGenerator();
$storage = $this->createMock(StorageInterface::class);
$storage->expects($this->never())->method('clear');
$debugger = new Debugger($idGenerator, $storage, []);
$debuggerIdGenerator = new DebuggerIdGenerator();

$command = new DebugRoutesCommand($routeCollection, $debugger);
$command = new DebugRoutesCommand(
new RouteCollection(
(new RouteCollector())->addRoute(
Route::get('/')
->host('example.com')
->defaults(['SpecialArg' => 1])
->action(fn () => 'Hello, XXXXXX!')
->name('site/index'),
Route::get('/about')
->action([TestController::class, 'index'])
->name('site/about'),
),
),
new Debugger(
$debuggerIdGenerator,
new MemoryStorage($debuggerIdGenerator),
[],
),
);

$commandTester = new CommandTester($command);

$commandTester->execute([]);
$output = $commandTester->getDisplay();

$this->assertStringContainsString('site/index', $output);
$this->assertStringContainsString('SpecialArg', $output);
$this->assertStringContainsString('example.com', $output);
$this->assertStringContainsString('XXXXXX', $output);
$this->assertStringContainsString('site/about', $output);
$this->assertStringContainsString(TestController::class . '::index', $output);
}

public function testSpecificRoute(): void
{
$debuggerIdGenerator = new DebuggerIdGenerator();

$command = new DebugRoutesCommand(
new RouteCollection(
(new RouteCollector())->addRoute(
Route::get('/')
->host('example.com')
->defaults(['SpecialArg' => 1])
->name('site/index')
->middleware(TestMiddleware1::class)
->action(fn () => 'Hello world!'),
Route::get('/about')->name('site/about'),
),
),
new Debugger(
$debuggerIdGenerator,
new MemoryStorage($debuggerIdGenerator),
[],
),
);

$commandTester = new CommandTester($command);
$commandTester->execute(['route' => ['site/index']]);
$output = $commandTester->getDisplay();

$this->assertStringContainsString('site/index', $output);
$this->assertStringContainsString('TestMiddleware1', $output);
$this->assertStringContainsString('SpecialArg', $output);
$this->assertStringContainsString('example.com', $output);
$this->assertStringNotContainsString('site/about', $output);
}
}
39 changes: 39 additions & 0 deletions tests/Debug/RouterCollectorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,14 +7,17 @@
use PHPUnit\Framework\MockObject\MockObject;
use Yiisoft\Di\Container;
use Yiisoft\Di\ContainerConfig;
use Yiisoft\Router\CurrentRoute;
use Yiisoft\Router\Debug\RouterCollector;
use Yiisoft\Router\Group;
use Yiisoft\Router\MatchingResult;
use Yiisoft\Router\Route;
use Yiisoft\Router\RouteCollection;
use Yiisoft\Router\RouteCollectionInterface;
use Yiisoft\Router\RouteCollector;
use Yiisoft\Router\RouteCollectorInterface;
use Yiisoft\Router\UrlMatcherInterface;
use Yiisoft\Test\Support\Container\SimpleContainer;
use Yiisoft\Yii\Debug\Collector\CollectorInterface;
use Yiisoft\Yii\Debug\Tests\Shared\AbstractCollectorTestCase;

Expand All @@ -24,6 +27,42 @@ final class RouterCollectorTest extends AbstractCollectorTestCase

private ?Container $container = null;

public function testWithoutCurrentRoute(): void
{
$collector = new RouterCollector(
new SimpleContainer()
);
$collector->startup();

$summary = $collector->getSummary();

$this->assertNull($summary['router']);
}

public function testWithoutRouteCollection(): void
{
$route = Route::get('/');
$arguments = ['a' => 19];
$result = MatchingResult::fromSuccess($route, $arguments);

$currentRoute = new CurrentRoute();
$currentRoute->setRouteWithArguments($result->route(), $result->arguments());
$collector = new RouterCollector(
new SimpleContainer([
CurrentRoute::class => $currentRoute,
])
);
$collector->startup();

$collected = $collector->getCollected();

$this->assertSame(['currentRoute'], array_keys($collected));
$this->assertSame(
['matchTime', 'name', 'pattern', 'arguments', 'host', 'uri', 'action', 'middlewares'],
array_keys($collected['currentRoute'])
);
}

/**
* @param CollectorInterface|RouterCollector $collector
*/
Expand Down
44 changes: 44 additions & 0 deletions tests/Debug/UrlMatcherInterfaceProxyTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
<?php

declare(strict_types=1);

namespace Yiisoft\Router\Tests\Debug;

use Nyholm\Psr7\ServerRequest;
use PHPUnit\Framework\TestCase;
use Yiisoft\Router\CurrentRoute;
use Yiisoft\Router\Debug\RouterCollector;
use Yiisoft\Router\Debug\UrlMatcherInterfaceProxy;
use Yiisoft\Router\MatchingResult;
use Yiisoft\Router\Route;
use Yiisoft\Router\Tests\Support\UrlMatcherStub;
use Yiisoft\Test\Support\Container\SimpleContainer;

final class UrlMatcherInterfaceProxyTest extends TestCase
{
public function testBase(): void
{
$request = new ServerRequest('GET', '/');
$route = Route::get('/');
$arguments = ['a' => 19];
$result = MatchingResult::fromSuccess($route, $arguments);

$currentRoute = new CurrentRoute();
$currentRoute->setRouteWithArguments($result->route(), $result->arguments());

$collector = new RouterCollector(
new SimpleContainer([
CurrentRoute::class => $currentRoute,
])
);
$collector->startup();

$proxy = new UrlMatcherInterfaceProxy(new UrlMatcherStub($result), $collector);

$proxyResult = $proxy->match($request);
$summary = $collector->getSummary();

$this->assertSame($result, $proxyResult);
$this->assertGreaterThan(0, $summary['router']['matchTime']);
}
}
22 changes: 22 additions & 0 deletions tests/Support/UrlMatcherStub.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
<?php

declare(strict_types=1);

namespace Yiisoft\Router\Tests\Support;

use Psr\Http\Message\ServerRequestInterface;
use Yiisoft\Router\MatchingResult;
use Yiisoft\Router\UrlMatcherInterface;

final class UrlMatcherStub implements UrlMatcherInterface
{
public function __construct(
private MatchingResult $result
) {
}

public function match(ServerRequestInterface $request): MatchingResult
{
return $this->result;
}
}

0 comments on commit 0892cbe

Please sign in to comment.