Skip to content

Commit

Permalink
Merge pull request #590 from FriendsOfSymfony/phpstan-levels
Browse files Browse the repository at this point in the history
Phpstan levels
  • Loading branch information
dbu authored Jan 3, 2025
2 parents 5fb0c38 + 50de1fa commit eed7738
Show file tree
Hide file tree
Showing 19 changed files with 92 additions and 59 deletions.
29 changes: 2 additions & 27 deletions .github/workflows/static.yml
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,15 @@ on:

jobs:
phpstan-src:
name: PHPStan src
name: PHPStan
runs-on: ubuntu-latest

steps:
- name: Checkout code
uses: actions/checkout@v4

- name: Pull in optional dependencies
run: composer require --no-update phpunit/phpunit toflar/psr6-symfony-http-cache-store:^4.2 symfony/process
run: composer require --no-update phpunit/phpunit toflar/psr6-symfony-http-cache-store:^4.2 symfony/process mockery/mockery phpstan/phpstan-mockery guzzlehttp/guzzle php-http/mock-client

- name: Cache Vendor
id: cache-vendor
Expand All @@ -30,31 +30,6 @@ jobs:
with:
args: analyze --no-progress

phpstan-tests:
name: PHPStan tests
runs-on: ubuntu-latest
env:
REQUIRE_DEV: "true"

steps:
- name: Checkout code
uses: actions/checkout@v4

- name: Pull in optional dependencies
run: composer require --no-update phpunit/phpunit toflar/psr6-symfony-http-cache-store:^4.2

- name: Cache Vendor
id: cache-vendor
uses: actions/cache@v4
with:
path: vendor
key: ${{ runner.os }}-vendor

- name: PHPStan
uses: docker://oskarstark/phpstan-ga
with:
args: analyze --no-progress -c phpstan.tests.neon.dist

php-cs-fixer:
name: PHP-CS-Fixer
runs-on: ubuntu-latest
Expand Down
2 changes: 1 addition & 1 deletion doc/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -154,5 +154,5 @@ doctest:
"results in $(BUILDDIR)/doctest/output.txt."

spelling:
$(SPHINXBUILD) -b spelling $(ALLSPHINXOPTS) -w $(BUILDDIR)/spelling/output.txt $(BUILDDIR)/spelling
$(SPHINXBUILD) -b spelling $(ALLSPHINXOPTS) -w $(BUILDDIR)/spelling/output.txt $(BUILDDIR)/spelling
@echo "Spelling report generated in $(BUILDDIR)/spelling/output.txt"
5 changes: 4 additions & 1 deletion phpstan.neon.dist
Original file line number Diff line number Diff line change
@@ -1,4 +1,7 @@
parameters:
level: 1
level: 4
paths:
- src
- tests

treatPhpDocTypesAsCertain: false
4 changes: 0 additions & 4 deletions phpstan.tests.neon.dist

This file was deleted.

16 changes: 3 additions & 13 deletions src/ProxyClient/Cloudflare.php
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ public function invalidateTags(array $tags): static
sprintf(self::API_ENDPOINT.'/zones/%s/purge_cache', $this->options['zone_identifier']),
[],
false,
$this->json_encode(['tags' => $tags])
json_encode(['tags' => $tags], JSON_THROW_ON_ERROR | JSON_UNESCAPED_SLASHES)
);

return $this;
Expand Down Expand Up @@ -115,7 +115,7 @@ public function clear(): static
sprintf(self::API_ENDPOINT.'/zones/%s/purge_cache', $this->options['zone_identifier']),
['Accept' => 'application/json'],
false,
$this->json_encode(['purge_everything' => true])
json_encode(['purge_everything' => true], JSON_THROW_ON_ERROR | JSON_UNESCAPED_SLASHES)
);

return $this;
Expand All @@ -130,7 +130,7 @@ public function flush(): int
sprintf(self::API_ENDPOINT.'/zones/%s/purge_cache', $this->options['zone_identifier']),
[],
false,
$this->json_encode(['files' => $urlChunk])
json_encode(['files' => $urlChunk], JSON_THROW_ON_ERROR | JSON_UNESCAPED_SLASHES)
);
}
$this->purgeByUrlsData = [];
Expand Down Expand Up @@ -165,14 +165,4 @@ protected function configureOptions(): OptionsResolver

return $resolver;
}

