From 47897cc4bf5d448e204dedb0e28ee2a4ff9995a7 Mon Sep 17 00:00:00 2001 From: Sergei Predvoditelev Date: Sat, 31 Oct 2026 10:12:32 +0300 Subject: [PATCH 1/2] Switch to infection/infection --- .github/workflows/mutation.yml | 3 ++- composer.json | 2 +- docs/internals.md | 5 ++--- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/.github/workflows/mutation.yml b/.github/workflows/mutation.yml index fafafa4..fc1822c 100644 --- a/.github/workflows/mutation.yml +++ b/.github/workflows/mutation.yml @@ -22,12 +22,13 @@ concurrency: jobs: mutation: - uses: yiisoft/actions/.github/workflows/roave-infection.yml@master + uses: yiisoft/actions/.github/workflows/infection.yml@master with: min-covered-msi: 100 os: >- ['ubuntu-latest'] php: >- ['8.3'] + infection-args: --ignore-msi-with-no-mutations secrets: STRYKER_DASHBOARD_API_KEY: ${{ secrets.STRYKER_DASHBOARD_API_KEY }} diff --git a/composer.json b/composer.json index 0fc8872..b91b340 100644 --- a/composer.json +++ b/composer.json @@ -41,9 +41,9 @@ "bamarni/composer-bin-plugin": "^1.9.1", "friendsofphp/php-cs-fixer": "^3.95", "httpsoft/http-message": "^1.1.6", + "infection/infection": "^0.26.6 || ^0.27.10 || ^0.29.8 || ^0.35.8", "phpunit/phpunit": "^9.6.22", "rector/rector": "^2.5.8", - "roave/infection-static-analysis-plugin": "^1.25", "shipmonk/composer-dependency-analyser": "^1.8", "spatie/phpunit-watcher": "^1.23.6", "vimeo/psalm": "^4.30 || ^5.26.1 || ^6.9.1", diff --git a/docs/internals.md b/docs/internals.md index b77907c..f486439 100644 --- a/docs/internals.md +++ b/docs/internals.md @@ -10,11 +10,10 @@ The package is tested with [PHPUnit](https://phpunit.de/). To run tests: ## Mutation testing -The package tests are checked with [Infection](https://infection.github.io/) mutation framework with -[Infection Static Analysis Plugin](https://github.com/Roave/infection-static-analysis-plugin). To run it: +The package tests are checked with [Infection](https://infection.github.io/) mutation framework. To run it: ```shell -./vendor/bin/roave-infection-static-analysis-plugin +./vendor/bin/infection ``` ## Static analysis From dc5e6b9de660572f8ecd8b98dcefaa60e359921a Mon Sep 17 00:00:00 2001 From: Sergei Predvoditelev Date: Mon, 2 Nov 2026 11:09:12 +0300 Subject: [PATCH 2/2] more tests --- .../ConfigurationExceptionTest.php | 40 +++++++++++++++++++ .../ProcessTest.php | 37 +++++++++++++++++ 2 files changed, 77 insertions(+) diff --git a/tests/TrustedHostsNetworkResolver/ConfigurationExceptionTest.php b/tests/TrustedHostsNetworkResolver/ConfigurationExceptionTest.php index c9d8392..bd709bb 100644 --- a/tests/TrustedHostsNetworkResolver/ConfigurationExceptionTest.php +++ b/tests/TrustedHostsNetworkResolver/ConfigurationExceptionTest.php @@ -349,6 +349,46 @@ public function dataWithForwardedHeaderGroupsException(): array 'Value in mapping for protocol header must be a valid protocol. Allowed values are: "http", "https" ' . '(case-sensitive).', ], + 'protocol, array, resolving: array, value is not a string' => [ + [ + TrustedHostsNetworkResolver::FORWARDED_HEADER_RFC, + [ + 'ip' => 'y-forwarded-for', + 'protocol' => [ + 'y-forwarded-proto', + [ + 'on1' => 'https', + 'on2' => 1, + 'on3' => 'https', + ], + ], + 'host' => 'y-forwarded-host', + 'port' => 'y-forwarded-port', + ], + TrustedHostsNetworkResolver::FORWARDED_HEADER_GROUP_X_PREFIX, + ], + 'Value in mapping for protocol header must be non-empty string.', + ], + 'protocol, array, resolving: array, value is an empty string' => [ + [ + TrustedHostsNetworkResolver::FORWARDED_HEADER_RFC, + [ + 'ip' => 'y-forwarded-for', + 'protocol' => [ + 'y-forwarded-proto', + [ + 'on1' => 'https', + 'on2' => '', + 'on3' => 'https', + ], + ], + 'host' => 'y-forwarded-host', + 'port' => 'y-forwarded-port', + ], + TrustedHostsNetworkResolver::FORWARDED_HEADER_GROUP_X_PREFIX, + ], + 'Value in mapping for protocol header must be non-empty string.', + ], ]; } diff --git a/tests/TrustedHostsNetworkResolver/ProcessTest.php b/tests/TrustedHostsNetworkResolver/ProcessTest.php index 202757c..d1d0825 100644 --- a/tests/TrustedHostsNetworkResolver/ProcessTest.php +++ b/tests/TrustedHostsNetworkResolver/ProcessTest.php @@ -1529,4 +1529,41 @@ public function testProcess( $this->assertSame($expectedData['host'] ?? '', $uri->getHost()); $this->assertSame($expectedData['port'] ?? null, $uri->getPort()); } + + public function testRemoteAddrNotSetResetsConnectionChainItemsAttribute(): void + { + $middleware = $this + ->createMiddleware() + ->withTrustedIps(['8.8.8.8']) + ->withConnectionChainItemsAttribute('connectionChainItems'); + $request = $this + ->createRequest() + ->withAttribute('connectionChainItems', ['test']); + $requestHandler = new MockRequestHandler(); + + $middleware->process($request, $requestHandler); + + $processedRequest = $requestHandler->processedRequest; + $this->assertNull($processedRequest->getAttribute('connectionChainItems', 'not-null')); + $this->assertNull( + $processedRequest->getAttribute(TrustedHostsNetworkResolver::ATTRIBUTE_REQUEST_CLIENT_IP, 'not-null'), + ); + } + + public function testRemoteAddrNotSetWithoutConnectionChainItemsAttribute(): void + { + $middleware = $this + ->createMiddleware() + ->withTrustedIps(['8.8.8.8']); + $request = $this->createRequest(); + $requestHandler = new MockRequestHandler(); + + $response = $middleware->process($request, $requestHandler); + + $this->assertSame(Status::OK, $response->getStatusCode()); + $this->assertSame( + [TrustedHostsNetworkResolver::ATTRIBUTE_REQUEST_CLIENT_IP => null], + $requestHandler->processedRequest->getAttributes(), + ); + } }