diff --git a/README.md b/README.md index f1a85865..24951f2d 100644 --- a/README.md +++ b/README.md @@ -13,8 +13,7 @@ Dotkernel web starter package suitable for frontend applications. [![Continuous Integration](https://github.com/dotkernel/frontend/actions/workflows/continuous-integration.yml/badge.svg?branch=5.0)](https://github.com/dotkernel/frontend/actions/workflows/continuous-integration.yml) [![codecov](https://codecov.io/gh/dotkernel/frontend/graph/badge.svg?token=BQS43UWAM4)](https://codecov.io/gh/dotkernel/frontend) [![Qodana](https://github.com/dotkernel/frontend/actions/workflows/qodana_code_quality.yml/badge.svg)](https://github.com/dotkernel/frontend/actions/workflows/qodana_code_quality.yml) - -[![SymfonyInsight](https://insight.symfony.com/projects/a28dac55-3366-4020-9a49-53f6fcbeda4e/big.svg)](https://insight.symfony.com/projects/a28dac55-3366-4020-9a49-53f6fcbeda4e) +[![PHPStan](https://github.com/dotkernel/frontend/actions/workflows/static-analysis.yml/badge.svg?branch=5.0)](https://github.com/dotkernel/frontend/actions/workflows/static-analysis.yml) ## Installing DotKernel `frontend` diff --git a/composer.json b/composer.json index fcb02e3e..103f783a 100644 --- a/composer.json +++ b/composer.json @@ -78,8 +78,11 @@ "mezzio/mezzio-tooling": "^2.9.0", "phpunit/phpunit": "^10.5", "roave/security-advisories": "dev-master", - "vimeo/psalm": "^5.21.1", - "vincentlanglet/twig-cs-fixer": "^2.12" + "vincentlanglet/twig-cs-fixer": "^2.12", + "phpstan/phpstan": "^2.0", + "phpstan/phpstan-doctrine": "^2.0", + "phpstan/phpstan-phpunit": "^2.0", + "symfony/var-dumper": "^7.1" }, "autoload": { "psr-4": { @@ -107,13 +110,14 @@ "mezzio": "mezzio --ansi", "check": [ "@cs-check", - "@test" + "@test", + "@static-analysis" ], "clear-config-cache": "php bin/clear-config-cache.php", "cs-check": "phpcs", "cs-fix": "phpcbf", "serve": "php -S 0.0.0.0:8080 -t public/", - "static-analysis": "psalm --shepherd --stats", + "static-analysis": "phpstan analyse", "test": "phpunit --colors=always", "test-coverage": "phpunit --colors=always --coverage-clover clover.xml", "twig-cs-check": "vendor/bin/twig-cs-fixer lint --config=config/twig-cs-fixer.php", diff --git a/phpstan.neon b/phpstan.neon new file mode 100644 index 00000000..96ced513 --- /dev/null +++ b/phpstan.neon @@ -0,0 +1,21 @@ +includes: + - vendor/phpstan/phpstan-doctrine/extension.neon + - vendor/phpstan/phpstan-phpunit/extension.neon +parameters: + level: 5 + paths: + - src + - test + treatPhpDocTypesAsCertain: false + ignoreErrors: + - '/Parameter #1 \$expected of method PHPUnit\\Framework\\Assert::assertSame\(\) contains unresolvable type\./' + - + message: '#Call to method PHPUnit\\Framework\\Assert::assertInstanceOf\(\) with .* will always evaluate to true.#' + path: test + - + message: '#Call to an undefined method Laminas\\InputFilter\\InputFilterInterface::getInputs\(\)#' + path: test + - + message: '#Call to an undefined method Laminas\\Authentication\\AuthenticationServiceInterface::getStorage\(\)#' + path: src/App/src/Middleware/RememberMeMiddleware.php + diff --git a/psalm-baseline.xml b/psalm-baseline.xml deleted file mode 100644 index e8a04843..00000000 --- a/psalm-baseline.xml +++ /dev/null @@ -1,19 +0,0 @@ - - - - - getStorage - getStorage - - - - - getCookieSameSite - - - - - iterable - - - diff --git a/psalm.xml b/psalm.xml deleted file mode 100644 index ed4c186a..00000000 --- a/psalm.xml +++ /dev/null @@ -1,17 +0,0 @@ - - - - - - - - - diff --git a/src/App/src/Service/CookieService.php b/src/App/src/Service/CookieService.php index 2fc0def1..dacced87 100644 --- a/src/App/src/Service/CookieService.php +++ b/src/App/src/Service/CookieService.php @@ -6,6 +6,7 @@ use Dot\DependencyInjection\Attribute\Inject; use Laminas\Session\Config\ConfigInterface; +use Laminas\Session\Config\SameSiteCookieCapableInterface; use Laminas\Session\SessionManager; use function setcookie; @@ -13,7 +14,7 @@ class CookieService implements CookieServiceInterface { - private ConfigInterface $sessionConfig; + private ConfigInterface|SameSiteCookieCapableInterface $sessionConfig; #[Inject(SessionManager::class)] public function __construct(SessionManager $sessionManager) diff --git a/src/Contact/src/Service/MessageService.php b/src/Contact/src/Service/MessageService.php index 4847a42d..006faee9 100644 --- a/src/Contact/src/Service/MessageService.php +++ b/src/Contact/src/Service/MessageService.php @@ -4,7 +4,6 @@ namespace Frontend\Contact\Service; -use Doctrine\ORM\EntityRepository; use Dot\DependencyInjection\Attribute\Inject; use Dot\Mail\Service\MailServiceInterface; use Frontend\Contact\Entity\Message; @@ -28,7 +27,7 @@ public function __construct( ) { } - public function getRepository(): MessageRepository|EntityRepository + public function getRepository(): MessageRepository { return $this->repository; } diff --git a/src/Plugin/src/PluginManager.php b/src/Plugin/src/PluginManager.php index d634f32a..4dc68a63 100644 --- a/src/Plugin/src/PluginManager.php +++ b/src/Plugin/src/PluginManager.php @@ -11,6 +11,6 @@ */ class PluginManager extends AbstractPluginManager { - /** @var string $instanceOf */ + /** @var class-string|null $instanceOf */ protected $instanceOf = PluginInterface::class; } diff --git a/src/User/src/Service/UserService.php b/src/User/src/Service/UserService.php index b32d79cb..93c85720 100644 --- a/src/User/src/Service/UserService.php +++ b/src/User/src/Service/UserService.php @@ -275,7 +275,7 @@ public function sendActivationMail(User $user): bool return $this->mailService->send()->isValid(); } - public function findOneBy(array $params = []): ?UserInterface + public function findOneBy(array $params = []): ?User { if (empty($params)) { return null; @@ -344,7 +344,7 @@ public function getRepository(): UserRepository /** * @throws Exception */ - public function addRememberMeToken(UserInterface|User $user, string $userAgent, array $cookies = []): void + public function addRememberMeToken(User $user, string $userAgent, array $cookies = []): void { $this->deleteExpiredRememberMeTokens(); diff --git a/src/User/src/Service/UserServiceInterface.php b/src/User/src/Service/UserServiceInterface.php index ae181dea..4eaf646d 100644 --- a/src/User/src/Service/UserServiceInterface.php +++ b/src/User/src/Service/UserServiceInterface.php @@ -18,7 +18,7 @@ public function createUser(array $data): UserInterface; */ public function sendActivationMail(User $user): bool; - public function findOneBy(array $params = []): ?UserInterface; + public function findOneBy(array $params = []): ?User; public function activateUser(User $user): User; @@ -26,7 +26,7 @@ public function findByUuid(string $uuid): ?User; public function getRepository(): UserRepository; - public function addRememberMeToken(UserInterface|User $user, string $userAgent, array $cookies = []): void; + public function addRememberMeToken(User $user, string $userAgent, array $cookies = []): void; public function deleteRememberMeToken(array $cookies = []): void; diff --git a/test/Unit/App/Middleware/RememberMeMiddlewareTest.php b/test/Unit/App/Middleware/RememberMeMiddlewareTest.php index 8bd96fc6..97c0975c 100644 --- a/test/Unit/App/Middleware/RememberMeMiddlewareTest.php +++ b/test/Unit/App/Middleware/RememberMeMiddlewareTest.php @@ -17,15 +17,16 @@ use Laminas\Authentication\AuthenticationService; use Laminas\Authentication\Exception\ExceptionInterface; use PHPUnit\Framework\MockObject\Exception; +use PHPUnit\Framework\MockObject\MockObject; use PHPUnit\Framework\TestCase; use Psr\Http\Message\ServerRequestInterface; use Psr\Http\Server\RequestHandlerInterface; class RememberMeMiddlewareTest extends TestCase { - private ServerRequestInterface $request; + private ServerRequestInterface|MockObject $request; - private RequestHandlerInterface $handler; + private RequestHandlerInterface|MockObject $handler; /** * @throws Exception diff --git a/test/Unit/Plugin/FormsPluginTest.php b/test/Unit/Plugin/FormsPluginTest.php index 4a64dd07..1fbc1361 100644 --- a/test/Unit/Plugin/FormsPluginTest.php +++ b/test/Unit/Plugin/FormsPluginTest.php @@ -37,6 +37,7 @@ public function testWillRestoreState(): void { $hash = (new Csrf(['session' => new Container()]))->getHash(); + /** @var array $oldData */ $oldData = [ 'identity' => 'old@identity.com', 'password' => 'old-password', @@ -155,7 +156,7 @@ public function testWillGetMessages(): void $this->assertNotEmpty($messagesAsString); } - private function getDummyFlashMessenger(): FlashMessengerInterface + private function getDummyFlashMessenger(): object { return new class implements FlashMessengerInterface { private array $data = [];