private function json_encode(array $data): string
{
$json = json_encode($data, JSON_THROW_ON_ERROR | JSON_UNESCAPED_SLASHES);
if (false === $json) {
throw new \InvalidArgumentException(sprintf('Cannot encode "$data": %s', json_last_error_msg()));
}

return $json;
}
}
6 changes: 4 additions & 2 deletions src/ProxyClient/MultiplexerClient.php
Original file line number Diff line number Diff line change
Expand Up @@ -133,7 +133,7 @@ public function clear(): static
* Invoke the given $method on all available ProxyClients implementing the
* given $interface.
*
* @param string $interface The FQN of the interface
* @param class-string $interface The FQN of the interface
* @param string $method The method to invoke
* @param array<mixed> $arguments The arguments to be passed to the method
*/
Expand All @@ -155,7 +155,9 @@ private function getProxyClients(string $interface): array
{
return array_filter(
$this->proxyClients,
static function ($proxyClient) use ($interface) {
static function (ProxyClient $proxyClient) use ($interface) {
// https://github.com/phpstan/phpstan/issues/8464
// @phpstan-ignore-next-line
return is_subclass_of($proxyClient, $interface);
}
);
Expand Down
2 changes: 1 addition & 1 deletion src/SymfonyCache/PurgeTagsListener.php
Original file line number Diff line number Diff line change
Expand Up @@ -118,7 +118,7 @@ public function handlePurgeTags(CacheEvent $event): void
if (1 === $reflection->getMethod('all')->getNumberOfParameters()) {
$headers = $request->headers->all($this->tagsHeader);
} else {
$headers = $request->headers->get($this->tagsHeader, '', false);
$headers = $request->headers->get($this->tagsHeader, '');
}

$tags = $this->tagsParser->parseTagsHeaderValue($headers);
Expand Down
6 changes: 4 additions & 2 deletions src/Test/EventDispatchingHttpCacheTestCase.php
Original file line number Diff line number Diff line change
Expand Up @@ -251,6 +251,7 @@ public function testPreStoreResponseNoStore()
$httpCache = $this->getHttpCachePartialMock();
$testListener = new TestListener($this, $httpCache, $request);
$testListener->preStoreResponse = $preStoreResponse;
$this->assertTrue(method_exists($httpCache, 'addSubscriber'));
$httpCache->addSubscriber($testListener);

$store = $this->createMock(StoreInterface::class);
Expand Down Expand Up @@ -279,8 +280,8 @@ public function testPreInvalidateCalled(): void

$httpCache = $this->getHttpCachePartialMock(['pass']);
$testListener = new TestListener($this, $httpCache, $request);
$httpCache->addSubscriber($testListener);
$this->assertTrue(method_exists($httpCache, 'addSubscriber'));
$httpCache->addSubscriber($testListener);
$httpCache
->method('pass')
->with($request)
Expand All @@ -307,8 +308,8 @@ public function testPreInvalidateReturnEarly(): void
$httpCache = $this->getHttpCachePartialMock(['pass']);
$testListener = new TestListener($this, $httpCache, $request);
$testListener->preInvalidateResponse = $response;
$httpCache->addSubscriber($testListener);
$this->assertTrue(method_exists($httpCache, 'addSubscriber'));
$httpCache->addSubscriber($testListener);
$httpCache
->expects($this->never())
->method('pass')
Expand All @@ -327,6 +328,7 @@ public function testAddListener(): void

$httpCache = $this->getHttpCachePartialMock(['lookup']);
$simpleListener = new SimpleListener($this, $httpCache, $request);
$this->assertTrue(method_exists($httpCache, 'addListener'));
$httpCache->addListener(Events::PRE_HANDLE, [$simpleListener, 'callback']);

$httpCache
Expand Down
5 changes: 1 addition & 4 deletions src/Test/WebServerSubscriber.php
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@

namespace FOS\HttpCache\Test;

use PHPUnit\Event\Code\TestMethod;
use PHPUnit\Event\TestRunner\ExecutionStarted;
use PHPUnit\Event\TestRunner\ExecutionStartedSubscriber;
use PHPUnit\Event\TestSuite\TestSuite;
Expand Down Expand Up @@ -52,8 +51,6 @@ private function hasTestsWithGroup(TestSuite $testSuite, string $group): bool
continue;
}

assert($test instanceof TestMethod);

foreach ($test->metadata()->isGroup() as $testGroup) {
assert($testGroup instanceof Group);

Expand Down Expand Up @@ -83,7 +80,7 @@ public function startPhpWebServer(): int

$this->waitFor($this->getHostName(), (int) $this->getPort(), 2000);

return $output[0];
return (int) $output[0];
}

public function getHostName(): string
Expand Down
4 changes: 2 additions & 2 deletions tests/Functional/ProxyClient/NginxProxyClientTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ public function testPurgeContentType(): void
{
$this->markTestSkipped('Not working with nginx, it can only purge one type');

$this->assertPurgeContentType($this->getProxyClient());
// $this->assertPurgeContentType($this->getProxyClient());
}

public function testPurgeSeparateLocationHost(): void
Expand All @@ -57,6 +57,6 @@ public function testRefreshContentType(): void
{
$this->markTestSkipped('TODO: is nginx mixing up variants?');

$this->assertRefreshContentType($this->getProxyClient());
// $this->assertRefreshContentType($this->getProxyClient());
}
}
2 changes: 2 additions & 0 deletions tests/Functional/Symfony/EventDispatchingHttpCacheTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ public function testEventListeners(): void
->shouldReceive('handle')
->andReturn($expectedResponse)
->getMock();
// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$store = \Mockery::mock(StoreInterface::class)
->shouldReceive('lookup')->andReturn(null)->times(1)
->shouldReceive('write')->times(1)
Expand Down
8 changes: 8 additions & 0 deletions tests/Unit/CacheInvalidatorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,8 @@ public function testSupportsInvalid(): void
public function testInvalidatePath(): void
{
/** @var MockInterface&PurgeCapable $purge */
// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$purge = \Mockery::mock(PurgeCapable::class)
->shouldReceive('purge')->once()->with('/my/route', [])
->shouldReceive('purge')->once()->with('/my/route', ['X-Test-Header' => 'xyz'])
Expand All @@ -97,6 +99,8 @@ public function testRefreshPath(): void
{
$headers = ['X' => 'Y'];
/** @var MockInterface&RefreshCapable $refresh */
// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$refresh = \Mockery::mock(RefreshCapable::class)
->shouldReceive('refresh')->once()->with('/my/route', $headers)
->shouldReceive('flush')->never()
Expand Down Expand Up @@ -190,6 +194,8 @@ public function testProxyClientExceptionsAreLogged(): void

$unreachableException = ProxyUnreachableException::proxyUnreachable($clientException);

// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$response = \Mockery::mock(ResponseInterface::class)
->shouldReceive('getStatusCode')->andReturn(403)
->shouldReceive('getReasonPhrase')->andReturn('Forbidden')
Expand All @@ -206,6 +212,8 @@ public function testProxyClientExceptionsAreLogged(): void

$cacheInvalidator = new CacheInvalidator($proxyClient);

// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$logger = \Mockery::mock(LoggerInterface::class)
->shouldReceive('log')->once()
->with(
Expand Down
6 changes: 6 additions & 0 deletions tests/Unit/ResponseTaggerTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,8 @@ public function testGetTagsHeaderValue(): void

public function testTagResponseReplace(): void
{
// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$headerFormatter = \Mockery::mock(TagHeaderFormatter::class)
->shouldReceive('getTagsHeaderValue')
->with(['tag-1', 'tag-2'])
Expand All @@ -73,6 +75,8 @@ public function testTagResponseReplace(): void

public function testTagResponseAdd(): void
{
// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$headerFormatter = \Mockery::mock(TagHeaderFormatter::class)
->shouldReceive('getTagsHeaderValue')
->with(['tag-1', 'tag-2'])
Expand Down Expand Up @@ -105,6 +109,8 @@ public function testTagResponseNoTags(): void

$tagger = new ResponseTagger(['header_formatter' => $headerFormatter]);

// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$response = \Mockery::mock(ResponseInterface::class)
->shouldReceive('withHeader')->never()
->shouldReceive('withAddedHeader')->never()
Expand Down
39 changes: 39 additions & 0 deletions tests/Unit/SymfonyCache/CacheAwareTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
<?php

/*
* This file is part of the FOSHttpCache package.
*
* (c) FriendsOfSymfony <http://friendsofsymfony.github.com/>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/

namespace FOS\HttpCache\Tests\Unit\SymfonyCache;

use FOS\HttpCache\SymfonyCache\HttpCacheAware;
use FOS\HttpCache\SymfonyCache\HttpCacheProvider;
use PHPUnit\Framework\TestCase;
use Symfony\Component\HttpKernel\HttpKernelInterface;

class CacheAwareTest extends TestCase
{
private HttpKernelInterface $cacheKernel;

protected function setUp(): void
{
$this->cacheKernel = $this->createMock(HttpKernelInterface::class);
}

public function testCacheGetterSetter(): void
{
$aware = new AppHttpCacheAware();
$aware->setHttpCache($this->cacheKernel);
$this->assertSame($this->cacheKernel, $aware->getHttpCache());
}
}

class AppHttpCacheAware implements HttpCacheProvider
{
use HttpCacheAware;
}
3 changes: 1 addition & 2 deletions tests/Unit/SymfonyCache/KernelDispatcherTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,7 @@ public function testFlush(): void
->with($this->callback(function (Request $request) {
// Test if the Symfony request contains the relevant information
// from the PSR-7 request
$valid = true;
$valid = $valid && 'PURGETAGS' === $request->getMethod();
$valid = 'PURGETAGS' === $request->getMethod();
$valid = $valid && 'foobar' === $request->headers->get('content-type');
$valid = $valid && 'foo,bar,stuff' === $request->headers->get('x-cache-tags');
$valid = $valid && ['query' => 'string', 'more' => 'stuff'] === $request->query->all();
Expand Down
4 changes: 4 additions & 0 deletions tests/Unit/SymfonyCache/PurgeListenerTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,8 @@ public function testInvalidConfiguration(): void

private function getKernelMock(StoreInterface $store): MockInterface&CacheInvalidation
{
// https://github.com/phpstan/phpstan-mockery/issues/8
/* @phpstan-ignore-next-line */
return \Mockery::mock(CacheInvalidation::class)
->shouldReceive('getStore')
->once()
Expand All @@ -196,6 +198,8 @@ private function getKernelMock(StoreInterface $store): MockInterface&CacheInvali

private function getUnusedKernelMock(): CacheInvalidation&MockInterface
{
// https://github.com/phpstan/phpstan-mockery/issues/8
/* @phpstan-ignore-next-line */
return \Mockery::mock(CacheInvalidation::class)
->shouldNotReceive('getStore')
->getMock();
Expand Down
4 changes: 4 additions & 0 deletions tests/Unit/SymfonyCache/PurgeTagsListenerTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,8 @@ public function testInvalidConfiguration(): void

private function getKernelMock(StoreInterface $store): CacheInvalidation&MockInterface
{
// https://github.com/phpstan/phpstan-mockery/issues/8
/* @phpstan-ignore-next-line */
return \Mockery::mock(CacheInvalidation::class)
->shouldReceive('getStore')
->once()
Expand All @@ -189,6 +191,8 @@ private function getKernelMock(StoreInterface $store): CacheInvalidation&MockInt

private function getUnusedKernelMock(): CacheInvalidation&MockInterface
{
// https://github.com/phpstan/phpstan-mockery/issues/8
/* @phpstan-ignore-next-line */
return \Mockery::mock(CacheInvalidation::class)
->shouldNotReceive('getStore')
->getMock();
Expand Down
4 changes: 4 additions & 0 deletions tests/Unit/Test/PHPUnit/IsCacheHitConstraintTestCase.php
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@ public function setUp(): void

public function testMatches(): void
{
// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$response = $this->getResponseMock()
->shouldReceive('hasHeader')->with('cache-header')->andReturn(true)
->shouldReceive('getHeaderLine')->with('cache-header')->once()->andReturn('MISS')
Expand All @@ -44,6 +46,8 @@ public function testMatchesThrowsExceptionIfHeaderIsMissing(): void
$this->expectException(\RuntimeException::class);
$this->expectExceptionMessage('Response has no "cache-header" header');

// https://github.com/phpstan/phpstan-mockery/issues/8
/** @phpstan-ignore-next-line */
$response = $this->getResponseMock()
->shouldReceive('hasHeader')->with('cache-header')->once()->andReturn(false)
->shouldReceive('getStatusCode')->andReturn(200)
Expand Down
Loading

0 comments on commit eed7738

Please sign in to comment.