From 790aed3e980f15b1546e74fc5620169d02e236f6 Mon Sep 17 00:00:00 2001 From: AntonV1211 Date: Tue, 26 May 2026 14:34:30 +0700 Subject: [PATCH 1/2] Fix. Code. Checking server settings --- RemoteCalls.php | 26 +++++++++- .../RemoteCalls/RemoteCallsGetSiteUrlTest.php | 47 +++++++++++++++++++ 2 files changed, 71 insertions(+), 2 deletions(-) create mode 100644 tests/RemoteCalls/RemoteCallsGetSiteUrlTest.php diff --git a/RemoteCalls.php b/RemoteCalls.php index 084a673..8c1bea1 100644 --- a/RemoteCalls.php +++ b/RemoteCalls.php @@ -165,7 +165,30 @@ protected function setLastCall($action) public static function getSiteUrl() { - return (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? "https" : "http") . "://" . $_SERVER['HTTP_HOST'] . (isset($_SERVER['SCRIPT_URL']) ? $_SERVER['SCRIPT_URL'] : ''); + $scheme = ( + isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' + ? 'https' + : 'http' + ); + + $host = isset($_SERVER['HTTP_HOST']) ? $_SERVER['HTTP_HOST'] : ''; + $host = preg_replace('/[^A-Za-z0-9.\-:]/', '', $host); + + $path = ''; + if ( isset($_SERVER['SCRIPT_URL']) ) { + $path = $_SERVER['SCRIPT_URL']; + } elseif ( isset($_SERVER['REQUEST_URI']) ) { + $path = parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH); + } + + $path = $path ? (string)$path : ''; + $path = preg_replace('/[\x00-\x1F\x7F]/', '', $path); + $path = preg_replace('/[^A-Za-z0-9\-._~\/]/', '', $path); + if ( $path !== '' && $path[0] !== '/' ) { + $path = '/' . $path; + } + + return $scheme . '://' . $host . $path; } public static function buildParameters($rc_action, $plugin_name, $api_key, $additional_params) @@ -183,7 +206,6 @@ public static function buildParameters($rc_action, $plugin_name, $api_key, $addi /** * Performs remote call to the current website * - * @param string $host * @param string $rc_action * @param string $plugin_name * @param string $api_key diff --git a/tests/RemoteCalls/RemoteCallsGetSiteUrlTest.php b/tests/RemoteCalls/RemoteCallsGetSiteUrlTest.php new file mode 100644 index 0000000..e1e5beb --- /dev/null +++ b/tests/RemoteCalls/RemoteCallsGetSiteUrlTest.php @@ -0,0 +1,47 @@ +server_backup = $_SERVER; + } + + public function tearDown(): void + { + $_SERVER = $this->server_backup; + } + + public function testGetSiteUrlSanitizesScriptUrl() + { + $_SERVER['HTTPS'] = 'on'; + $_SERVER['HTTP_HOST'] = 'example.com'; + $_SERVER['SCRIPT_URL'] = '/'; + + $result = RemoteCalls::getSiteUrl(); + + self::assertSame('https://example.com/imgsrcxonerroralert1', $result); + self::assertStringNotContainsString('<', $result); + self::assertStringNotContainsString('>', $result); + self::assertStringNotContainsString('"', $result); + self::assertStringNotContainsString("'", $result); + } + + public function testGetSiteUrlFallsBackToRequestUri() + { + unset($_SERVER['SCRIPT_URL']); + $_SERVER['HTTP_HOST'] = 'example.com'; + $_SERVER['REQUEST_URI'] = '/path/to/page?x='; + + $result = RemoteCalls::getSiteUrl(); + + self::assertSame('http://example.com/path/to/page', $result); + } +} From 6bb3cfe6a3c62e75acf389db05c7194155b74fe4 Mon Sep 17 00:00:00 2001 From: AntonV1211 Date: Thu, 28 May 2026 15:51:22 +0700 Subject: [PATCH 2/2] Fix. Code. Normalization edit for ipv6, taking into account % and unit tests --- RemoteCalls.php | 8 +++++-- .../RemoteCalls/RemoteCallsGetSiteUrlTest.php | 22 +++++++++++++++++++ 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/RemoteCalls.php b/RemoteCalls.php index 8c1bea1..c69c59f 100644 --- a/RemoteCalls.php +++ b/RemoteCalls.php @@ -172,7 +172,7 @@ public static function getSiteUrl() ); $host = isset($_SERVER['HTTP_HOST']) ? $_SERVER['HTTP_HOST'] : ''; - $host = preg_replace('/[^A-Za-z0-9.\-:]/', '', $host); + $host = preg_replace('/[^A-Za-z0-9.\-:\[\]]/', '', $host); $path = ''; if ( isset($_SERVER['SCRIPT_URL']) ) { @@ -183,7 +183,11 @@ public static function getSiteUrl() $path = $path ? (string)$path : ''; $path = preg_replace('/[\x00-\x1F\x7F]/', '', $path); - $path = preg_replace('/[^A-Za-z0-9\-._~\/]/', '', $path); + $path = preg_replace('/[^A-Za-z0-9\-._~\/%]/', '', $path); + $path = preg_replace_callback('/%[0-9a-fA-F]{2}/', static function ($matches) { + return strtoupper($matches[0]); + }, $path); + $path = preg_replace('/%(?![0-9A-Fa-f]{2})/', '', $path); if ( $path !== '' && $path[0] !== '/' ) { $path = '/' . $path; } diff --git a/tests/RemoteCalls/RemoteCallsGetSiteUrlTest.php b/tests/RemoteCalls/RemoteCallsGetSiteUrlTest.php index e1e5beb..07f3a3f 100644 --- a/tests/RemoteCalls/RemoteCallsGetSiteUrlTest.php +++ b/tests/RemoteCalls/RemoteCallsGetSiteUrlTest.php @@ -37,6 +37,7 @@ public function testGetSiteUrlSanitizesScriptUrl() public function testGetSiteUrlFallsBackToRequestUri() { unset($_SERVER['SCRIPT_URL']); + unset($_SERVER['HTTPS']); $_SERVER['HTTP_HOST'] = 'example.com'; $_SERVER['REQUEST_URI'] = '/path/to/page?x='; @@ -44,4 +45,25 @@ public function testGetSiteUrlFallsBackToRequestUri() self::assertSame('http://example.com/path/to/page', $result); } + + public function testGetSiteUrlPreservesEncodedPathFromScriptUrl() + { + $_SERVER['HTTP_HOST'] = 'example.com'; + $_SERVER['SCRIPT_URL'] = '/a%20b/c%2fd'; + + $result = RemoteCalls::getSiteUrl(); + + self::assertSame('http://example.com/a%20b/c%2Fd', $result); + } + + public function testGetSiteUrlRemovesInvalidPercentFromRequestUri() + { + unset($_SERVER['SCRIPT_URL']); + $_SERVER['HTTP_HOST'] = 'example.com'; + $_SERVER['REQUEST_URI'] = '/a%2gb%zz'; + + $result = RemoteCalls::getSiteUrl(); + + self::assertSame('http://example.com/a2gbzz', $result); + } }