diff --git a/.github/workflows/ci_cd.yml b/.github/workflows/ci_cd.yml index 47d4e25..2f1da62 100644 --- a/.github/workflows/ci_cd.yml +++ b/.github/workflows/ci_cd.yml @@ -9,6 +9,7 @@ on: pull_request: branches: - main + - fix/dependency-cves permissions: contents: read diff --git a/composer.lock b/composer.lock index 0d3d5b2..7ff93f0 100644 --- a/composer.lock +++ b/composer.lock @@ -1451,20 +1451,20 @@ }, { "name": "laravel/framework", - "version": "v13.26.1", + "version": "v13.34.0", "source": { "type": "git", "url": "https://github.com/laravel/framework.git", - "reference": "e4a1bc52ef551d52e60244bb004256d6861da7ab" + "reference": "c829b4982d29344cbcf1d7ad78eb5d2bb8ae66c4" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/laravel/framework/zipball/e4a1bc52ef551d52e60244bb004256d6861da7ab", - "reference": "e4a1bc52ef551d52e60244bb004256d6861da7ab", + "url": "https://api.github.com/repos/laravel/framework/zipball/c829b4982d29344cbcf1d7ad78eb5d2bb8ae66c4", + "reference": "c829b4982d29344cbcf1d7ad78eb5d2bb8ae66c4", "shasum": "" }, "require": { - "brick/math": "^0.14.2 || ^0.15 || ^0.16 || ^0.17 || ^0.18 || ^0.19", + "brick/math": "^0.14.2 || ^0.15 || ^0.16 || ^0.17 || ^0.18 || ^0.19 || ^0.20 || ^1.0", "composer-runtime-api": "^2.2", "doctrine/inflector": "^2.0.5", "dragonmantank/cron-expression": "^3.4", @@ -1576,18 +1576,20 @@ "league/flysystem-sftp-v3": "^3.25.1", "mockery/mockery": "^1.6.10", "opis/json-schema": "^2.4.1", - "orchestra/testbench-core": "^11.0.0", + "orchestra/testbench-core": "^11.5.0", "pda/pheanstalk": "^7.0.0 || ^8.0.0", "php-http/discovery": "^1.15", - "phpstan/phpstan": "^2.0", + "phpstan/phpstan": "2.2.15", "phpunit/phpunit": "^11.5.50 || ^12.5.8 || ^13.0.3", "predis/predis": "^2.3 || ^3.0", - "rector/rector": "^2.3", + "rector/rector": "2.6.3", "resend/resend-php": "^1.0", "symfony/cache": "^7.4.0 || ^8.0.0", "symfony/http-client": "^7.4.0 || ^8.0.0", + "symfony/mercure": "^0.8.0", "symfony/psr-http-message-bridge": "^7.4.0 || ^8.0.0", - "symfony/translation": "^7.4.0 || ^8.0.0" + "symfony/translation": "^7.4.0 || ^8.0.0", + "web-token/jwt-library": "^4.1" }, "suggest": { "ably/ably-php": "Required to use the Ably broadcast driver (^1.0).", @@ -1623,8 +1625,10 @@ "symfony/filesystem": "Required to enable support for relative symbolic links (^7.4 || ^8.0).", "symfony/http-client": "Required to enable support for the Symfony API mail transports (^7.4 || ^8.0).", "symfony/mailgun-mailer": "Required to enable support for the Mailgun mail transport (^7.4 || ^8.0).", + "symfony/mercure": "Required to use the Mercure broadcast driver (^0.8).", "symfony/postmark-mailer": "Required to enable support for the Postmark mail transport (^7.4 || ^8.0).", - "symfony/psr-http-message-bridge": "Required to use PSR-7 bridging features (^7.4 || ^8.0)." + "symfony/psr-http-message-bridge": "Required to use PSR-7 bridging features (^7.4 || ^8.0).", + "web-token/jwt-library": "Required to sign Mercure JWTs and use end-to-end encrypted channels (^4.1)." }, "type": "library", "extra": { @@ -1674,7 +1678,7 @@ "issues": "https://github.com/laravel/framework/issues", "source": "https://github.com/laravel/framework" }, - "time": "2026-08-18T20:31:28+00:00" + "time": "2026-09-29T12:46:21+00:00" }, { "name": "laravel/mcp", @@ -2192,16 +2196,16 @@ }, { "name": "league/flysystem", - "version": "3.35.2", + "version": "3.36.0", "source": { "type": "git", "url": "https://github.com/thephpleague/flysystem.git", - "reference": "b277b5dc3d56650b68904117124e79c851e12376" + "reference": "f7fb152932f30072d573510cbd4dd657d6475b25" }, "dist": { "type": "zip", - "url": "https://api.github.com/repos/thephpleague/flysystem/zipball/b277b5dc3d56650b68904117124e79c851e12376", - "reference": "b277b5dc3d56650b68904117124e79c851e12376", + "url": "https://api.github.com/repos/thephpleague/flysystem/zipball/f7fb152932f30072d573510cbd4dd657d6475b25", + "reference": "f7fb152932f30072d573510cbd4dd657d6475b25", "shasum": "" }, "require": { @@ -2269,9 +2273,9 @@ ], "support": { "issues": "https://github.com/thephpleague/flysystem/issues", - "source": "https://github.com/thephpleague/flysystem/tree/3.35.2" + "source": "https://github.com/thephpleague/flysystem/tree/3.36.0" }, - "time": "2026-07-06T14:42:07+00:00" + "time": "2026-09-02T08:00:27+00:00" }, { "name": "league/flysystem-aws-s3-v3", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 0b86342..d9a6a90 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -1088,14 +1088,14 @@ packages: boolbase@1.0.0: resolution: {integrity: sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww==} - brace-expansion@1.1.18: - resolution: {integrity: sha512-Edep/X9fGqVNmzKBVsDYIOtD+z1tuezV70LBjdCst9Tqu76lsnvRiZ6oTic1n+/BIwX6QDGAO94PN4N2SADvtw==} + brace-expansion@1.1.21: + resolution: {integrity: sha512-9zeA+KLZNNzglF2TPKRQEDyx6Yby7daAkuy8MiPzpXPsYDWi/DRM8jmwUDxokQjYqBpv5DgPiwD4h4ZZSy1Ujw==} - brace-expansion@2.1.4: - resolution: {integrity: sha512-hGfVzPxthbf3+2yjg/RBs60cB0FhqBS/zvdV/4wn4/BmN0bNMMHPc4V/BbFieqf1TKAGGAHnY4eSjajCl0f2Xg==} + brace-expansion@2.1.7: + resolution: {integrity: sha512-uZbew1NqdmPDTMJ8ah1y+b+9QEJrfkXFk3RcTQw3X0jW/xRUvFKsg1CfQdSYGdTbXZWExtU3J3ccxtnfw1Fi0g==} - brace-expansion@5.0.9: - resolution: {integrity: sha512-ScQ4IuvIEF1TMlP7Zt+vjJ//9zlPb2SDcxWxM3bk8s6t6GGdJ7KO1dCcTidOPJKePW30LE/2cT7wCyPho9/Wxg==} + brace-expansion@5.0.12: + resolution: {integrity: sha512-YovQ3rzhaLMIrDjNDMkNS01tea93qhEhG5xy8f6+R0l+dw3Ki+5sCoIoI942iuLZTHWogWktgwVDhU09iNEimQ==} engines: {node: 20 || >=22} braces@3.0.3: @@ -3303,16 +3303,16 @@ snapshots: boolbase@1.0.0: {} - brace-expansion@1.1.18: + brace-expansion@1.1.21: dependencies: balanced-match: 1.0.2 concat-map: 0.0.1 - brace-expansion@2.1.4: + brace-expansion@2.1.7: dependencies: balanced-match: 1.0.2 - brace-expansion@5.0.9: + brace-expansion@5.0.12: dependencies: balanced-match: 4.0.4 @@ -4206,15 +4206,15 @@ snapshots: minimatch@10.2.4: dependencies: - brace-expansion: 5.0.9 + brace-expansion: 5.0.12 minimatch@3.1.5: dependencies: - brace-expansion: 1.1.18 + brace-expansion: 1.1.21 minimatch@9.0.9: dependencies: - brace-expansion: 2.1.4 + brace-expansion: 2.1.7 minimist@1.2.8: {} diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index ed48c9b..a6b45ab 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -1,4 +1,9 @@ minimumReleaseAge: 10080 +# Security patches for GHSA-q2hr-2g5m-vwhr, GHSA-qhr7-859c-m2p7 and GHSA-6j4f-fj2g-mc7p. +minimumReleaseAgeExclude: + - brace-expansion@1.1.21 + - brace-expansion@2.1.7 + - brace-expansion@5.0.12 allowBuilds: unrs-resolver: true vue-demi: true diff --git a/tests/Unit/FilesystemPathSecurityTest.php b/tests/Unit/FilesystemPathSecurityTest.php new file mode 100644 index 0000000..9a5f891 --- /dev/null +++ b/tests/Unit/FilesystemPathSecurityTest.php @@ -0,0 +1,39 @@ +expectException(CorruptedPathDetected::class); + + (new WhitespacePathNormalizer)->normalizePath($path); + } + + /** + * @return array + */ + public static function corruptedPaths(): array + { + return [ + 'control character' => ["avatars/user\x00.svg"], + 'malformed UTF-8' => ["avatars/user\xFF.svg"], + 'control character hidden by malformed UTF-8' => ["avatars/user\xFF\x00.svg"], + ]; + } + + public function test_valid_unicode_paths_remain_supported(): void + { + $this->assertSame( + 'avatars/benützer.svg', + (new WhitespacePathNormalizer)->normalizePath('./avatars//benützer.svg'), + ); + } +}