This commit is contained in:
Roland Gruber 2024-12-04 07:59:29 +01:00
parent 96646536e0
commit b93333df1b
142 changed files with 2129 additions and 1235 deletions

276
lam/composer.lock generated
View file

@ -4,20 +4,20 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically" "This file is @generated automatically"
], ],
"content-hash": "a4cf937ec482ba4747016ff3f8a38d8d", "content-hash": "ebcc864bc725d4b59b4acd088924a39a",
"packages": [ "packages": [
{ {
"name": "beberlei/assert", "name": "beberlei/assert",
"version": "v3.3.2", "version": "v3.3.3",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/beberlei/assert.git", "url": "https://github.com/beberlei/assert.git",
"reference": "cb70015c04be1baee6f5f5c953703347c0ac1655" "reference": "b5fd8eacd8915a1b627b8bfc027803f1939734dd"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/beberlei/assert/zipball/cb70015c04be1baee6f5f5c953703347c0ac1655", "url": "https://api.github.com/repos/beberlei/assert/zipball/b5fd8eacd8915a1b627b8bfc027803f1939734dd",
"reference": "cb70015c04be1baee6f5f5c953703347c0ac1655", "reference": "b5fd8eacd8915a1b627b8bfc027803f1939734dd",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -25,7 +25,7 @@
"ext-json": "*", "ext-json": "*",
"ext-mbstring": "*", "ext-mbstring": "*",
"ext-simplexml": "*", "ext-simplexml": "*",
"php": "^7.0 || ^8.0" "php": "^7.1 || ^8.0"
}, },
"require-dev": { "require-dev": {
"friendsofphp/php-cs-fixer": "*", "friendsofphp/php-cs-fixer": "*",
@ -69,9 +69,9 @@
], ],
"support": { "support": {
"issues": "https://github.com/beberlei/assert/issues", "issues": "https://github.com/beberlei/assert/issues",
"source": "https://github.com/beberlei/assert/tree/v3.3.2" "source": "https://github.com/beberlei/assert/tree/v3.3.3"
}, },
"time": "2021-12-16T21:41:27+00:00" "time": "2024-07-15T13:18:35+00:00"
}, },
{ {
"name": "brick/math", "name": "brick/math",
@ -679,16 +679,16 @@
}, },
{ {
"name": "firebase/php-jwt", "name": "firebase/php-jwt",
"version": "v6.10.1", "version": "v6.10.2",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/firebase/php-jwt.git", "url": "https://github.com/firebase/php-jwt.git",
"reference": "500501c2ce893c824c801da135d02661199f60c5" "reference": "30c19ed0f3264cb660ea496895cfb6ef7ee3653b"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/firebase/php-jwt/zipball/500501c2ce893c824c801da135d02661199f60c5", "url": "https://api.github.com/repos/firebase/php-jwt/zipball/30c19ed0f3264cb660ea496895cfb6ef7ee3653b",
"reference": "500501c2ce893c824c801da135d02661199f60c5", "reference": "30c19ed0f3264cb660ea496895cfb6ef7ee3653b",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -736,9 +736,9 @@
], ],
"support": { "support": {
"issues": "https://github.com/firebase/php-jwt/issues", "issues": "https://github.com/firebase/php-jwt/issues",
"source": "https://github.com/firebase/php-jwt/tree/v6.10.1" "source": "https://github.com/firebase/php-jwt/tree/v6.10.2"
}, },
"time": "2024-05-18T18:05:11+00:00" "time": "2024-11-24T11:22:49+00:00"
}, },
{ {
"name": "guzzlehttp/psr7", "name": "guzzlehttp/psr7",
@ -916,16 +916,16 @@
}, },
{ {
"name": "illuminate/collections", "name": "illuminate/collections",
"version": "v10.48.20", "version": "v10.48.25",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/illuminate/collections.git", "url": "https://github.com/illuminate/collections.git",
"reference": "37c863cffb345869dd134eff8e646bc82a19cc96" "reference": "48de3d6bc6aa779112ddcb608a3a96fc975d89d8"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/illuminate/collections/zipball/37c863cffb345869dd134eff8e646bc82a19cc96", "url": "https://api.github.com/repos/illuminate/collections/zipball/48de3d6bc6aa779112ddcb608a3a96fc975d89d8",
"reference": "37c863cffb345869dd134eff8e646bc82a19cc96", "reference": "48de3d6bc6aa779112ddcb608a3a96fc975d89d8",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -967,20 +967,20 @@
"issues": "https://github.com/laravel/framework/issues", "issues": "https://github.com/laravel/framework/issues",
"source": "https://github.com/laravel/framework" "source": "https://github.com/laravel/framework"
}, },
"time": "2024-06-19T14:25:05+00:00" "time": "2024-11-21T14:02:44+00:00"
}, },
{ {
"name": "illuminate/conditionable", "name": "illuminate/conditionable",
"version": "v10.48.20", "version": "v10.48.25",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/illuminate/conditionable.git", "url": "https://github.com/illuminate/conditionable.git",
"reference": "d0958e4741fc9d6f516a552060fd1b829a85e009" "reference": "3ee34ac306fafc2a6f19cd7cd68c9af389e432a5"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/illuminate/conditionable/zipball/d0958e4741fc9d6f516a552060fd1b829a85e009", "url": "https://api.github.com/repos/illuminate/conditionable/zipball/3ee34ac306fafc2a6f19cd7cd68c9af389e432a5",
"reference": "d0958e4741fc9d6f516a552060fd1b829a85e009", "reference": "3ee34ac306fafc2a6f19cd7cd68c9af389e432a5",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -1013,20 +1013,20 @@
"issues": "https://github.com/laravel/framework/issues", "issues": "https://github.com/laravel/framework/issues",
"source": "https://github.com/laravel/framework" "source": "https://github.com/laravel/framework"
}, },
"time": "2023-02-03T08:06:17+00:00" "time": "2024-11-21T14:02:44+00:00"
}, },
{ {
"name": "illuminate/contracts", "name": "illuminate/contracts",
"version": "v10.48.20", "version": "v10.48.25",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/illuminate/contracts.git", "url": "https://github.com/illuminate/contracts.git",
"reference": "8d7152c4a1f5d9cf7da3e8b71f23e4556f6138ac" "reference": "f90663a69f926105a70b78060a31f3c64e2d1c74"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/illuminate/contracts/zipball/8d7152c4a1f5d9cf7da3e8b71f23e4556f6138ac", "url": "https://api.github.com/repos/illuminate/contracts/zipball/f90663a69f926105a70b78060a31f3c64e2d1c74",
"reference": "8d7152c4a1f5d9cf7da3e8b71f23e4556f6138ac", "reference": "f90663a69f926105a70b78060a31f3c64e2d1c74",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -1061,11 +1061,11 @@
"issues": "https://github.com/laravel/framework/issues", "issues": "https://github.com/laravel/framework/issues",
"source": "https://github.com/laravel/framework" "source": "https://github.com/laravel/framework"
}, },
"time": "2024-01-15T18:52:32+00:00" "time": "2024-11-21T14:02:44+00:00"
}, },
{ {
"name": "illuminate/macroable", "name": "illuminate/macroable",
"version": "v10.48.20", "version": "v10.48.25",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/illuminate/macroable.git", "url": "https://github.com/illuminate/macroable.git",
@ -1111,7 +1111,7 @@
}, },
{ {
"name": "illuminate/pagination", "name": "illuminate/pagination",
"version": "v10.48.20", "version": "v10.48.25",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/illuminate/pagination.git", "url": "https://github.com/illuminate/pagination.git",
@ -1161,16 +1161,16 @@
}, },
{ {
"name": "illuminate/support", "name": "illuminate/support",
"version": "v10.48.20", "version": "v10.48.25",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/illuminate/support.git", "url": "https://github.com/illuminate/support.git",
"reference": "56c6d9895605b019e3debb9440454596ef99312a" "reference": "64b258f80175c658aef9e22dd3f2ba18c99b243c"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/illuminate/support/zipball/56c6d9895605b019e3debb9440454596ef99312a", "url": "https://api.github.com/repos/illuminate/support/zipball/64b258f80175c658aef9e22dd3f2ba18c99b243c",
"reference": "56c6d9895605b019e3debb9440454596ef99312a", "reference": "64b258f80175c658aef9e22dd3f2ba18c99b243c",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -1228,20 +1228,20 @@
"issues": "https://github.com/laravel/framework/issues", "issues": "https://github.com/laravel/framework/issues",
"source": "https://github.com/laravel/framework" "source": "https://github.com/laravel/framework"
}, },
"time": "2024-05-20T13:31:33+00:00" "time": "2024-11-21T14:02:44+00:00"
}, },
{ {
"name": "monolog/monolog", "name": "monolog/monolog",
"version": "3.7.0", "version": "3.8.0",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/Seldaek/monolog.git", "url": "https://github.com/Seldaek/monolog.git",
"reference": "f4393b648b78a5408747de94fca38beb5f7e9ef8" "reference": "32e515fdc02cdafbe4593e30a9350d486b125b67"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/Seldaek/monolog/zipball/f4393b648b78a5408747de94fca38beb5f7e9ef8", "url": "https://api.github.com/repos/Seldaek/monolog/zipball/32e515fdc02cdafbe4593e30a9350d486b125b67",
"reference": "f4393b648b78a5408747de94fca38beb5f7e9ef8", "reference": "32e515fdc02cdafbe4593e30a9350d486b125b67",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -1261,12 +1261,14 @@
"guzzlehttp/psr7": "^2.2", "guzzlehttp/psr7": "^2.2",
"mongodb/mongodb": "^1.8", "mongodb/mongodb": "^1.8",
"php-amqplib/php-amqplib": "~2.4 || ^3", "php-amqplib/php-amqplib": "~2.4 || ^3",
"phpstan/phpstan": "^1.9", "php-console/php-console": "^3.1.8",
"phpstan/phpstan-deprecation-rules": "^1.0", "phpstan/phpstan": "^2",
"phpstan/phpstan-strict-rules": "^1.4", "phpstan/phpstan-deprecation-rules": "^2",
"phpunit/phpunit": "^10.5.17", "phpstan/phpstan-strict-rules": "^2",
"phpunit/phpunit": "^10.5.17 || ^11.0.7",
"predis/predis": "^1.1 || ^2", "predis/predis": "^1.1 || ^2",
"ruflin/elastica": "^7", "rollbar/rollbar": "^4.0",
"ruflin/elastica": "^7 || ^8",
"symfony/mailer": "^5.4 || ^6", "symfony/mailer": "^5.4 || ^6",
"symfony/mime": "^5.4 || ^6" "symfony/mime": "^5.4 || ^6"
}, },
@ -1317,7 +1319,7 @@
], ],
"support": { "support": {
"issues": "https://github.com/Seldaek/monolog/issues", "issues": "https://github.com/Seldaek/monolog/issues",
"source": "https://github.com/Seldaek/monolog/tree/3.7.0" "source": "https://github.com/Seldaek/monolog/tree/3.8.0"
}, },
"funding": [ "funding": [
{ {
@ -1329,7 +1331,7 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-06-28T09:40:51+00:00" "time": "2024-11-12T13:57:08+00:00"
}, },
{ {
"name": "nesbot/carbon", "name": "nesbot/carbon",
@ -1561,16 +1563,16 @@
}, },
{ {
"name": "php-http/discovery", "name": "php-http/discovery",
"version": "1.19.4", "version": "1.20.0",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/php-http/discovery.git", "url": "https://github.com/php-http/discovery.git",
"reference": "0700efda8d7526335132360167315fdab3aeb599" "reference": "82fe4c73ef3363caed49ff8dd1539ba06044910d"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/php-http/discovery/zipball/0700efda8d7526335132360167315fdab3aeb599", "url": "https://api.github.com/repos/php-http/discovery/zipball/82fe4c73ef3363caed49ff8dd1539ba06044910d",
"reference": "0700efda8d7526335132360167315fdab3aeb599", "reference": "82fe4c73ef3363caed49ff8dd1539ba06044910d",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -1634,22 +1636,22 @@
], ],
"support": { "support": {
"issues": "https://github.com/php-http/discovery/issues", "issues": "https://github.com/php-http/discovery/issues",
"source": "https://github.com/php-http/discovery/tree/1.19.4" "source": "https://github.com/php-http/discovery/tree/1.20.0"
}, },
"time": "2024-03-29T13:00:05+00:00" "time": "2024-10-02T11:20:13+00:00"
}, },
{ {
"name": "phpmailer/phpmailer", "name": "phpmailer/phpmailer",
"version": "v6.9.1", "version": "v6.9.3",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/PHPMailer/PHPMailer.git", "url": "https://github.com/PHPMailer/PHPMailer.git",
"reference": "039de174cd9c17a8389754d3b877a2ed22743e18" "reference": "2f5c94fe7493efc213f643c23b1b1c249d40f47e"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/PHPMailer/PHPMailer/zipball/039de174cd9c17a8389754d3b877a2ed22743e18", "url": "https://api.github.com/repos/PHPMailer/PHPMailer/zipball/2f5c94fe7493efc213f643c23b1b1c249d40f47e",
"reference": "039de174cd9c17a8389754d3b877a2ed22743e18", "reference": "2f5c94fe7493efc213f643c23b1b1c249d40f47e",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -1709,7 +1711,7 @@
"description": "PHPMailer is a full-featured email creation and transfer class for PHP", "description": "PHPMailer is a full-featured email creation and transfer class for PHP",
"support": { "support": {
"issues": "https://github.com/PHPMailer/PHPMailer/issues", "issues": "https://github.com/PHPMailer/PHPMailer/issues",
"source": "https://github.com/PHPMailer/PHPMailer/tree/v6.9.1" "source": "https://github.com/PHPMailer/PHPMailer/tree/v6.9.3"
}, },
"funding": [ "funding": [
{ {
@ -1717,20 +1719,20 @@
"type": "github" "type": "github"
} }
], ],
"time": "2023-11-25T22:23:28+00:00" "time": "2024-11-24T18:04:13+00:00"
}, },
{ {
"name": "phpseclib/phpseclib", "name": "phpseclib/phpseclib",
"version": "3.0.41", "version": "3.0.42",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/phpseclib/phpseclib.git", "url": "https://github.com/phpseclib/phpseclib.git",
"reference": "621c73f7dcb310b61de34d1da4c4204e8ace6ceb" "reference": "db92f1b1987b12b13f248fe76c3a52cadb67bb98"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/phpseclib/phpseclib/zipball/621c73f7dcb310b61de34d1da4c4204e8ace6ceb", "url": "https://api.github.com/repos/phpseclib/phpseclib/zipball/db92f1b1987b12b13f248fe76c3a52cadb67bb98",
"reference": "621c73f7dcb310b61de34d1da4c4204e8ace6ceb", "reference": "db92f1b1987b12b13f248fe76c3a52cadb67bb98",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -1811,7 +1813,7 @@
], ],
"support": { "support": {
"issues": "https://github.com/phpseclib/phpseclib/issues", "issues": "https://github.com/phpseclib/phpseclib/issues",
"source": "https://github.com/phpseclib/phpseclib/tree/3.0.41" "source": "https://github.com/phpseclib/phpseclib/tree/3.0.42"
}, },
"funding": [ "funding": [
{ {
@ -1827,7 +1829,7 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-08-12T00:13:54+00:00" "time": "2024-09-16T03:06:04+00:00"
}, },
{ {
"name": "psr/clock", "name": "psr/clock",
@ -2498,16 +2500,16 @@
}, },
{ {
"name": "symfony/deprecation-contracts", "name": "symfony/deprecation-contracts",
"version": "v3.5.0", "version": "v3.5.1",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/deprecation-contracts.git", "url": "https://github.com/symfony/deprecation-contracts.git",
"reference": "0e0d29ce1f20deffb4ab1b016a7257c4f1e789a1" "reference": "74c71c939a79f7d5bf3c1ce9f5ea37ba0114c6f6"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/0e0d29ce1f20deffb4ab1b016a7257c4f1e789a1", "url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/74c71c939a79f7d5bf3c1ce9f5ea37ba0114c6f6",
"reference": "0e0d29ce1f20deffb4ab1b016a7257c4f1e789a1", "reference": "74c71c939a79f7d5bf3c1ce9f5ea37ba0114c6f6",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -2545,7 +2547,7 @@
"description": "A generic function and convention to trigger deprecation notices", "description": "A generic function and convention to trigger deprecation notices",
"homepage": "https://symfony.com", "homepage": "https://symfony.com",
"support": { "support": {
"source": "https://github.com/symfony/deprecation-contracts/tree/v3.5.0" "source": "https://github.com/symfony/deprecation-contracts/tree/v3.5.1"
}, },
"funding": [ "funding": [
{ {
@ -2561,27 +2563,27 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-04-18T09:32:20+00:00" "time": "2024-09-25T14:20:29+00:00"
}, },
{ {
"name": "symfony/http-client", "name": "symfony/http-client",
"version": "v6.4.15", "version": "v6.4.16",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/http-client.git", "url": "https://github.com/symfony/http-client.git",
"reference": "cb4073c905cd12b8496d24ac428a9228c1750670" "reference": "60a113666fa67e598abace38e5f46a0954d8833d"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/http-client/zipball/cb4073c905cd12b8496d24ac428a9228c1750670", "url": "https://api.github.com/repos/symfony/http-client/zipball/60a113666fa67e598abace38e5f46a0954d8833d",
"reference": "cb4073c905cd12b8496d24ac428a9228c1750670", "reference": "60a113666fa67e598abace38e5f46a0954d8833d",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
"php": ">=8.1", "php": ">=8.1",
"psr/log": "^1|^2|^3", "psr/log": "^1|^2|^3",
"symfony/deprecation-contracts": "^2.5|^3", "symfony/deprecation-contracts": "^2.5|^3",
"symfony/http-client-contracts": "^3.4.1", "symfony/http-client-contracts": "~3.4.3|^3.5.1",
"symfony/service-contracts": "^2.5|^3" "symfony/service-contracts": "^2.5|^3"
}, },
"conflict": { "conflict": {
@ -2638,7 +2640,7 @@
"http" "http"
], ],
"support": { "support": {
"source": "https://github.com/symfony/http-client/tree/v6.4.15" "source": "https://github.com/symfony/http-client/tree/v6.4.16"
}, },
"funding": [ "funding": [
{ {
@ -2654,20 +2656,20 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-11-13T13:40:18+00:00" "time": "2024-11-27T11:52:33+00:00"
}, },
{ {
"name": "symfony/http-client-contracts", "name": "symfony/http-client-contracts",
"version": "v3.5.0", "version": "v3.5.1",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/http-client-contracts.git", "url": "https://github.com/symfony/http-client-contracts.git",
"reference": "20414d96f391677bf80078aa55baece78b82647d" "reference": "c2f3ad828596624ca39ea40f83617ef51ca8bbf9"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/http-client-contracts/zipball/20414d96f391677bf80078aa55baece78b82647d", "url": "https://api.github.com/repos/symfony/http-client-contracts/zipball/c2f3ad828596624ca39ea40f83617ef51ca8bbf9",
"reference": "20414d96f391677bf80078aa55baece78b82647d", "reference": "c2f3ad828596624ca39ea40f83617ef51ca8bbf9",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -2716,7 +2718,7 @@
"standards" "standards"
], ],
"support": { "support": {
"source": "https://github.com/symfony/http-client-contracts/tree/v3.5.0" "source": "https://github.com/symfony/http-client-contracts/tree/v3.5.1"
}, },
"funding": [ "funding": [
{ {
@ -2732,20 +2734,20 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-04-18T09:32:20+00:00" "time": "2024-11-25T12:02:18+00:00"
}, },
{ {
"name": "symfony/http-foundation", "name": "symfony/http-foundation",
"version": "v6.4.14", "version": "v6.4.16",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/http-foundation.git", "url": "https://github.com/symfony/http-foundation.git",
"reference": "ba020a321a95519303a3f09ec2824d34d601c388" "reference": "431771b7a6f662f1575b3cfc8fd7617aa9864d57"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/http-foundation/zipball/ba020a321a95519303a3f09ec2824d34d601c388", "url": "https://api.github.com/repos/symfony/http-foundation/zipball/431771b7a6f662f1575b3cfc8fd7617aa9864d57",
"reference": "ba020a321a95519303a3f09ec2824d34d601c388", "reference": "431771b7a6f662f1575b3cfc8fd7617aa9864d57",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -2755,12 +2757,12 @@
"symfony/polyfill-php83": "^1.27" "symfony/polyfill-php83": "^1.27"
}, },
"conflict": { "conflict": {
"symfony/cache": "<6.3" "symfony/cache": "<6.4.12|>=7.0,<7.1.5"
}, },
"require-dev": { "require-dev": {
"doctrine/dbal": "^2.13.1|^3|^4", "doctrine/dbal": "^2.13.1|^3|^4",
"predis/predis": "^1.1|^2.0", "predis/predis": "^1.1|^2.0",
"symfony/cache": "^6.3|^7.0", "symfony/cache": "^6.4.12|^7.1.5",
"symfony/dependency-injection": "^5.4|^6.0|^7.0", "symfony/dependency-injection": "^5.4|^6.0|^7.0",
"symfony/expression-language": "^5.4|^6.0|^7.0", "symfony/expression-language": "^5.4|^6.0|^7.0",
"symfony/http-kernel": "^5.4.12|^6.0.12|^6.1.4|^7.0", "symfony/http-kernel": "^5.4.12|^6.0.12|^6.1.4|^7.0",
@ -2793,7 +2795,7 @@
"description": "Defines an object-oriented layer for the HTTP specification", "description": "Defines an object-oriented layer for the HTTP specification",
"homepage": "https://symfony.com", "homepage": "https://symfony.com",
"support": { "support": {
"source": "https://github.com/symfony/http-foundation/tree/v6.4.14" "source": "https://github.com/symfony/http-foundation/tree/v6.4.16"
}, },
"funding": [ "funding": [
{ {
@ -2809,7 +2811,7 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-11-05T16:39:55+00:00" "time": "2024-11-13T18:58:10+00:00"
}, },
{ {
"name": "symfony/polyfill-mbstring", "name": "symfony/polyfill-mbstring",
@ -3049,20 +3051,20 @@
}, },
{ {
"name": "symfony/polyfill-uuid", "name": "symfony/polyfill-uuid",
"version": "v1.30.0", "version": "v1.31.0",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/polyfill-uuid.git", "url": "https://github.com/symfony/polyfill-uuid.git",
"reference": "2ba1f33797470debcda07fe9dce20a0003df18e9" "reference": "21533be36c24be3f4b1669c4725c7d1d2bab4ae2"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/polyfill-uuid/zipball/2ba1f33797470debcda07fe9dce20a0003df18e9", "url": "https://api.github.com/repos/symfony/polyfill-uuid/zipball/21533be36c24be3f4b1669c4725c7d1d2bab4ae2",
"reference": "2ba1f33797470debcda07fe9dce20a0003df18e9", "reference": "21533be36c24be3f4b1669c4725c7d1d2bab4ae2",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
"php": ">=7.1" "php": ">=7.2"
}, },
"provide": { "provide": {
"ext-uuid": "*" "ext-uuid": "*"
@ -3108,7 +3110,7 @@
"uuid" "uuid"
], ],
"support": { "support": {
"source": "https://github.com/symfony/polyfill-uuid/tree/v1.30.0" "source": "https://github.com/symfony/polyfill-uuid/tree/v1.31.0"
}, },
"funding": [ "funding": [
{ {
@ -3124,20 +3126,20 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-05-31T15:07:36+00:00" "time": "2024-09-09T11:45:10+00:00"
}, },
{ {
"name": "symfony/psr-http-message-bridge", "name": "symfony/psr-http-message-bridge",
"version": "v6.4.11", "version": "v6.4.13",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/psr-http-message-bridge.git", "url": "https://github.com/symfony/psr-http-message-bridge.git",
"reference": "74835ba54eca99a38f374f7a6d932fa510124773" "reference": "c9cf83326a1074f83a738fc5320945abf7fb7fec"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/psr-http-message-bridge/zipball/74835ba54eca99a38f374f7a6d932fa510124773", "url": "https://api.github.com/repos/symfony/psr-http-message-bridge/zipball/c9cf83326a1074f83a738fc5320945abf7fb7fec",
"reference": "74835ba54eca99a38f374f7a6d932fa510124773", "reference": "c9cf83326a1074f83a738fc5320945abf7fb7fec",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -3191,7 +3193,7 @@
"psr-7" "psr-7"
], ],
"support": { "support": {
"source": "https://github.com/symfony/psr-http-message-bridge/tree/v6.4.11" "source": "https://github.com/symfony/psr-http-message-bridge/tree/v6.4.13"
}, },
"funding": [ "funding": [
{ {
@ -3207,20 +3209,20 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-08-14T13:55:58+00:00" "time": "2024-09-25T14:18:03+00:00"
}, },
{ {
"name": "symfony/service-contracts", "name": "symfony/service-contracts",
"version": "v3.5.0", "version": "v3.5.1",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/service-contracts.git", "url": "https://github.com/symfony/service-contracts.git",
"reference": "bd1d9e59a81d8fa4acdcea3f617c581f7475a80f" "reference": "e53260aabf78fb3d63f8d79d69ece59f80d5eda0"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/service-contracts/zipball/bd1d9e59a81d8fa4acdcea3f617c581f7475a80f", "url": "https://api.github.com/repos/symfony/service-contracts/zipball/e53260aabf78fb3d63f8d79d69ece59f80d5eda0",
"reference": "bd1d9e59a81d8fa4acdcea3f617c581f7475a80f", "reference": "e53260aabf78fb3d63f8d79d69ece59f80d5eda0",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -3274,7 +3276,7 @@
"standards" "standards"
], ],
"support": { "support": {
"source": "https://github.com/symfony/service-contracts/tree/v3.5.0" "source": "https://github.com/symfony/service-contracts/tree/v3.5.1"
}, },
"funding": [ "funding": [
{ {
@ -3290,20 +3292,20 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-04-18T09:32:20+00:00" "time": "2024-09-25T14:20:29+00:00"
}, },
{ {
"name": "symfony/translation", "name": "symfony/translation",
"version": "v6.4.10", "version": "v6.4.13",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/translation.git", "url": "https://github.com/symfony/translation.git",
"reference": "94041203f8ac200ae9e7c6a18fa6137814ccecc9" "reference": "bee9bfabfa8b4045a66bf82520e492cddbaffa66"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/translation/zipball/94041203f8ac200ae9e7c6a18fa6137814ccecc9", "url": "https://api.github.com/repos/symfony/translation/zipball/bee9bfabfa8b4045a66bf82520e492cddbaffa66",
"reference": "94041203f8ac200ae9e7c6a18fa6137814ccecc9", "reference": "bee9bfabfa8b4045a66bf82520e492cddbaffa66",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -3369,7 +3371,7 @@
"description": "Provides tools to internationalize your application", "description": "Provides tools to internationalize your application",
"homepage": "https://symfony.com", "homepage": "https://symfony.com",
"support": { "support": {
"source": "https://github.com/symfony/translation/tree/v6.4.10" "source": "https://github.com/symfony/translation/tree/v6.4.13"
}, },
"funding": [ "funding": [
{ {
@ -3385,20 +3387,20 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-07-26T12:30:32+00:00" "time": "2024-09-27T18:14:25+00:00"
}, },
{ {
"name": "symfony/translation-contracts", "name": "symfony/translation-contracts",
"version": "v3.5.0", "version": "v3.5.1",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/translation-contracts.git", "url": "https://github.com/symfony/translation-contracts.git",
"reference": "b9d2189887bb6b2e0367a9fc7136c5239ab9b05a" "reference": "4667ff3bd513750603a09c8dedbea942487fb07c"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/translation-contracts/zipball/b9d2189887bb6b2e0367a9fc7136c5239ab9b05a", "url": "https://api.github.com/repos/symfony/translation-contracts/zipball/4667ff3bd513750603a09c8dedbea942487fb07c",
"reference": "b9d2189887bb6b2e0367a9fc7136c5239ab9b05a", "reference": "4667ff3bd513750603a09c8dedbea942487fb07c",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -3447,7 +3449,7 @@
"standards" "standards"
], ],
"support": { "support": {
"source": "https://github.com/symfony/translation-contracts/tree/v3.5.0" "source": "https://github.com/symfony/translation-contracts/tree/v3.5.1"
}, },
"funding": [ "funding": [
{ {
@ -3463,20 +3465,20 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-04-18T09:32:20+00:00" "time": "2024-09-25T14:20:29+00:00"
}, },
{ {
"name": "symfony/uid", "name": "symfony/uid",
"version": "v6.4.11", "version": "v6.4.13",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/symfony/uid.git", "url": "https://github.com/symfony/uid.git",
"reference": "6a0394ad707de386547223948fac1e0f2805bc0b" "reference": "18eb207f0436a993fffbdd811b5b8fa35fa5e007"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/symfony/uid/zipball/6a0394ad707de386547223948fac1e0f2805bc0b", "url": "https://api.github.com/repos/symfony/uid/zipball/18eb207f0436a993fffbdd811b5b8fa35fa5e007",
"reference": "6a0394ad707de386547223948fac1e0f2805bc0b", "reference": "18eb207f0436a993fffbdd811b5b8fa35fa5e007",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -3521,7 +3523,7 @@
"uuid" "uuid"
], ],
"support": { "support": {
"source": "https://github.com/symfony/uid/tree/v6.4.11" "source": "https://github.com/symfony/uid/tree/v6.4.13"
}, },
"funding": [ "funding": [
{ {
@ -3537,7 +3539,7 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2024-08-12T09:55:28+00:00" "time": "2024-09-25T14:18:03+00:00"
}, },
{ {
"name": "thecodingmachine/safe", "name": "thecodingmachine/safe",
@ -3680,16 +3682,16 @@
}, },
{ {
"name": "voku/portable-ascii", "name": "voku/portable-ascii",
"version": "2.0.1", "version": "2.0.3",
"source": { "source": {
"type": "git", "type": "git",
"url": "https://github.com/voku/portable-ascii.git", "url": "https://github.com/voku/portable-ascii.git",
"reference": "b56450eed252f6801410d810c8e1727224ae0743" "reference": "b1d923f88091c6bf09699efcd7c8a1b1bfd7351d"
}, },
"dist": { "dist": {
"type": "zip", "type": "zip",
"url": "https://api.github.com/repos/voku/portable-ascii/zipball/b56450eed252f6801410d810c8e1727224ae0743", "url": "https://api.github.com/repos/voku/portable-ascii/zipball/b1d923f88091c6bf09699efcd7c8a1b1bfd7351d",
"reference": "b56450eed252f6801410d810c8e1727224ae0743", "reference": "b1d923f88091c6bf09699efcd7c8a1b1bfd7351d",
"shasum": "" "shasum": ""
}, },
"require": { "require": {
@ -3714,7 +3716,7 @@
"authors": [ "authors": [
{ {
"name": "Lars Moelleken", "name": "Lars Moelleken",
"homepage": "http://www.moelleken.org/" "homepage": "https://www.moelleken.org/"
} }
], ],
"description": "Portable ASCII library - performance optimized (ascii) string functions for php.", "description": "Portable ASCII library - performance optimized (ascii) string functions for php.",
@ -3726,7 +3728,7 @@
], ],
"support": { "support": {
"issues": "https://github.com/voku/portable-ascii/issues", "issues": "https://github.com/voku/portable-ascii/issues",
"source": "https://github.com/voku/portable-ascii/tree/2.0.1" "source": "https://github.com/voku/portable-ascii/tree/2.0.3"
}, },
"funding": [ "funding": [
{ {
@ -3750,7 +3752,7 @@
"type": "tidelift" "type": "tidelift"
} }
], ],
"time": "2022-03-08T17:03:00+00:00" "time": "2024-11-21T01:49:47+00:00"
}, },
{ {
"name": "web-auth/cose-lib", "name": "web-auth/cose-lib",
@ -4621,5 +4623,5 @@
"platform-overrides": { "platform-overrides": {
"php": "8.1" "php": "8.1"
}, },
"plugin-api-version": "2.6.0" "plugin-api-version": "2.3.0"
} }

View file

@ -1,64 +0,0 @@
on: [push, pull_request]
name: CI
jobs:
tests:
name: Tests
runs-on: ubuntu-latest
strategy:
matrix:
php-versions: ['7.0', '7.1', '7.2', '7.3', '7.4', '8.0', '8.1']
steps:
- name: Checkout
uses: actions/checkout@v1
- name: Setup PHP
uses: shivammathur/setup-php@v2
with:
php-version: ${{ matrix.php-versions }}
tools: "cs2pr"
- name: "Cache dependencies installed with composer"
uses: "actions/cache@v1"
with:
path: "~/.composer/cache"
key: "php-${{ matrix.php-version }}-composer-locked-${{ hashFiles('composer.lock') }}"
restore-keys: "php-${{ matrix.php-version }}-composer-locked-"
- name: "Composer"
run: "composer update --prefer-stable"
- name: "PHPUnit"
run: "php vendor/bin/phpunit"
# lint:
# name: Lint
# runs-on: ubuntu-latest
# steps:
# - name: Checkout
# uses: actions/checkout@v1
# - name: Setup PHP
# uses: shivammathur/setup-php@v2
# with:
# php-version: 7.4
# - name: "Cache dependencies installed with composer"
# uses: "actions/cache@v1"
# with:
# path: "~/.composer/cache"
# key: "php-${{ matrix.php-version }}-composer-locked-${{ hashFiles('composer.lock') }}"
# restore-keys: "php-${{ matrix.php-version }}-composer-locked-"
# - name: "Composer"
# run: "composer update --prefer-stable"
# - name: "assert:cs-lint"
# run: "composer assert:cs-lint"
# - name: "assert:sa-code"
# run: "composer assert:sa-code"
# - name: "assert:sa-tests"
# run: "composer assert:sa-tests"

View file

@ -23,7 +23,7 @@
"sort-packages": true "sort-packages": true
}, },
"require": { "require": {
"php": "^7.0 || ^8.0", "php": "^7.1 || ^8.0",
"ext-simplexml": "*", "ext-simplexml": "*",
"ext-mbstring": "*", "ext-mbstring": "*",
"ext-ctype": "*", "ext-ctype": "*",

View file

@ -42,7 +42,7 @@ abstract class Assert
* The assertion chain can be stateful, that means be careful when you reuse * The assertion chain can be stateful, that means be careful when you reuse
* it. You should never pass around the chain. * it. You should never pass around the chain.
*/ */
public static function that($value, $defaultMessage = null, string $defaultPropertyPath = null): AssertionChain public static function that($value, $defaultMessage = null, ?string $defaultPropertyPath = null): AssertionChain
{ {
$assertionChain = new AssertionChain($value, $defaultMessage, $defaultPropertyPath); $assertionChain = new AssertionChain($value, $defaultMessage, $defaultPropertyPath);
@ -55,7 +55,7 @@ abstract class Assert
* @param mixed $values * @param mixed $values
* @param string|callable|null $defaultMessage * @param string|callable|null $defaultMessage
*/ */
public static function thatAll($values, $defaultMessage = null, string $defaultPropertyPath = null): AssertionChain public static function thatAll($values, $defaultMessage = null, ?string $defaultPropertyPath = null): AssertionChain
{ {
return static::that($values, $defaultMessage, $defaultPropertyPath)->all(); return static::that($values, $defaultMessage, $defaultPropertyPath)->all();
} }
@ -66,7 +66,7 @@ abstract class Assert
* @param mixed $value * @param mixed $value
* @param string|callable|null $defaultMessage * @param string|callable|null $defaultMessage
*/ */
public static function thatNullOr($value, $defaultMessage = null, string $defaultPropertyPath = null): AssertionChain public static function thatNullOr($value, $defaultMessage = null, ?string $defaultPropertyPath = null): AssertionChain
{ {
return static::that($value, $defaultMessage, $defaultPropertyPath)->nullOr(); return static::that($value, $defaultMessage, $defaultPropertyPath)->nullOr();
} }

View file

@ -307,7 +307,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function eq($value, $value2, $message = null, string $propertyPath = null): bool public static function eq($value, $value2, $message = null, ?string $propertyPath = null): bool
{ {
if ($value != $value2) { if ($value != $value2) {
$message = \sprintf( $message = \sprintf(
@ -331,7 +331,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function eqArraySubset($value, $value2, $message = null, string $propertyPath = null): bool public static function eqArraySubset($value, $value2, $message = null, ?string $propertyPath = null): bool
{ {
static::isArray($value, $message, $propertyPath); static::isArray($value, $message, $propertyPath);
static::isArray($value2, $message, $propertyPath); static::isArray($value2, $message, $propertyPath);
@ -358,7 +358,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function same($value, $value2, $message = null, string $propertyPath = null): bool public static function same($value, $value2, $message = null, ?string $propertyPath = null): bool
{ {
if ($value !== $value2) { if ($value !== $value2) {
$message = \sprintf( $message = \sprintf(
@ -382,7 +382,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notEq($value1, $value2, $message = null, string $propertyPath = null): bool public static function notEq($value1, $value2, $message = null, ?string $propertyPath = null): bool
{ {
if ($value1 == $value2) { if ($value1 == $value2) {
$message = \sprintf( $message = \sprintf(
@ -412,7 +412,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notSame($value1, $value2, $message = null, string $propertyPath = null): bool public static function notSame($value1, $value2, $message = null, ?string $propertyPath = null): bool
{ {
if ($value1 === $value2) { if ($value1 === $value2) {
$message = \sprintf( $message = \sprintf(
@ -434,7 +434,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notInArray($value, array $choices, $message = null, string $propertyPath = null): bool public static function notInArray($value, array $choices, $message = null, ?string $propertyPath = null): bool
{ {
if (true === \in_array($value, $choices)) { if (true === \in_array($value, $choices)) {
$message = \sprintf( $message = \sprintf(
@ -461,7 +461,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function integer($value, $message = null, string $propertyPath = null): bool public static function integer($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_int($value)) { if (!\is_int($value)) {
$message = \sprintf( $message = \sprintf(
@ -488,7 +488,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function float($value, $message = null, string $propertyPath = null): bool public static function float($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_float($value)) { if (!\is_float($value)) {
$message = \sprintf( $message = \sprintf(
@ -515,7 +515,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function digit($value, $message = null, string $propertyPath = null): bool public static function digit($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\ctype_digit((string)$value)) { if (!\ctype_digit((string)$value)) {
$message = \sprintf( $message = \sprintf(
@ -537,7 +537,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function integerish($value, $message = null, string $propertyPath = null): bool public static function integerish($value, $message = null, ?string $propertyPath = null): bool
{ {
if ( if (
\is_resource($value) || \is_resource($value) ||
@ -577,7 +577,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function boolean($value, $message = null, string $propertyPath = null): bool public static function boolean($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_bool($value)) { if (!\is_bool($value)) {
$message = \sprintf( $message = \sprintf(
@ -604,7 +604,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function scalar($value, $message = null, string $propertyPath = null): bool public static function scalar($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_scalar($value)) { if (!\is_scalar($value)) {
$message = \sprintf( $message = \sprintf(
@ -631,7 +631,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notEmpty($value, $message = null, string $propertyPath = null): bool public static function notEmpty($value, $message = null, ?string $propertyPath = null): bool
{ {
if (empty($value)) { if (empty($value)) {
$message = \sprintf( $message = \sprintf(
@ -658,7 +658,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function noContent($value, $message = null, string $propertyPath = null): bool public static function noContent($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!empty($value)) { if (!empty($value)) {
$message = \sprintf( $message = \sprintf(
@ -683,7 +683,7 @@ class Assertion
* *
* @return bool * @return bool
*/ */
public static function null($value, $message = null, string $propertyPath = null): bool public static function null($value, $message = null, ?string $propertyPath = null): bool
{ {
if (null !== $value) { if (null !== $value) {
$message = \sprintf( $message = \sprintf(
@ -710,7 +710,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notNull($value, $message = null, string $propertyPath = null): bool public static function notNull($value, $message = null, ?string $propertyPath = null): bool
{ {
if (null === $value) { if (null === $value) {
$message = \sprintf( $message = \sprintf(
@ -737,7 +737,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function string($value, $message = null, string $propertyPath = null) public static function string($value, $message = null, ?string $propertyPath = null)
{ {
if (!\is_string($value)) { if (!\is_string($value)) {
$message = \sprintf( $message = \sprintf(
@ -766,7 +766,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function regex($value, $pattern, $message = null, string $propertyPath = null): bool public static function regex($value, $pattern, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -794,7 +794,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notRegex($value, $pattern, $message = null, string $propertyPath = null): bool public static function notRegex($value, $pattern, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -825,7 +825,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function length($value, $length, $message = null, string $propertyPath = null, $encoding = 'utf8'): bool public static function length($value, $length, $message = null, ?string $propertyPath = null, $encoding = 'utf8'): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -858,7 +858,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function minLength($value, $minLength, $message = null, string $propertyPath = null, $encoding = 'utf8'): bool public static function minLength($value, $minLength, $message = null, ?string $propertyPath = null, $encoding = 'utf8'): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -891,7 +891,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function maxLength($value, $maxLength, $message = null, string $propertyPath = null, $encoding = 'utf8'): bool public static function maxLength($value, $maxLength, $message = null, ?string $propertyPath = null, $encoding = 'utf8'): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -925,7 +925,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function betweenLength($value, $minLength, $maxLength, $message = null, string $propertyPath = null, $encoding = 'utf8'): bool public static function betweenLength($value, $minLength, $maxLength, $message = null, ?string $propertyPath = null, $encoding = 'utf8'): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
static::minLength($value, $minLength, $message, $propertyPath, $encoding); static::minLength($value, $minLength, $message, $propertyPath, $encoding);
@ -949,7 +949,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function startsWith($string, $needle, $message = null, string $propertyPath = null, $encoding = 'utf8'): bool public static function startsWith($string, $needle, $message = null, ?string $propertyPath = null, $encoding = 'utf8'): bool
{ {
static::string($string, $message, $propertyPath); static::string($string, $message, $propertyPath);
@ -981,7 +981,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function endsWith($string, $needle, $message = null, string $propertyPath = null, $encoding = 'utf8'): bool public static function endsWith($string, $needle, $message = null, ?string $propertyPath = null, $encoding = 'utf8'): bool
{ {
static::string($string, $message, $propertyPath); static::string($string, $message, $propertyPath);
@ -1015,7 +1015,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function contains($string, $needle, $message = null, string $propertyPath = null, $encoding = 'utf8'): bool public static function contains($string, $needle, $message = null, ?string $propertyPath = null, $encoding = 'utf8'): bool
{ {
static::string($string, $message, $propertyPath); static::string($string, $message, $propertyPath);
@ -1047,7 +1047,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notContains($string, $needle, $message = null, string $propertyPath = null, $encoding = 'utf8'): bool public static function notContains($string, $needle, $message = null, ?string $propertyPath = null, $encoding = 'utf8'): bool
{ {
static::string($string, $message, $propertyPath); static::string($string, $message, $propertyPath);
@ -1072,7 +1072,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function choice($value, array $choices, $message = null, string $propertyPath = null): bool public static function choice($value, array $choices, $message = null, ?string $propertyPath = null): bool
{ {
if (!\in_array($value, $choices, true)) { if (!\in_array($value, $choices, true)) {
$message = \sprintf( $message = \sprintf(
@ -1097,7 +1097,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function inArray($value, array $choices, $message = null, string $propertyPath = null): bool public static function inArray($value, array $choices, $message = null, ?string $propertyPath = null): bool
{ {
return static::choice($value, $choices, $message, $propertyPath); return static::choice($value, $choices, $message, $propertyPath);
} }
@ -1115,7 +1115,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function numeric($value, $message = null, string $propertyPath = null): bool public static function numeric($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_numeric($value)) { if (!\is_numeric($value)) {
$message = \sprintf( $message = \sprintf(
@ -1140,7 +1140,7 @@ class Assertion
* *
* @return bool * @return bool
*/ */
public static function isResource($value, $message = null, string $propertyPath = null): bool public static function isResource($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_resource($value)) { if (!\is_resource($value)) {
$message = \sprintf( $message = \sprintf(
@ -1167,7 +1167,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function isArray($value, $message = null, string $propertyPath = null): bool public static function isArray($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_array($value)) { if (!\is_array($value)) {
$message = \sprintf( $message = \sprintf(
@ -1194,7 +1194,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function isTraversable($value, $message = null, string $propertyPath = null): bool public static function isTraversable($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_array($value) && !$value instanceof Traversable) { if (!\is_array($value) && !$value instanceof Traversable) {
$message = \sprintf( $message = \sprintf(
@ -1216,7 +1216,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function isArrayAccessible($value, $message = null, string $propertyPath = null): bool public static function isArrayAccessible($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_array($value) && !$value instanceof ArrayAccess) { if (!\is_array($value) && !$value instanceof ArrayAccess) {
$message = \sprintf( $message = \sprintf(
@ -1233,7 +1233,7 @@ class Assertion
/** /**
* Assert that value is countable. * Assert that value is countable.
* *
* @param array|Countable|ResourceBundle|SimpleXMLElement $value * @param mixed $value
* @param string|callable|null $message * @param string|callable|null $message
* @param string|null $propertyPath * @param string|null $propertyPath
* *
@ -1243,7 +1243,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function isCountable($value, $message = null, string $propertyPath = null): bool public static function isCountable($value, $message = null, ?string $propertyPath = null): bool
{ {
if (\function_exists('is_countable')) { if (\function_exists('is_countable')) {
$assert = \is_countable($value); $assert = \is_countable($value);
@ -1272,7 +1272,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function keyExists($value, $key, $message = null, string $propertyPath = null): bool public static function keyExists($value, $key, $message = null, ?string $propertyPath = null): bool
{ {
static::isArray($value, $message, $propertyPath); static::isArray($value, $message, $propertyPath);
@ -1297,7 +1297,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function keyNotExists($value, $key, $message = null, string $propertyPath = null): bool public static function keyNotExists($value, $key, $message = null, ?string $propertyPath = null): bool
{ {
static::isArray($value, $message, $propertyPath); static::isArray($value, $message, $propertyPath);
@ -1321,7 +1321,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function uniqueValues(array $values, $message = null, string $propertyPath = null): bool public static function uniqueValues(array $values, $message = null, ?string $propertyPath = null): bool
{ {
foreach ($values as $key => $value) { foreach ($values as $key => $value) {
if (\array_search($value, $values, true) !== $key) { if (\array_search($value, $values, true) !== $key) {
@ -1346,7 +1346,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function keyIsset($value, $key, $message = null, string $propertyPath = null): bool public static function keyIsset($value, $key, $message = null, ?string $propertyPath = null): bool
{ {
static::isArrayAccessible($value, $message, $propertyPath); static::isArrayAccessible($value, $message, $propertyPath);
@ -1371,7 +1371,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notEmptyKey($value, $key, $message = null, string $propertyPath = null): bool public static function notEmptyKey($value, $key, $message = null, ?string $propertyPath = null): bool
{ {
static::keyIsset($value, $key, $message, $propertyPath); static::keyIsset($value, $key, $message, $propertyPath);
static::notEmpty($value[$key], $message, $propertyPath); static::notEmpty($value[$key], $message, $propertyPath);
@ -1387,7 +1387,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notBlank($value, $message = null, string $propertyPath = null): bool public static function notBlank($value, $message = null, ?string $propertyPath = null): bool
{ {
if (false === $value || (empty($value) && '0' != $value) || (\is_string($value) && '' === \trim($value))) { if (false === $value || (empty($value) && '0' != $value) || (\is_string($value) && '' === \trim($value))) {
$message = \sprintf( $message = \sprintf(
@ -1417,7 +1417,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function isInstanceOf($value, $className, $message = null, string $propertyPath = null): bool public static function isInstanceOf($value, $className, $message = null, ?string $propertyPath = null): bool
{ {
if (!($value instanceof $className)) { if (!($value instanceof $className)) {
$message = \sprintf( $message = \sprintf(
@ -1448,7 +1448,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function notIsInstanceOf($value, $className, $message = null, string $propertyPath = null): bool public static function notIsInstanceOf($value, $className, $message = null, ?string $propertyPath = null): bool
{ {
if ($value instanceof $className) { if ($value instanceof $className) {
$message = \sprintf( $message = \sprintf(
@ -1472,7 +1472,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function subclassOf($value, $className, $message = null, string $propertyPath = null): bool public static function subclassOf($value, $className, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_subclass_of($value, $className)) { if (!\is_subclass_of($value, $className)) {
$message = \sprintf( $message = \sprintf(
@ -1502,7 +1502,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function range($value, $minValue, $maxValue, $message = null, string $propertyPath = null): bool public static function range($value, $minValue, $maxValue, $message = null, ?string $propertyPath = null): bool
{ {
static::numeric($value, $message, $propertyPath); static::numeric($value, $message, $propertyPath);
@ -1534,7 +1534,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function min($value, $minValue, $message = null, string $propertyPath = null): bool public static function min($value, $minValue, $message = null, ?string $propertyPath = null): bool
{ {
static::numeric($value, $message, $propertyPath); static::numeric($value, $message, $propertyPath);
@ -1565,7 +1565,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function max($value, $maxValue, $message = null, string $propertyPath = null): bool public static function max($value, $maxValue, $message = null, ?string $propertyPath = null): bool
{ {
static::numeric($value, $message, $propertyPath); static::numeric($value, $message, $propertyPath);
@ -1590,7 +1590,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function file($value, $message = null, string $propertyPath = null): bool public static function file($value, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
static::notEmpty($value, $message, $propertyPath); static::notEmpty($value, $message, $propertyPath);
@ -1615,7 +1615,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function directory($value, $message = null, string $propertyPath = null): bool public static function directory($value, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -1639,7 +1639,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function readable($value, $message = null, string $propertyPath = null): bool public static function readable($value, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -1663,7 +1663,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function writeable($value, $message = null, string $propertyPath = null): bool public static function writeable($value, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -1692,7 +1692,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function email($value, $message = null, string $propertyPath = null): bool public static function email($value, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -1726,7 +1726,7 @@ class Assertion
* @see https://github.com/symfony/Validator/blob/master/Constraints/UrlValidator.php * @see https://github.com/symfony/Validator/blob/master/Constraints/UrlValidator.php
* @see https://github.com/symfony/Validator/blob/master/Constraints/Url.php * @see https://github.com/symfony/Validator/blob/master/Constraints/Url.php
*/ */
public static function url($value, $message = null, string $propertyPath = null): bool public static function url($value, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
@ -1772,7 +1772,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function alnum($value, $message = null, string $propertyPath = null): bool public static function alnum($value, $message = null, ?string $propertyPath = null): bool
{ {
try { try {
static::regex($value, '(^([a-zA-Z]{1}[a-zA-Z0-9]*)$)', $message, $propertyPath); static::regex($value, '(^([a-zA-Z]{1}[a-zA-Z0-9]*)$)', $message, $propertyPath);
@ -1801,7 +1801,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function true($value, $message = null, string $propertyPath = null): bool public static function true($value, $message = null, ?string $propertyPath = null): bool
{ {
if (true !== $value) { if (true !== $value) {
$message = \sprintf( $message = \sprintf(
@ -1828,7 +1828,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function false($value, $message = null, string $propertyPath = null): bool public static function false($value, $message = null, ?string $propertyPath = null): bool
{ {
if (false !== $value) { if (false !== $value) {
$message = \sprintf( $message = \sprintf(
@ -1855,7 +1855,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function classExists($value, $message = null, string $propertyPath = null): bool public static function classExists($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\class_exists($value)) { if (!\class_exists($value)) {
$message = \sprintf( $message = \sprintf(
@ -1882,7 +1882,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function interfaceExists($value, $message = null, string $propertyPath = null): bool public static function interfaceExists($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\interface_exists($value)) { if (!\interface_exists($value)) {
$message = \sprintf( $message = \sprintf(
@ -1905,7 +1905,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function implementsInterface($class, $interfaceName, $message = null, string $propertyPath = null): bool public static function implementsInterface($class, $interfaceName, $message = null, ?string $propertyPath = null): bool
{ {
try { try {
$reflection = new ReflectionClass($class); $reflection = new ReflectionClass($class);
@ -1948,7 +1948,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function isJsonString($value, $message = null, string $propertyPath = null): bool public static function isJsonString($value, $message = null, ?string $propertyPath = null): bool
{ {
if (null === \json_decode($value) && JSON_ERROR_NONE !== \json_last_error()) { if (null === \json_decode($value) && JSON_ERROR_NONE !== \json_last_error()) {
$message = \sprintf( $message = \sprintf(
@ -1972,7 +1972,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function uuid($value, $message = null, string $propertyPath = null): bool public static function uuid($value, $message = null, ?string $propertyPath = null): bool
{ {
$value = \str_replace(['urn:', 'uuid:', '{', '}'], '', $value); $value = \str_replace(['urn:', 'uuid:', '{', '}'], '', $value);
@ -2002,7 +2002,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function e164($value, $message = null, string $propertyPath = null): bool public static function e164($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\preg_match('/^\+?[1-9]\d{1,14}$/', $value)) { if (!\preg_match('/^\+?[1-9]\d{1,14}$/', $value)) {
$message = \sprintf( $message = \sprintf(
@ -2028,7 +2028,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function count($countable, $count, $message = null, string $propertyPath = null): bool public static function count($countable, $count, $message = null, ?string $propertyPath = null): bool
{ {
if ($count !== \count($countable)) { if ($count !== \count($countable)) {
$message = \sprintf( $message = \sprintf(
@ -2052,7 +2052,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function minCount($countable, $count, $message = null, string $propertyPath = null): bool public static function minCount($countable, $count, $message = null, ?string $propertyPath = null): bool
{ {
if ($count > \count($countable)) { if ($count > \count($countable)) {
$message = \sprintf( $message = \sprintf(
@ -2076,7 +2076,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function maxCount($countable, $count, $message = null, string $propertyPath = null): bool public static function maxCount($countable, $count, $message = null, ?string $propertyPath = null): bool
{ {
if ($count < \count($countable)) { if ($count < \count($countable)) {
$message = \sprintf( $message = \sprintf(
@ -2147,7 +2147,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function choicesNotEmpty(array $values, array $choices, $message = null, string $propertyPath = null): bool public static function choicesNotEmpty(array $values, array $choices, $message = null, ?string $propertyPath = null): bool
{ {
static::notEmpty($values, $message, $propertyPath); static::notEmpty($values, $message, $propertyPath);
@ -2167,7 +2167,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function methodExists($value, $object, $message = null, string $propertyPath = null): bool public static function methodExists($value, $object, $message = null, ?string $propertyPath = null): bool
{ {
static::isObject($object, $message, $propertyPath); static::isObject($object, $message, $propertyPath);
@ -2196,7 +2196,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function isObject($value, $message = null, string $propertyPath = null): bool public static function isObject($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_object($value)) { if (!\is_object($value)) {
$message = \sprintf( $message = \sprintf(
@ -2219,7 +2219,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function lessThan($value, $limit, $message = null, string $propertyPath = null): bool public static function lessThan($value, $limit, $message = null, ?string $propertyPath = null): bool
{ {
if ($value >= $limit) { if ($value >= $limit) {
$message = \sprintf( $message = \sprintf(
@ -2243,7 +2243,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function lessOrEqualThan($value, $limit, $message = null, string $propertyPath = null): bool public static function lessOrEqualThan($value, $limit, $message = null, ?string $propertyPath = null): bool
{ {
if ($value > $limit) { if ($value > $limit) {
$message = \sprintf( $message = \sprintf(
@ -2267,7 +2267,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function greaterThan($value, $limit, $message = null, string $propertyPath = null): bool public static function greaterThan($value, $limit, $message = null, ?string $propertyPath = null): bool
{ {
if ($value <= $limit) { if ($value <= $limit) {
$message = \sprintf( $message = \sprintf(
@ -2291,7 +2291,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function greaterOrEqualThan($value, $limit, $message = null, string $propertyPath = null): bool public static function greaterOrEqualThan($value, $limit, $message = null, ?string $propertyPath = null): bool
{ {
if ($value < $limit) { if ($value < $limit) {
$message = \sprintf( $message = \sprintf(
@ -2317,7 +2317,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function between($value, $lowerLimit, $upperLimit, $message = null, string $propertyPath = null): bool public static function between($value, $lowerLimit, $upperLimit, $message = null, ?string $propertyPath = null): bool
{ {
if ($lowerLimit > $value || $value > $upperLimit) { if ($lowerLimit > $value || $value > $upperLimit) {
$message = \sprintf( $message = \sprintf(
@ -2344,7 +2344,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function betweenExclusive($value, $lowerLimit, $upperLimit, $message = null, string $propertyPath = null): bool public static function betweenExclusive($value, $lowerLimit, $upperLimit, $message = null, ?string $propertyPath = null): bool
{ {
if ($lowerLimit >= $value || $value >= $upperLimit) { if ($lowerLimit >= $value || $value >= $upperLimit) {
$message = \sprintf( $message = \sprintf(
@ -2368,7 +2368,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function extensionLoaded($value, $message = null, string $propertyPath = null): bool public static function extensionLoaded($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\extension_loaded($value)) { if (!\extension_loaded($value)) {
$message = \sprintf( $message = \sprintf(
@ -2394,7 +2394,7 @@ class Assertion
* *
* @see http://php.net/manual/function.date.php#refsect1-function.date-parameters * @see http://php.net/manual/function.date.php#refsect1-function.date-parameters
*/ */
public static function date($value, $format, $message = null, string $propertyPath = null): bool public static function date($value, $format, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
static::string($format, $message, $propertyPath); static::string($format, $message, $propertyPath);
@ -2422,7 +2422,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function objectOrClass($value, $message = null, string $propertyPath = null): bool public static function objectOrClass($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_object($value)) { if (!\is_object($value)) {
static::classExists($value, $message, $propertyPath); static::classExists($value, $message, $propertyPath);
@ -2440,7 +2440,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function propertyExists($value, $property, $message = null, string $propertyPath = null): bool public static function propertyExists($value, $property, $message = null, ?string $propertyPath = null): bool
{ {
static::objectOrClass($value); static::objectOrClass($value);
@ -2465,7 +2465,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function propertiesExist($value, array $properties, $message = null, string $propertyPath = null): bool public static function propertiesExist($value, array $properties, $message = null, ?string $propertyPath = null): bool
{ {
static::objectOrClass($value); static::objectOrClass($value);
static::allString($properties, $message, $propertyPath); static::allString($properties, $message, $propertyPath);
@ -2500,7 +2500,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function version($version1, $operator, $version2, $message = null, string $propertyPath = null): bool public static function version($version1, $operator, $version2, $message = null, ?string $propertyPath = null): bool
{ {
static::notEmpty($operator, 'versionCompare operator is required and cannot be empty.'); static::notEmpty($operator, 'versionCompare operator is required and cannot be empty.');
@ -2527,7 +2527,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function phpVersion($operator, $version, $message = null, string $propertyPath = null): bool public static function phpVersion($operator, $version, $message = null, ?string $propertyPath = null): bool
{ {
static::defined('PHP_VERSION'); static::defined('PHP_VERSION');
@ -2544,7 +2544,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function extensionVersion($extension, $operator, $version, $message = null, string $propertyPath = null): bool public static function extensionVersion($extension, $operator, $version, $message = null, ?string $propertyPath = null): bool
{ {
static::extensionLoaded($extension, $message, $propertyPath); static::extensionLoaded($extension, $message, $propertyPath);
@ -2564,7 +2564,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function isCallable($value, $message = null, string $propertyPath = null): bool public static function isCallable($value, $message = null, ?string $propertyPath = null): bool
{ {
if (!\is_callable($value)) { if (!\is_callable($value)) {
$message = \sprintf( $message = \sprintf(
@ -2589,7 +2589,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function satisfy($value, $callback, $message = null, string $propertyPath = null): bool public static function satisfy($value, $callback, $message = null, ?string $propertyPath = null): bool
{ {
static::isCallable($callback); static::isCallable($callback);
@ -2617,7 +2617,7 @@ class Assertion
* *
* @see http://php.net/manual/filter.filters.flags.php * @see http://php.net/manual/filter.filters.flags.php
*/ */
public static function ip($value, $flag = null, $message = null, string $propertyPath = null): bool public static function ip($value, $flag = null, $message = null, ?string $propertyPath = null): bool
{ {
static::string($value, $message, $propertyPath); static::string($value, $message, $propertyPath);
if ($flag === null) { if ($flag === null) {
@ -2648,7 +2648,7 @@ class Assertion
* *
* @see http://php.net/manual/filter.filters.flags.php * @see http://php.net/manual/filter.filters.flags.php
*/ */
public static function ipv4($value, $flag = null, $message = null, string $propertyPath = null): bool public static function ipv4($value, $flag = null, $message = null, ?string $propertyPath = null): bool
{ {
static::ip($value, $flag | FILTER_FLAG_IPV4, static::generateMessage($message ?: 'Value "%s" was expected to be a valid IPv4 address.'), $propertyPath); static::ip($value, $flag | FILTER_FLAG_IPV4, static::generateMessage($message ?: 'Value "%s" was expected to be a valid IPv4 address.'), $propertyPath);
@ -2667,7 +2667,7 @@ class Assertion
* *
* @see http://php.net/manual/filter.filters.flags.php * @see http://php.net/manual/filter.filters.flags.php
*/ */
public static function ipv6($value, $flag = null, $message = null, string $propertyPath = null): bool public static function ipv6($value, $flag = null, $message = null, ?string $propertyPath = null): bool
{ {
static::ip($value, $flag | FILTER_FLAG_IPV6, static::generateMessage($message ?: 'Value "%s" was expected to be a valid IPv6 address.'), $propertyPath); static::ip($value, $flag | FILTER_FLAG_IPV6, static::generateMessage($message ?: 'Value "%s" was expected to be a valid IPv6 address.'), $propertyPath);
@ -2680,7 +2680,7 @@ class Assertion
* @param mixed $constant * @param mixed $constant
* @param string|callable|null $message * @param string|callable|null $message
*/ */
public static function defined($constant, $message = null, string $propertyPath = null): bool public static function defined($constant, $message = null, ?string $propertyPath = null): bool
{ {
if (!\defined($constant)) { if (!\defined($constant)) {
$message = \sprintf(static::generateMessage($message ?: 'Value "%s" expected to be a defined constant.'), $constant); $message = \sprintf(static::generateMessage($message ?: 'Value "%s" expected to be a defined constant.'), $constant);
@ -2699,7 +2699,7 @@ class Assertion
* *
* @throws AssertionFailedException * @throws AssertionFailedException
*/ */
public static function base64($value, $message = null, string $propertyPath = null): bool public static function base64($value, $message = null, ?string $propertyPath = null): bool
{ {
if (false === \base64_decode($value, true)) { if (false === \base64_decode($value, true)) {
$message = \sprintf(static::generateMessage($message ?: 'Value "%s" is not a valid base64 string.'), $value); $message = \sprintf(static::generateMessage($message ?: 'Value "%s" is not a valid base64 string.'), $value);

View file

@ -151,7 +151,7 @@ class AssertionChain
* @param mixed $value * @param mixed $value
* @param string|callable|null $defaultMessage * @param string|callable|null $defaultMessage
*/ */
public function __construct($value, $defaultMessage = null, string $defaultPropertyPath = null) public function __construct($value, $defaultMessage = null, ?string $defaultPropertyPath = null)
{ {
$this->value = $value; $this->value = $value;
$this->defaultMessage = $defaultMessage; $this->defaultMessage = $defaultMessage;

View file

@ -31,7 +31,7 @@ class InvalidArgumentException extends \InvalidArgumentException implements Asse
*/ */
private $constraints; private $constraints;
public function __construct($message, $code, string $propertyPath = null, $value = null, array $constraints = []) public function __construct($message, $code, ?string $propertyPath = null, $value = null, array $constraints = [])
{ {
parent::__construct($message, $code); parent::__construct($message, $code);

View file

@ -133,7 +133,7 @@ class LazyAssertion
* *
* @return static * @return static
*/ */
public function that($value, string $propertyPath = null, $defaultMessage = null) public function that($value, ?string $propertyPath = null, $defaultMessage = null)
{ {
$this->currentChainFailed = false; $this->currentChainFailed = false;
$this->thisChainTryAll = false; $this->thisChainTryAll = false;

View file

@ -32,7 +32,7 @@ namespace Assert;
* The assertion chain can be stateful, that means be careful when you reuse * The assertion chain can be stateful, that means be careful when you reuse
* it. You should never pass around the chain. * it. You should never pass around the chain.
*/ */
function that($value, $defaultMessage = null, string $defaultPropertyPath = null): AssertionChain function that($value, $defaultMessage = null, ?string $defaultPropertyPath = null): AssertionChain
{ {
return Assert::that($value, $defaultMessage, $defaultPropertyPath); return Assert::that($value, $defaultMessage, $defaultPropertyPath);
} }
@ -44,7 +44,7 @@ function that($value, $defaultMessage = null, string $defaultPropertyPath = null
* @param string|callable|null $defaultMessage * @param string|callable|null $defaultMessage
* @param string $defaultPropertyPath * @param string $defaultPropertyPath
*/ */
function thatAll($values, $defaultMessage = null, string $defaultPropertyPath = null): AssertionChain function thatAll($values, $defaultMessage = null, ?string $defaultPropertyPath = null): AssertionChain
{ {
return Assert::thatAll($values, $defaultMessage, $defaultPropertyPath); return Assert::thatAll($values, $defaultMessage, $defaultPropertyPath);
} }
@ -58,7 +58,7 @@ function thatAll($values, $defaultMessage = null, string $defaultPropertyPath =
* *
* @deprecated In favour of Assert::thatNullOr($value, $defaultMessage = null, $defaultPropertyPath = null) * @deprecated In favour of Assert::thatNullOr($value, $defaultMessage = null, $defaultPropertyPath = null)
*/ */
function thatNullOr($value, $defaultMessage = null, string $defaultPropertyPath = null): AssertionChain function thatNullOr($value, $defaultMessage = null, ?string $defaultPropertyPath = null): AssertionChain
{ {
return Assert::thatNullOr($value, $defaultMessage, $defaultPropertyPath); return Assert::thatNullOr($value, $defaultMessage, $defaultPropertyPath);
} }

File diff suppressed because it is too large Load diff

View file

@ -1,8 +1,8 @@
<?php return array( <?php return array(
'root' => array( 'root' => array(
'name' => 'ldap-account-manager/ldap-account-manager', 'name' => 'ldap-account-manager/ldap-account-manager',
'pretty_version' => '8.8', 'pretty_version' => '9.0',
'version' => '8.8.0.0', 'version' => '9.0.0.0',
'reference' => null, 'reference' => null,
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../../../../', 'install_path' => __DIR__ . '/../../../../',
@ -11,9 +11,9 @@
), ),
'versions' => array( 'versions' => array(
'beberlei/assert' => array( 'beberlei/assert' => array(
'pretty_version' => 'v3.3.2', 'pretty_version' => 'v3.3.3',
'version' => '3.3.2.0', 'version' => '3.3.3.0',
'reference' => 'cb70015c04be1baee6f5f5c953703347c0ac1655', 'reference' => 'b5fd8eacd8915a1b627b8bfc027803f1939734dd',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../beberlei/assert', 'install_path' => __DIR__ . '/../beberlei/assert',
'aliases' => array(), 'aliases' => array(),
@ -92,9 +92,9 @@
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'firebase/php-jwt' => array( 'firebase/php-jwt' => array(
'pretty_version' => 'v6.10.1', 'pretty_version' => 'v6.10.2',
'version' => '6.10.1.0', 'version' => '6.10.2.0',
'reference' => '500501c2ce893c824c801da135d02661199f60c5', 'reference' => '30c19ed0f3264cb660ea496895cfb6ef7ee3653b',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../firebase/php-jwt', 'install_path' => __DIR__ . '/../firebase/php-jwt',
'aliases' => array(), 'aliases' => array(),
@ -119,35 +119,35 @@
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'illuminate/collections' => array( 'illuminate/collections' => array(
'pretty_version' => 'v10.48.20', 'pretty_version' => 'v10.48.25',
'version' => '10.48.20.0', 'version' => '10.48.25.0',
'reference' => '37c863cffb345869dd134eff8e646bc82a19cc96', 'reference' => '48de3d6bc6aa779112ddcb608a3a96fc975d89d8',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../illuminate/collections', 'install_path' => __DIR__ . '/../illuminate/collections',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'illuminate/conditionable' => array( 'illuminate/conditionable' => array(
'pretty_version' => 'v10.48.20', 'pretty_version' => 'v10.48.25',
'version' => '10.48.20.0', 'version' => '10.48.25.0',
'reference' => 'd0958e4741fc9d6f516a552060fd1b829a85e009', 'reference' => '3ee34ac306fafc2a6f19cd7cd68c9af389e432a5',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../illuminate/conditionable', 'install_path' => __DIR__ . '/../illuminate/conditionable',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'illuminate/contracts' => array( 'illuminate/contracts' => array(
'pretty_version' => 'v10.48.20', 'pretty_version' => 'v10.48.25',
'version' => '10.48.20.0', 'version' => '10.48.25.0',
'reference' => '8d7152c4a1f5d9cf7da3e8b71f23e4556f6138ac', 'reference' => 'f90663a69f926105a70b78060a31f3c64e2d1c74',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../illuminate/contracts', 'install_path' => __DIR__ . '/../illuminate/contracts',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'illuminate/macroable' => array( 'illuminate/macroable' => array(
'pretty_version' => 'v10.48.20', 'pretty_version' => 'v10.48.25',
'version' => '10.48.20.0', 'version' => '10.48.25.0',
'reference' => 'dff667a46ac37b634dcf68909d9d41e94dc97c27', 'reference' => 'dff667a46ac37b634dcf68909d9d41e94dc97c27',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../illuminate/macroable', 'install_path' => __DIR__ . '/../illuminate/macroable',
@ -155,8 +155,8 @@
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'illuminate/pagination' => array( 'illuminate/pagination' => array(
'pretty_version' => 'v10.48.20', 'pretty_version' => 'v10.48.25',
'version' => '10.48.20.0', 'version' => '10.48.25.0',
'reference' => '616874b9607ff35925347e1710a8b5151858cdf2', 'reference' => '616874b9607ff35925347e1710a8b5151858cdf2',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../illuminate/pagination', 'install_path' => __DIR__ . '/../illuminate/pagination',
@ -164,17 +164,17 @@
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'illuminate/support' => array( 'illuminate/support' => array(
'pretty_version' => 'v10.48.20', 'pretty_version' => 'v10.48.25',
'version' => '10.48.20.0', 'version' => '10.48.25.0',
'reference' => '56c6d9895605b019e3debb9440454596ef99312a', 'reference' => '64b258f80175c658aef9e22dd3f2ba18c99b243c',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../illuminate/support', 'install_path' => __DIR__ . '/../illuminate/support',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'ldap-account-manager/ldap-account-manager' => array( 'ldap-account-manager/ldap-account-manager' => array(
'pretty_version' => '8.8', 'pretty_version' => '9.0',
'version' => '8.8.0.0', 'version' => '9.0.0.0',
'reference' => null, 'reference' => null,
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../../../../', 'install_path' => __DIR__ . '/../../../../',
@ -182,9 +182,9 @@
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'monolog/monolog' => array( 'monolog/monolog' => array(
'pretty_version' => '3.7.0', 'pretty_version' => '3.8.0',
'version' => '3.7.0.0', 'version' => '3.8.0.0',
'reference' => 'f4393b648b78a5408747de94fca38beb5f7e9ef8', 'reference' => '32e515fdc02cdafbe4593e30a9350d486b125b67',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../monolog/monolog', 'install_path' => __DIR__ . '/../monolog/monolog',
'aliases' => array(), 'aliases' => array(),
@ -230,27 +230,27 @@
), ),
), ),
'php-http/discovery' => array( 'php-http/discovery' => array(
'pretty_version' => '1.19.4', 'pretty_version' => '1.20.0',
'version' => '1.19.4.0', 'version' => '1.20.0.0',
'reference' => '0700efda8d7526335132360167315fdab3aeb599', 'reference' => '82fe4c73ef3363caed49ff8dd1539ba06044910d',
'type' => 'composer-plugin', 'type' => 'composer-plugin',
'install_path' => __DIR__ . '/../php-http/discovery', 'install_path' => __DIR__ . '/../php-http/discovery',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'phpmailer/phpmailer' => array( 'phpmailer/phpmailer' => array(
'pretty_version' => 'v6.9.1', 'pretty_version' => 'v6.9.3',
'version' => '6.9.1.0', 'version' => '6.9.3.0',
'reference' => '039de174cd9c17a8389754d3b877a2ed22743e18', 'reference' => '2f5c94fe7493efc213f643c23b1b1c249d40f47e',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../phpmailer/phpmailer', 'install_path' => __DIR__ . '/../phpmailer/phpmailer',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'phpseclib/phpseclib' => array( 'phpseclib/phpseclib' => array(
'pretty_version' => '3.0.41', 'pretty_version' => '3.0.42',
'version' => '3.0.41.0', 'version' => '3.0.42.0',
'reference' => '621c73f7dcb310b61de34d1da4c4204e8ace6ceb', 'reference' => 'db92f1b1987b12b13f248fe76c3a52cadb67bb98',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../phpseclib/phpseclib', 'install_path' => __DIR__ . '/../phpseclib/phpseclib',
'aliases' => array(), 'aliases' => array(),
@ -308,9 +308,9 @@
'psr/http-factory-implementation' => array( 'psr/http-factory-implementation' => array(
'dev_requirement' => false, 'dev_requirement' => false,
'provided' => array( 'provided' => array(
0 => '^1.0', 0 => '1.0',
1 => '*', 1 => '^1.0',
2 => '1.0', 2 => '*',
), ),
), ),
'psr/http-message' => array( 'psr/http-message' => array(
@ -325,8 +325,8 @@
'psr/http-message-implementation' => array( 'psr/http-message-implementation' => array(
'dev_requirement' => false, 'dev_requirement' => false,
'provided' => array( 'provided' => array(
0 => '*', 0 => '1.0',
1 => '1.0', 1 => '*',
), ),
), ),
'psr/http-server-handler' => array( 'psr/http-server-handler' => array(
@ -348,9 +348,9 @@
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'psr/log' => array( 'psr/log' => array(
'pretty_version' => '3.0.1', 'pretty_version' => '3.0.2',
'version' => '3.0.1.0', 'version' => '3.0.2.0',
'reference' => '79dff0b268932c640297f5208d6298f71855c03e', 'reference' => 'f16e1d5863e37f8d8c2a01719f5b34baa2b714d3',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../psr/log', 'install_path' => __DIR__ . '/../psr/log',
'aliases' => array(), 'aliases' => array(),
@ -399,27 +399,27 @@
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/deprecation-contracts' => array( 'symfony/deprecation-contracts' => array(
'pretty_version' => 'v3.5.0', 'pretty_version' => 'v3.5.1',
'version' => '3.5.0.0', 'version' => '3.5.1.0',
'reference' => '0e0d29ce1f20deffb4ab1b016a7257c4f1e789a1', 'reference' => '74c71c939a79f7d5bf3c1ce9f5ea37ba0114c6f6',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/deprecation-contracts', 'install_path' => __DIR__ . '/../symfony/deprecation-contracts',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/http-client' => array( 'symfony/http-client' => array(
'pretty_version' => 'v6.4.11', 'pretty_version' => 'v6.4.16',
'version' => '6.4.11.0', 'version' => '6.4.16.0',
'reference' => '4c92046bb788648ff1098cc66da69aa7eac8cb65', 'reference' => '60a113666fa67e598abace38e5f46a0954d8833d',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/http-client', 'install_path' => __DIR__ . '/../symfony/http-client',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/http-client-contracts' => array( 'symfony/http-client-contracts' => array(
'pretty_version' => 'v3.5.0', 'pretty_version' => 'v3.5.1',
'version' => '3.5.0.0', 'version' => '3.5.1.0',
'reference' => '20414d96f391677bf80078aa55baece78b82647d', 'reference' => 'c2f3ad828596624ca39ea40f83617ef51ca8bbf9',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/http-client-contracts', 'install_path' => __DIR__ . '/../symfony/http-client-contracts',
'aliases' => array(), 'aliases' => array(),
@ -432,81 +432,81 @@
), ),
), ),
'symfony/http-foundation' => array( 'symfony/http-foundation' => array(
'pretty_version' => 'v6.4.10', 'pretty_version' => 'v6.4.16',
'version' => '6.4.10.0', 'version' => '6.4.16.0',
'reference' => '117f1f20a7ade7bcea28b861fb79160a21a1e37b', 'reference' => '431771b7a6f662f1575b3cfc8fd7617aa9864d57',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/http-foundation', 'install_path' => __DIR__ . '/../symfony/http-foundation',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/polyfill-mbstring' => array( 'symfony/polyfill-mbstring' => array(
'pretty_version' => 'v1.30.0', 'pretty_version' => 'v1.31.0',
'version' => '1.30.0.0', 'version' => '1.31.0.0',
'reference' => 'fd22ab50000ef01661e2a31d850ebaa297f8e03c', 'reference' => '85181ba99b2345b0ef10ce42ecac37612d9fd341',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/polyfill-mbstring', 'install_path' => __DIR__ . '/../symfony/polyfill-mbstring',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/polyfill-php80' => array( 'symfony/polyfill-php80' => array(
'pretty_version' => 'v1.30.0', 'pretty_version' => 'v1.31.0',
'version' => '1.30.0.0', 'version' => '1.31.0.0',
'reference' => '77fa7995ac1b21ab60769b7323d600a991a90433', 'reference' => '60328e362d4c2c802a54fcbf04f9d3fb892b4cf8',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/polyfill-php80', 'install_path' => __DIR__ . '/../symfony/polyfill-php80',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/polyfill-php83' => array( 'symfony/polyfill-php83' => array(
'pretty_version' => 'v1.30.0', 'pretty_version' => 'v1.31.0',
'version' => '1.30.0.0', 'version' => '1.31.0.0',
'reference' => 'dbdcdf1a4dcc2743591f1079d0c35ab1e2dcbbc9', 'reference' => '2fb86d65e2d424369ad2905e83b236a8805ba491',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/polyfill-php83', 'install_path' => __DIR__ . '/../symfony/polyfill-php83',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/polyfill-uuid' => array( 'symfony/polyfill-uuid' => array(
'pretty_version' => 'v1.30.0', 'pretty_version' => 'v1.31.0',
'version' => '1.30.0.0', 'version' => '1.31.0.0',
'reference' => '2ba1f33797470debcda07fe9dce20a0003df18e9', 'reference' => '21533be36c24be3f4b1669c4725c7d1d2bab4ae2',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/polyfill-uuid', 'install_path' => __DIR__ . '/../symfony/polyfill-uuid',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/psr-http-message-bridge' => array( 'symfony/psr-http-message-bridge' => array(
'pretty_version' => 'v6.4.11', 'pretty_version' => 'v6.4.13',
'version' => '6.4.11.0', 'version' => '6.4.13.0',
'reference' => '74835ba54eca99a38f374f7a6d932fa510124773', 'reference' => 'c9cf83326a1074f83a738fc5320945abf7fb7fec',
'type' => 'symfony-bridge', 'type' => 'symfony-bridge',
'install_path' => __DIR__ . '/../symfony/psr-http-message-bridge', 'install_path' => __DIR__ . '/../symfony/psr-http-message-bridge',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/service-contracts' => array( 'symfony/service-contracts' => array(
'pretty_version' => 'v3.5.0', 'pretty_version' => 'v3.5.1',
'version' => '3.5.0.0', 'version' => '3.5.1.0',
'reference' => 'bd1d9e59a81d8fa4acdcea3f617c581f7475a80f', 'reference' => 'e53260aabf78fb3d63f8d79d69ece59f80d5eda0',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/service-contracts', 'install_path' => __DIR__ . '/../symfony/service-contracts',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/translation' => array( 'symfony/translation' => array(
'pretty_version' => 'v6.4.10', 'pretty_version' => 'v6.4.13',
'version' => '6.4.10.0', 'version' => '6.4.13.0',
'reference' => '94041203f8ac200ae9e7c6a18fa6137814ccecc9', 'reference' => 'bee9bfabfa8b4045a66bf82520e492cddbaffa66',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/translation', 'install_path' => __DIR__ . '/../symfony/translation',
'aliases' => array(), 'aliases' => array(),
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'symfony/translation-contracts' => array( 'symfony/translation-contracts' => array(
'pretty_version' => 'v3.5.0', 'pretty_version' => 'v3.5.1',
'version' => '3.5.0.0', 'version' => '3.5.1.0',
'reference' => 'b9d2189887bb6b2e0367a9fc7136c5239ab9b05a', 'reference' => '4667ff3bd513750603a09c8dedbea942487fb07c',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/translation-contracts', 'install_path' => __DIR__ . '/../symfony/translation-contracts',
'aliases' => array(), 'aliases' => array(),
@ -519,9 +519,9 @@
), ),
), ),
'symfony/uid' => array( 'symfony/uid' => array(
'pretty_version' => 'v6.4.11', 'pretty_version' => 'v6.4.13',
'version' => '6.4.11.0', 'version' => '6.4.13.0',
'reference' => '6a0394ad707de386547223948fac1e0f2805bc0b', 'reference' => '18eb207f0436a993fffbdd811b5b8fa35fa5e007',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../symfony/uid', 'install_path' => __DIR__ . '/../symfony/uid',
'aliases' => array(), 'aliases' => array(),
@ -537,9 +537,9 @@
'dev_requirement' => false, 'dev_requirement' => false,
), ),
'voku/portable-ascii' => array( 'voku/portable-ascii' => array(
'pretty_version' => '2.0.1', 'pretty_version' => '2.0.3',
'version' => '2.0.1.0', 'version' => '2.0.3.0',
'reference' => 'b56450eed252f6801410d810c8e1727224ae0743', 'reference' => 'b1d923f88091c6bf09699efcd7c8a1b1bfd7351d',
'type' => 'library', 'type' => 'library',
'install_path' => __DIR__ . '/../voku/portable-ascii', 'install_path' => __DIR__ . '/../voku/portable-ascii',
'aliases' => array(), 'aliases' => array(),

View file

@ -1,5 +1,13 @@
# Changelog # Changelog
## [6.10.2](https://github.com/firebase/php-jwt/compare/v6.10.1...v6.10.2) (2024-11-24)
### Bug Fixes
* Mitigate PHP8.4 deprecation warnings ([#570](https://github.com/firebase/php-jwt/issues/570)) ([76808fa](https://github.com/firebase/php-jwt/commit/76808fa227f3811aa5cdb3bf81233714b799a5b5))
* support php 8.4 ([#583](https://github.com/firebase/php-jwt/issues/583)) ([e3d68b0](https://github.com/firebase/php-jwt/commit/e3d68b044421339443c74199edd020e03fb1887e))
## [6.10.1](https://github.com/firebase/php-jwt/compare/v6.10.0...v6.10.1) (2024-05-18) ## [6.10.1](https://github.com/firebase/php-jwt/compare/v6.10.0...v6.10.1) (2024-05-18)

View file

@ -80,9 +80,9 @@ class CachedKeySet implements ArrayAccess
ClientInterface $httpClient, ClientInterface $httpClient,
RequestFactoryInterface $httpFactory, RequestFactoryInterface $httpFactory,
CacheItemPoolInterface $cache, CacheItemPoolInterface $cache,
int $expiresAfter = null, ?int $expiresAfter = null,
bool $rateLimit = false, bool $rateLimit = false,
string $defaultAlg = null ?string $defaultAlg = null
) { ) {
$this->jwksUri = $jwksUri; $this->jwksUri = $jwksUri;
$this->httpClient = $httpClient; $this->httpClient = $httpClient;
@ -180,7 +180,7 @@ class CachedKeySet implements ArrayAccess
$jwksResponse = $this->httpClient->sendRequest($request); $jwksResponse = $this->httpClient->sendRequest($request);
if ($jwksResponse->getStatusCode() !== 200) { if ($jwksResponse->getStatusCode() !== 200) {
throw new UnexpectedValueException( throw new UnexpectedValueException(
sprintf('HTTP Error: %d %s for URI "%s"', \sprintf('HTTP Error: %d %s for URI "%s"',
$jwksResponse->getStatusCode(), $jwksResponse->getStatusCode(),
$jwksResponse->getReasonPhrase(), $jwksResponse->getReasonPhrase(),
$this->jwksUri, $this->jwksUri,

View file

@ -52,7 +52,7 @@ class JWK
* *
* @uses parseKey * @uses parseKey
*/ */
public static function parseKeySet(array $jwks, string $defaultAlg = null): array public static function parseKeySet(array $jwks, ?string $defaultAlg = null): array
{ {
$keys = []; $keys = [];
@ -93,7 +93,7 @@ class JWK
* *
* @uses createPemFromModulusAndExponent * @uses createPemFromModulusAndExponent
*/ */
public static function parseKey(array $jwk, string $defaultAlg = null): ?Key public static function parseKey(array $jwk, ?string $defaultAlg = null): ?Key
{ {
if (empty($jwk)) { if (empty($jwk)) {
throw new InvalidArgumentException('JWK must not be empty'); throw new InvalidArgumentException('JWK must not be empty');
@ -212,7 +212,7 @@ class JWK
) )
); );
return sprintf( return \sprintf(
"-----BEGIN PUBLIC KEY-----\n%s\n-----END PUBLIC KEY-----\n", "-----BEGIN PUBLIC KEY-----\n%s\n-----END PUBLIC KEY-----\n",
wordwrap(base64_encode($pem), 64, "\n", true) wordwrap(base64_encode($pem), 64, "\n", true)
); );

View file

@ -96,7 +96,7 @@ class JWT
public static function decode( public static function decode(
string $jwt, string $jwt,
$keyOrKeyArray, $keyOrKeyArray,
stdClass &$headers = null ?stdClass &$headers = null
): stdClass { ): stdClass {
// Validate JWT // Validate JWT
$timestamp = \is_null(static::$timestamp) ? \time() : static::$timestamp; $timestamp = \is_null(static::$timestamp) ? \time() : static::$timestamp;
@ -200,11 +200,11 @@ class JWT
array $payload, array $payload,
$key, $key,
string $alg, string $alg,
string $keyId = null, ?string $keyId = null,
array $head = null ?array $head = null
): string { ): string {
$header = ['typ' => 'JWT']; $header = ['typ' => 'JWT'];
if (isset($head) && \is_array($head)) { if (isset($head)) {
$header = \array_merge($header, $head); $header = \array_merge($header, $head);
} }
$header['alg'] = $alg; $header['alg'] = $alg;
@ -387,12 +387,7 @@ class JWT
*/ */
public static function jsonEncode(array $input): string public static function jsonEncode(array $input): string
{ {
if (PHP_VERSION_ID >= 50400) {
$json = \json_encode($input, \JSON_UNESCAPED_SLASHES); $json = \json_encode($input, \JSON_UNESCAPED_SLASHES);
} else {
// PHP 5.3 only
$json = \json_encode($input);
}
if ($errno = \json_last_error()) { if ($errno = \json_last_error()) {
self::handleJsonError($errno); self::handleJsonError($errno);
} elseif ($json === 'null') { } elseif ($json === 'null') {

View file

@ -185,7 +185,7 @@ class Arr
* @param mixed $default * @param mixed $default
* @return mixed * @return mixed
*/ */
public static function first($array, callable $callback = null, $default = null) public static function first($array, ?callable $callback = null, $default = null)
{ {
if (is_null($callback)) { if (is_null($callback)) {
if (empty($array)) { if (empty($array)) {
@ -216,7 +216,7 @@ class Arr
* @param mixed $default * @param mixed $default
* @return mixed * @return mixed
*/ */
public static function last($array, callable $callback = null, $default = null) public static function last($array, ?callable $callback = null, $default = null)
{ {
if (is_null($callback)) { if (is_null($callback)) {
return empty($array) ? value($default) : end($array); return empty($array) ? value($default) : end($array);

View file

@ -382,7 +382,7 @@ class Collection implements ArrayAccess, CanBeEscapedWhenCastToString, Enumerabl
* @param (callable(TValue, TKey): bool)|null $callback * @param (callable(TValue, TKey): bool)|null $callback
* @return static * @return static
*/ */
public function filter(callable $callback = null) public function filter(?callable $callback = null)
{ {
if ($callback) { if ($callback) {
return new static(Arr::where($this->items, $callback)); return new static(Arr::where($this->items, $callback));
@ -400,7 +400,7 @@ class Collection implements ArrayAccess, CanBeEscapedWhenCastToString, Enumerabl
* @param TFirstDefault|(\Closure(): TFirstDefault) $default * @param TFirstDefault|(\Closure(): TFirstDefault) $default
* @return TValue|TFirstDefault * @return TValue|TFirstDefault
*/ */
public function first(callable $callback = null, $default = null) public function first(?callable $callback = null, $default = null)
{ {
return Arr::first($this->items, $callback, $default); return Arr::first($this->items, $callback, $default);
} }
@ -748,7 +748,7 @@ class Collection implements ArrayAccess, CanBeEscapedWhenCastToString, Enumerabl
* @param TLastDefault|(\Closure(): TLastDefault) $default * @param TLastDefault|(\Closure(): TLastDefault) $default
* @return TValue|TLastDefault * @return TValue|TLastDefault
*/ */
public function last(callable $callback = null, $default = null) public function last(?callable $callback = null, $default = null)
{ {
return Arr::last($this->items, $callback, $default); return Arr::last($this->items, $callback, $default);
} }

View file

@ -38,7 +38,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param callable|null $callback * @param callable|null $callback
* @return static * @return static
*/ */
public static function times($number, callable $callback = null); public static function times($number, ?callable $callback = null);
/** /**
* Create a collection with the given range. * Create a collection with the given range.
@ -296,7 +296,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param (callable(TValue): bool)|null $callback * @param (callable(TValue): bool)|null $callback
* @return static * @return static
*/ */
public function filter(callable $callback = null); public function filter(?callable $callback = null);
/** /**
* Apply the callback if the given "value" is (or resolves to) truthy. * Apply the callback if the given "value" is (or resolves to) truthy.
@ -308,7 +308,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param (callable($this): TWhenReturnType)|null $default * @param (callable($this): TWhenReturnType)|null $default
* @return $this|TWhenReturnType * @return $this|TWhenReturnType
*/ */
public function when($value, callable $callback = null, callable $default = null); public function when($value, ?callable $callback = null, ?callable $default = null);
/** /**
* Apply the callback if the collection is empty. * Apply the callback if the collection is empty.
@ -319,7 +319,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param (callable($this): TWhenEmptyReturnType)|null $default * @param (callable($this): TWhenEmptyReturnType)|null $default
* @return $this|TWhenEmptyReturnType * @return $this|TWhenEmptyReturnType
*/ */
public function whenEmpty(callable $callback, callable $default = null); public function whenEmpty(callable $callback, ?callable $default = null);
/** /**
* Apply the callback if the collection is not empty. * Apply the callback if the collection is not empty.
@ -330,7 +330,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param (callable($this): TWhenNotEmptyReturnType)|null $default * @param (callable($this): TWhenNotEmptyReturnType)|null $default
* @return $this|TWhenNotEmptyReturnType * @return $this|TWhenNotEmptyReturnType
*/ */
public function whenNotEmpty(callable $callback, callable $default = null); public function whenNotEmpty(callable $callback, ?callable $default = null);
/** /**
* Apply the callback if the given "value" is (or resolves to) truthy. * Apply the callback if the given "value" is (or resolves to) truthy.
@ -342,7 +342,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param (callable($this): TUnlessReturnType)|null $default * @param (callable($this): TUnlessReturnType)|null $default
* @return $this|TUnlessReturnType * @return $this|TUnlessReturnType
*/ */
public function unless($value, callable $callback, callable $default = null); public function unless($value, callable $callback, ?callable $default = null);
/** /**
* Apply the callback unless the collection is empty. * Apply the callback unless the collection is empty.
@ -353,7 +353,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param (callable($this): TUnlessEmptyReturnType)|null $default * @param (callable($this): TUnlessEmptyReturnType)|null $default
* @return $this|TUnlessEmptyReturnType * @return $this|TUnlessEmptyReturnType
*/ */
public function unlessEmpty(callable $callback, callable $default = null); public function unlessEmpty(callable $callback, ?callable $default = null);
/** /**
* Apply the callback unless the collection is not empty. * Apply the callback unless the collection is not empty.
@ -364,7 +364,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param (callable($this): TUnlessNotEmptyReturnType)|null $default * @param (callable($this): TUnlessNotEmptyReturnType)|null $default
* @return $this|TUnlessNotEmptyReturnType * @return $this|TUnlessNotEmptyReturnType
*/ */
public function unlessNotEmpty(callable $callback, callable $default = null); public function unlessNotEmpty(callable $callback, ?callable $default = null);
/** /**
* Filter items by the given key value pair. * Filter items by the given key value pair.
@ -476,7 +476,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param TFirstDefault|(\Closure(): TFirstDefault) $default * @param TFirstDefault|(\Closure(): TFirstDefault) $default
* @return TValue|TFirstDefault * @return TValue|TFirstDefault
*/ */
public function first(callable $callback = null, $default = null); public function first(?callable $callback = null, $default = null);
/** /**
* Get the first item by the given key value pair. * Get the first item by the given key value pair.
@ -618,7 +618,7 @@ interface Enumerable extends Arrayable, Countable, IteratorAggregate, Jsonable,
* @param TLastDefault|(\Closure(): TLastDefault) $default * @param TLastDefault|(\Closure(): TLastDefault) $default
* @return TValue|TLastDefault * @return TValue|TLastDefault
*/ */
public function last(callable $callback = null, $default = null); public function last(?callable $callback = null, $default = null);
/** /**
* Run a map over each of the items. * Run a map over each of the items.

View file

@ -428,7 +428,7 @@ class LazyCollection implements CanBeEscapedWhenCastToString, Enumerable
* @param (callable(TValue, TKey): bool)|null $callback * @param (callable(TValue, TKey): bool)|null $callback
* @return static * @return static
*/ */
public function filter(callable $callback = null) public function filter(?callable $callback = null)
{ {
if (is_null($callback)) { if (is_null($callback)) {
$callback = fn ($value) => (bool) $value; $callback = fn ($value) => (bool) $value;
@ -452,7 +452,7 @@ class LazyCollection implements CanBeEscapedWhenCastToString, Enumerable
* @param TFirstDefault|(\Closure(): TFirstDefault) $default * @param TFirstDefault|(\Closure(): TFirstDefault) $default
* @return TValue|TFirstDefault * @return TValue|TFirstDefault
*/ */
public function first(callable $callback = null, $default = null) public function first(?callable $callback = null, $default = null)
{ {
$iterator = $this->getIterator(); $iterator = $this->getIterator();
@ -732,7 +732,7 @@ class LazyCollection implements CanBeEscapedWhenCastToString, Enumerable
* @param TLastDefault|(\Closure(): TLastDefault) $default * @param TLastDefault|(\Closure(): TLastDefault) $default
* @return TValue|TLastDefault * @return TValue|TLastDefault
*/ */
public function last(callable $callback = null, $default = null) public function last(?callable $callback = null, $default = null)
{ {
$needle = $placeholder = new stdClass; $needle = $placeholder = new stdClass;

View file

@ -164,7 +164,7 @@ trait EnumeratesValues
* @param (callable(int): TTimesValue)|null $callback * @param (callable(int): TTimesValue)|null $callback
* @return static<int, TTimesValue> * @return static<int, TTimesValue>
*/ */
public static function times($number, callable $callback = null) public static function times($number, ?callable $callback = null)
{ {
if ($number < 1) { if ($number < 1) {
return new static; return new static;
@ -534,7 +534,7 @@ trait EnumeratesValues
* @param (callable($this): TWhenEmptyReturnType)|null $default * @param (callable($this): TWhenEmptyReturnType)|null $default
* @return $this|TWhenEmptyReturnType * @return $this|TWhenEmptyReturnType
*/ */
public function whenEmpty(callable $callback, callable $default = null) public function whenEmpty(callable $callback, ?callable $default = null)
{ {
return $this->when($this->isEmpty(), $callback, $default); return $this->when($this->isEmpty(), $callback, $default);
} }
@ -548,7 +548,7 @@ trait EnumeratesValues
* @param (callable($this): TWhenNotEmptyReturnType)|null $default * @param (callable($this): TWhenNotEmptyReturnType)|null $default
* @return $this|TWhenNotEmptyReturnType * @return $this|TWhenNotEmptyReturnType
*/ */
public function whenNotEmpty(callable $callback, callable $default = null) public function whenNotEmpty(callable $callback, ?callable $default = null)
{ {
return $this->when($this->isNotEmpty(), $callback, $default); return $this->when($this->isNotEmpty(), $callback, $default);
} }
@ -562,7 +562,7 @@ trait EnumeratesValues
* @param (callable($this): TUnlessEmptyReturnType)|null $default * @param (callable($this): TUnlessEmptyReturnType)|null $default
* @return $this|TUnlessEmptyReturnType * @return $this|TUnlessEmptyReturnType
*/ */
public function unlessEmpty(callable $callback, callable $default = null) public function unlessEmpty(callable $callback, ?callable $default = null)
{ {
return $this->whenNotEmpty($callback, $default); return $this->whenNotEmpty($callback, $default);
} }
@ -576,7 +576,7 @@ trait EnumeratesValues
* @param (callable($this): TUnlessNotEmptyReturnType)|null $default * @param (callable($this): TUnlessNotEmptyReturnType)|null $default
* @return $this|TUnlessNotEmptyReturnType * @return $this|TUnlessNotEmptyReturnType
*/ */
public function unlessNotEmpty(callable $callback, callable $default = null) public function unlessNotEmpty(callable $callback, ?callable $default = null)
{ {
return $this->whenEmpty($callback, $default); return $this->whenEmpty($callback, $default);
} }

View file

@ -18,7 +18,7 @@ trait Conditionable
* @param (callable($this, TWhenParameter): TWhenReturnType)|null $default * @param (callable($this, TWhenParameter): TWhenReturnType)|null $default
* @return $this|TWhenReturnType * @return $this|TWhenReturnType
*/ */
public function when($value = null, callable $callback = null, callable $default = null) public function when($value = null, ?callable $callback = null, ?callable $default = null)
{ {
$value = $value instanceof Closure ? $value($this) : $value; $value = $value instanceof Closure ? $value($this) : $value;
@ -50,7 +50,7 @@ trait Conditionable
* @param (callable($this, TUnlessParameter): TUnlessReturnType)|null $default * @param (callable($this, TUnlessParameter): TUnlessReturnType)|null $default
* @return $this|TUnlessReturnType * @return $this|TUnlessReturnType
*/ */
public function unless($value = null, callable $callback = null, callable $default = null) public function unless($value = null, ?callable $callback = null, ?callable $default = null)
{ {
$value = $value instanceof Closure ? $value($this) : $value; $value = $value instanceof Closure ? $value($this) : $value;

View file

@ -29,7 +29,7 @@ interface Gate
* @param array|null $abilities * @param array|null $abilities
* @return $this * @return $this
*/ */
public function resource($name, $class, array $abilities = null); public function resource($name, $class, ?array $abilities = null);
/** /**
* Define a policy class for a given class type. * Define a policy class for a given class type.

View file

@ -48,7 +48,7 @@ interface PasswordBroker
* @param \Closure|null $callback * @param \Closure|null $callback
* @return string * @return string
*/ */
public function sendResetLink(array $credentials, Closure $callback = null); public function sendResetLink(array $credentials, ?Closure $callback = null);
/** /**
* Reset the password for the given token. * Reset the password for the given token.

View file

@ -197,7 +197,7 @@ interface Container extends ContainerInterface
* @param \Closure|null $callback * @param \Closure|null $callback
* @return void * @return void
*/ */
public function beforeResolving($abstract, Closure $callback = null); public function beforeResolving($abstract, ?Closure $callback = null);
/** /**
* Register a new resolving callback. * Register a new resolving callback.
@ -206,7 +206,7 @@ interface Container extends ContainerInterface
* @param \Closure|null $callback * @param \Closure|null $callback
* @return void * @return void
*/ */
public function resolving($abstract, Closure $callback = null); public function resolving($abstract, ?Closure $callback = null);
/** /**
* Register a new after resolving callback. * Register a new after resolving callback.
@ -215,5 +215,5 @@ interface Container extends ContainerInterface
* @param \Closure|null $callback * @param \Closure|null $callback
* @return void * @return void
*/ */
public function afterResolving($abstract, Closure $callback = null); public function afterResolving($abstract, ?Closure $callback = null);
} }

View file

@ -60,5 +60,5 @@ interface InvokedProcess
* @param callable|null $output * @param callable|null $output
* @return \Illuminate\Console\Process\ProcessResult * @return \Illuminate\Console\Process\ProcessResult
*/ */
public function wait(callable $output = null); public function wait(?callable $output = null);
} }

View file

@ -52,7 +52,7 @@ interface ProcessResult
* @param callable|null $callback * @param callable|null $callback
* @return $this * @return $this
*/ */
public function throw(callable $callback = null); public function throw(?callable $callback = null);
/** /**
* Throw an exception if the process failed and the given condition is true. * Throw an exception if the process failed and the given condition is true.
@ -61,5 +61,5 @@ interface ProcessResult
* @param callable|null $callback * @param callable|null $callback
* @return $this * @return $this
*/ */
public function throwIf(bool $condition, callable $callback = null); public function throwIf(bool $condition, ?callable $callback = null);
} }

View file

@ -63,7 +63,7 @@ class Composer
* @param string|null $composerBinary * @param string|null $composerBinary
* @return bool * @return bool
*/ */
public function requirePackages(array $packages, bool $dev = false, Closure|OutputInterface $output = null, $composerBinary = null) public function requirePackages(array $packages, bool $dev = false, Closure|OutputInterface|null $output = null, $composerBinary = null)
{ {
$command = collect([ $command = collect([
...$this->findComposer($composerBinary), ...$this->findComposer($composerBinary),
@ -92,7 +92,7 @@ class Composer
* @param string|null $composerBinary * @param string|null $composerBinary
* @return bool * @return bool
*/ */
public function removePackages(array $packages, bool $dev = false, Closure|OutputInterface $output = null, $composerBinary = null) public function removePackages(array $packages, bool $dev = false, Closure|OutputInterface|null $output = null, $composerBinary = null)
{ {
$command = collect([ $command = collect([
...$this->findComposer($composerBinary), ...$this->findComposer($composerBinary),

View file

@ -60,7 +60,7 @@ class Bus extends Facade
* @param \Illuminate\Bus\BatchRepository|null $batchRepository * @param \Illuminate\Bus\BatchRepository|null $batchRepository
* @return \Illuminate\Support\Testing\Fakes\BusFake * @return \Illuminate\Support\Testing\Fakes\BusFake
*/ */
public static function fake($jobsToFake = [], BatchRepository $batchRepository = null) public static function fake($jobsToFake = [], ?BatchRepository $batchRepository = null)
{ {
$actualDispatcher = static::isFake() $actualDispatcher = static::isFake()
? static::getFacadeRoot()->dispatcher ? static::getFacadeRoot()->dispatcher

View file

@ -65,7 +65,7 @@ class Process extends Facade
* @param \Closure|array|null $callback * @param \Closure|array|null $callback
* @return \Illuminate\Process\Factory * @return \Illuminate\Process\Factory
*/ */
public static function fake(Closure|array $callback = null) public static function fake(Closure|array|null $callback = null)
{ {
return tap(static::getFacadeRoot(), function ($fake) use ($callback) { return tap(static::getFacadeRoot(), function ($fake) use ($callback) {
static::swap($fake->fake($callback)); static::swap($fake->fake($callback));

View file

@ -959,7 +959,7 @@ class Str
* @param callable|null $factory * @param callable|null $factory
* @return void * @return void
*/ */
public static function createRandomStringsUsing(callable $factory = null) public static function createRandomStringsUsing(?callable $factory = null)
{ {
static::$randomStringFactory = $factory; static::$randomStringFactory = $factory;
} }
@ -1665,7 +1665,7 @@ class Str
* @param callable|null $factory * @param callable|null $factory
* @return void * @return void
*/ */
public static function createUuidsUsing(callable $factory = null) public static function createUuidsUsing(?callable $factory = null)
{ {
static::$uuidFactory = $factory; static::$uuidFactory = $factory;
} }
@ -1710,7 +1710,7 @@ class Str
* @param \Closure|null $callback * @param \Closure|null $callback
* @return \Ramsey\Uuid\UuidInterface * @return \Ramsey\Uuid\UuidInterface
*/ */
public static function freezeUuids(Closure $callback = null) public static function freezeUuids(?Closure $callback = null)
{ {
$uuid = Str::uuid(); $uuid = Str::uuid();
@ -1772,7 +1772,7 @@ class Str
* @param callable|null $factory * @param callable|null $factory
* @return void * @return void
*/ */
public static function createUlidsUsing(callable $factory = null) public static function createUlidsUsing(?callable $factory = null)
{ {
static::$ulidFactory = $factory; static::$ulidFactory = $factory;
} }
@ -1817,7 +1817,7 @@ class Str
* @param Closure|null $callback * @param Closure|null $callback
* @return Ulid * @return Ulid
*/ */
public static function freezeUlids(Closure $callback = null) public static function freezeUlids(?Closure $callback = null)
{ {
$ulid = Str::ulid(); $ulid = Str::ulid();

View file

@ -88,7 +88,7 @@ class BusFake implements Fake, QueueingDispatcher
* @param \Illuminate\Bus\BatchRepository|null $batchRepository * @param \Illuminate\Bus\BatchRepository|null $batchRepository
* @return void * @return void
*/ */
public function __construct(QueueingDispatcher $dispatcher, $jobsToFake = [], BatchRepository $batchRepository = null) public function __construct(QueueingDispatcher $dispatcher, $jobsToFake = [], ?BatchRepository $batchRepository = null)
{ {
$this->dispatcher = $dispatcher; $this->dispatcher = $dispatcher;
$this->jobsToFake = Arr::wrap($jobsToFake); $this->jobsToFake = Arr::wrap($jobsToFake);

View file

@ -296,7 +296,7 @@ class NotificationFake implements Fake, NotificationDispatcher, NotificationFact
* @param array|null $channels * @param array|null $channels
* @return void * @return void
*/ */
public function sendNow($notifiables, $notification, array $channels = null) public function sendNow($notifiables, $notification, ?array $channels = null)
{ {
if (! $notifiables instanceof Collection && ! is_array($notifiables)) { if (! $notifiables instanceof Collection && ! is_array($notifiables)) {
$notifiables = [$notifiables]; $notifiables = [$notifiables];

View file

@ -280,7 +280,7 @@ class ValidatedInput implements ValidatedData
* @param callable|null $default * @param callable|null $default
* @return $this|mixed * @return $this|mixed
*/ */
public function whenHas($key, callable $callback, callable $default = null) public function whenHas($key, callable $callback, ?callable $default = null)
{ {
if ($this->has($key)) { if ($this->has($key)) {
return $callback(data_get($this->all(), $key)) ?: $this; return $callback(data_get($this->all(), $key)) ?: $this;
@ -358,7 +358,7 @@ class ValidatedInput implements ValidatedData
* @param callable|null $default * @param callable|null $default
* @return $this|mixed * @return $this|mixed
*/ */
public function whenFilled($key, callable $callback, callable $default = null) public function whenFilled($key, callable $callback, ?callable $default = null)
{ {
if ($this->filled($key)) { if ($this->filled($key)) {
return $callback(data_get($this->all(), $key)) ?: $this; return $callback(data_get($this->all(), $key)) ?: $this;
@ -379,7 +379,7 @@ class ValidatedInput implements ValidatedData
* @param callable|null $default * @param callable|null $default
* @return $this|mixed * @return $this|mixed
*/ */
public function whenMissing($key, callable $callback, callable $default = null) public function whenMissing($key, callable $callback, ?callable $default = null)
{ {
if ($this->missing($key)) { if ($this->missing($key)) {
return $callback(data_get($this->all(), $key)) ?: $this; return $callback(data_get($this->all(), $key)) ?: $this;

View file

@ -187,7 +187,7 @@ if (! function_exists('optional')) {
* @param callable|null $callback * @param callable|null $callback
* @return mixed * @return mixed
*/ */
function optional($value = null, callable $callback = null) function optional($value = null, ?callable $callback = null)
{ {
if (is_null($callback)) { if (is_null($callback)) {
return new Optional($value); return new Optional($value);
@ -427,7 +427,7 @@ if (! function_exists('with')) {
* @param (callable(TValue): (TReturn))|null $callback * @param (callable(TValue): (TReturn))|null $callback
* @return ($callback is null ? TValue : TReturn) * @return ($callback is null ? TValue : TReturn)
*/ */
function with($value, callable $callback = null) function with($value, ?callable $callback = null)
{ {
return is_null($callback) ? $value : $callback($value); return is_null($callback) ? $value : $callback($value);
} }

View file

@ -1,3 +1,17 @@
### 3.8.0 (2024-11-12)
* Added `$fileOpenMode` param to `StreamHandler` to define a custom fopen mode to open the log file (#1913)
* Fixed PHP 8.4 deprecation notices (#1903)
* Added ability to extend/override `IntrospectionProcessor` (#1899)
* Added `$timeout` param to `ProcessHandler` to configure the stream_select() timeout to avoid blocking too long (default is 1.0 sec) (#1916)
* Fixed JsonFormatter batch handling to normalize records individually to make sure they look the same as if they were handled one by one (#1906)
* Fixed `StreamHandler` handling of write failures so that it now closes/reopens the stream and retries the write once before failing (#1882)
* Fixed `StreamHandler` error handler causing issues if a stream handler triggers an error (#1866)
* Fixed `StreamHandler::reset` not closing the stream, so that it would fail to write in some cases with long running processes (#1862)
* Fixed `RotatingFileHandler` issue where rotation does not happen in some long running processes (#1905)
* Fixed `JsonFormatter` handling of incomplete classes (#1834)
* Fixed `RotatingFileHandler` bug where rotation could sometimes not happen correctly (#1905)
### 3.7.0 (2024-06-28) ### 3.7.0 (2024-06-28)
* Added `NormalizerFormatter->setBasePath(...)` (and `JsonFormatter` by extension) that allows removing the project's path from the stack trace output (47e301d3e) * Added `NormalizerFormatter->setBasePath(...)` (and `JsonFormatter` by extension) that allows removing the project's path from the stack trace output (47e301d3e)
@ -122,6 +136,14 @@ New deprecations:
value equal to what `Logger::WARNING` was giving you. value equal to what `Logger::WARNING` was giving you.
- `Logger::getLevelName()` is now deprecated. - `Logger::getLevelName()` is now deprecated.
### 2.10.0 (2024-11-12)
* Added `$fileOpenMode` to `StreamHandler` to define a custom fopen mode to open the log file (#1913)
* Fixed `StreamHandler` handling of write failures so that it now closes/reopens the stream and retries the write once before failing (#1882)
* Fixed `StreamHandler` error handler causing issues if a stream handler triggers an error (#1866)
* Fixed `JsonFormatter` handling of incomplete classes (#1834)
* Fixed `RotatingFileHandler` bug where rotation could sometimes not happen correctly (#1905)
### 2.9.3 (2024-04-12) ### 2.9.3 (2024-04-12)
* Fixed PHP 8.4 deprecation warnings (#1874) * Fixed PHP 8.4 deprecation warnings (#1874)

View file

@ -106,7 +106,6 @@ Bugs and feature request are tracked on [GitHub](https://github.com/Seldaek/mono
- [Lumen](http://lumen.laravel.com/) comes out of the box with Monolog. - [Lumen](http://lumen.laravel.com/) comes out of the box with Monolog.
- [PPI](https://github.com/ppi/framework) comes out of the box with Monolog. - [PPI](https://github.com/ppi/framework) comes out of the box with Monolog.
- [CakePHP](http://cakephp.org/) is usable with Monolog via the [cakephp-monolog](https://github.com/jadb/cakephp-monolog) plugin. - [CakePHP](http://cakephp.org/) is usable with Monolog via the [cakephp-monolog](https://github.com/jadb/cakephp-monolog) plugin.
- [Slim](http://www.slimframework.com/) is usable with Monolog via the [Slim-Monolog](https://github.com/Flynsarmy/Slim-Monolog) log writer.
- [XOOPS 2.6](http://xoops.org/) comes out of the box with Monolog. - [XOOPS 2.6](http://xoops.org/) comes out of the box with Monolog.
- [Aura.Web_Project](https://github.com/auraphp/Aura.Web_Project) comes out of the box with Monolog. - [Aura.Web_Project](https://github.com/auraphp/Aura.Web_Project) comes out of the box with Monolog.
- [Nette Framework](http://nette.org/en/) is usable with Monolog via the [contributte/monolog](https://github.com/contributte/monolog) or [orisai/nette-monolog](https://github.com/orisai/nette-monolog) extensions. - [Nette Framework](http://nette.org/en/) is usable with Monolog via the [contributte/monolog](https://github.com/contributte/monolog) or [orisai/nette-monolog](https://github.com/orisai/nette-monolog) extensions.

View file

@ -26,12 +26,14 @@
"guzzlehttp/psr7": "^2.2", "guzzlehttp/psr7": "^2.2",
"mongodb/mongodb": "^1.8", "mongodb/mongodb": "^1.8",
"php-amqplib/php-amqplib": "~2.4 || ^3", "php-amqplib/php-amqplib": "~2.4 || ^3",
"phpstan/phpstan": "^1.9", "php-console/php-console": "^3.1.8",
"phpstan/phpstan-deprecation-rules": "^1.0", "phpstan/phpstan": "^2",
"phpstan/phpstan-strict-rules": "^1.4", "phpstan/phpstan-deprecation-rules": "^2",
"phpunit/phpunit": "^10.5.17", "phpstan/phpstan-strict-rules": "^2",
"phpunit/phpunit": "^10.5.17 || ^11.0.7",
"predis/predis": "^1.1 || ^2", "predis/predis": "^1.1 || ^2",
"ruflin/elastica": "^7", "rollbar/rollbar": "^4.0",
"ruflin/elastica": "^7 || ^8",
"symfony/mailer": "^5.4 || ^6", "symfony/mailer": "^5.4 || ^6",
"symfony/mime": "^5.4 || ^6" "symfony/mime": "^5.4 || ^6"
}, },
@ -72,6 +74,9 @@
"config": { "config": {
"lock": false, "lock": false,
"sort-packages": true, "sort-packages": true,
"platform-check": false "platform-check": false,
"allow-plugins": {
"php-http/discovery": false
}
} }
} }

View file

@ -167,7 +167,7 @@ class ErrorHandler
E_USER_ERROR => LogLevel::ERROR, E_USER_ERROR => LogLevel::ERROR,
E_USER_WARNING => LogLevel::WARNING, E_USER_WARNING => LogLevel::WARNING,
E_USER_NOTICE => LogLevel::NOTICE, E_USER_NOTICE => LogLevel::NOTICE,
E_STRICT => LogLevel::NOTICE, 2048 => LogLevel::NOTICE, // E_STRICT
E_RECOVERABLE_ERROR => LogLevel::ERROR, E_RECOVERABLE_ERROR => LogLevel::ERROR,
E_DEPRECATED => LogLevel::NOTICE, E_DEPRECATED => LogLevel::NOTICE,
E_USER_DEPRECATED => LogLevel::NOTICE, E_USER_DEPRECATED => LogLevel::NOTICE,
@ -269,7 +269,7 @@ class ErrorHandler
E_USER_ERROR => 'E_USER_ERROR', E_USER_ERROR => 'E_USER_ERROR',
E_USER_WARNING => 'E_USER_WARNING', E_USER_WARNING => 'E_USER_WARNING',
E_USER_NOTICE => 'E_USER_NOTICE', E_USER_NOTICE => 'E_USER_NOTICE',
E_STRICT => 'E_STRICT', 2048 => 'E_STRICT',
E_RECOVERABLE_ERROR => 'E_RECOVERABLE_ERROR', E_RECOVERABLE_ERROR => 'E_RECOVERABLE_ERROR',
E_DEPRECATED => 'E_DEPRECATED', E_DEPRECATED => 'E_DEPRECATED',
E_USER_DEPRECATED => 'E_USER_DEPRECATED', E_USER_DEPRECATED => 'E_USER_DEPRECATED',

View file

@ -34,8 +34,6 @@ class ElasticaFormatter extends NormalizerFormatter
/** /**
* @param string $index Elastic Search index name * @param string $index Elastic Search index name
* @param ?string $type Elastic Search document type, deprecated as of Elastica 7 * @param ?string $type Elastic Search document type, deprecated as of Elastica 7
*
* @throws \RuntimeException If the function json_encode does not exist
*/ */
public function __construct(string $index, ?string $type) public function __construct(string $index, ?string $type)
{ {

View file

@ -34,8 +34,6 @@ class ElasticsearchFormatter extends NormalizerFormatter
/** /**
* @param string $index Elasticsearch index name * @param string $index Elasticsearch index name
* @param string $type Elasticsearch record type * @param string $type Elasticsearch record type
*
* @throws \RuntimeException If the function json_encode does not exist
*/ */
public function __construct(string $index, string $type) public function __construct(string $index, string $type)
{ {

View file

@ -42,15 +42,8 @@ class FluentdFormatter implements FormatterInterface
*/ */
protected bool $levelTag = false; protected bool $levelTag = false;
/**
* @throws \RuntimeException If the function json_encode does not exist
*/
public function __construct(bool $levelTag = false) public function __construct(bool $levelTag = false)
{ {
if (!\function_exists('json_encode')) {
throw new \RuntimeException('PHP\'s json extension is required to use Monolog\'s FluentdUnixFormatter');
}
$this->levelTag = $levelTag; $this->levelTag = $levelTag;
} }

View file

@ -88,11 +88,11 @@ class GelfMessageFormatter extends NormalizerFormatter
{ {
$context = $extra = []; $context = $extra = [];
if (isset($record->context)) { if (isset($record->context)) {
/** @var mixed[] $context */ /** @var array<array<mixed>|bool|float|int|string|null> $context */
$context = parent::normalize($record->context); $context = parent::normalize($record->context);
} }
if (isset($record->extra)) { if (isset($record->extra)) {
/** @var mixed[] $extra */ /** @var array<array<mixed>|bool|float|int|string|null> $extra */
$extra = parent::normalize($record->extra); $extra = parent::normalize($record->extra);
} }

View file

@ -43,7 +43,6 @@ class HtmlFormatter extends NormalizerFormatter
/** /**
* @param string|null $dateFormat The format of the timestamp: one supported by DateTime::format * @param string|null $dateFormat The format of the timestamp: one supported by DateTime::format
* @throws \RuntimeException If the function json_encode does not exist
*/ */
public function __construct(?string $dateFormat = null) public function __construct(?string $dateFormat = null)
{ {

View file

@ -38,8 +38,6 @@ class JsonFormatter extends NormalizerFormatter
/** /**
* @param self::BATCH_MODE_* $batchMode * @param self::BATCH_MODE_* $batchMode
*
* @throws \RuntimeException If the function json_encode does not exist
*/ */
public function __construct(int $batchMode = self::BATCH_MODE_JSON, bool $appendNewline = true, bool $ignoreEmptyContextAndExtra = false, bool $includeStacktraces = false) public function __construct(int $batchMode = self::BATCH_MODE_JSON, bool $appendNewline = true, bool $ignoreEmptyContextAndExtra = false, bool $includeStacktraces = false)
{ {
@ -76,22 +74,7 @@ class JsonFormatter extends NormalizerFormatter
*/ */
public function format(LogRecord $record): string public function format(LogRecord $record): string
{ {
$normalized = parent::format($record); $normalized = $this->normalizeRecord($record);
if (isset($normalized['context']) && $normalized['context'] === []) {
if ($this->ignoreEmptyContextAndExtra) {
unset($normalized['context']);
} else {
$normalized['context'] = new \stdClass;
}
}
if (isset($normalized['extra']) && $normalized['extra'] === []) {
if ($this->ignoreEmptyContextAndExtra) {
unset($normalized['extra']);
} else {
$normalized['extra'] = new \stdClass;
}
}
return $this->toJson($normalized, true) . ($this->appendNewline ? "\n" : ''); return $this->toJson($normalized, true) . ($this->appendNewline ? "\n" : '');
} }
@ -117,6 +100,31 @@ class JsonFormatter extends NormalizerFormatter
return $this; return $this;
} }
/**
* @return array<array<mixed>|bool|float|int|\stdClass|string|null>
*/
protected function normalizeRecord(LogRecord $record): array
{
$normalized = parent::normalizeRecord($record);
if (isset($normalized['context']) && $normalized['context'] === []) {
if ($this->ignoreEmptyContextAndExtra) {
unset($normalized['context']);
} else {
$normalized['context'] = new \stdClass;
}
}
if (isset($normalized['extra']) && $normalized['extra'] === []) {
if ($this->ignoreEmptyContextAndExtra) {
unset($normalized['extra']);
} else {
$normalized['extra'] = new \stdClass;
}
}
return $normalized;
}
/** /**
* Return a JSON-encoded array of records. * Return a JSON-encoded array of records.
* *
@ -124,7 +132,9 @@ class JsonFormatter extends NormalizerFormatter
*/ */
protected function formatBatchJson(array $records): string protected function formatBatchJson(array $records): string
{ {
return $this->toJson($this->normalize($records), true); $formatted = array_map(fn (LogRecord $record) => $this->normalizeRecord($record), $records);
return $this->toJson($formatted, true);
} }
/** /**
@ -206,7 +216,7 @@ class JsonFormatter extends NormalizerFormatter
* Normalizes given exception with or without its own stack trace based on * Normalizes given exception with or without its own stack trace based on
* `includeStacktraces` property. * `includeStacktraces` property.
* *
* @inheritDoc * @return array<string, string|int|array<string|int|array<string>>>|string
*/ */
protected function normalizeException(Throwable $e, int $depth = 0): array protected function normalizeException(Throwable $e, int $depth = 0): array
{ {

View file

@ -40,8 +40,6 @@ class LineFormatter extends NormalizerFormatter
* @param string|null $format The format of the message * @param string|null $format The format of the message
* @param string|null $dateFormat The format of the timestamp: one supported by DateTime::format * @param string|null $dateFormat The format of the timestamp: one supported by DateTime::format
* @param bool $allowInlineLineBreaks Whether to allow inline line breaks in log entries * @param bool $allowInlineLineBreaks Whether to allow inline line breaks in log entries
*
* @throws \RuntimeException If the function json_encode does not exist
*/ */
public function __construct(?string $format = null, ?string $dateFormat = null, bool $allowInlineLineBreaks = false, bool $ignoreEmptyContextAndExtra = false, bool $includeStacktraces = false) public function __construct(?string $format = null, ?string $dateFormat = null, bool $allowInlineLineBreaks = false, bool $ignoreEmptyContextAndExtra = false, bool $includeStacktraces = false)
{ {
@ -177,7 +175,7 @@ class LineFormatter extends NormalizerFormatter
if (null === $output) { if (null === $output) {
$pcreErrorCode = preg_last_error(); $pcreErrorCode = preg_last_error();
throw new \RuntimeException('Failed to run preg_replace: ' . $pcreErrorCode . ' / ' . Utils::pcreLastErrorMessage($pcreErrorCode)); throw new \RuntimeException('Failed to run preg_replace: ' . $pcreErrorCode . ' / ' . preg_last_error_msg());
} }
} }
@ -245,7 +243,7 @@ class LineFormatter extends NormalizerFormatter
if (null === $str) { if (null === $str) {
$pcreErrorCode = preg_last_error(); $pcreErrorCode = preg_last_error();
throw new \RuntimeException('Failed to run preg_replace: ' . $pcreErrorCode . ' / ' . Utils::pcreLastErrorMessage($pcreErrorCode)); throw new \RuntimeException('Failed to run preg_replace: ' . $pcreErrorCode . ' / ' . preg_last_error_msg());
} }
} }
@ -311,6 +309,6 @@ class LineFormatter extends NormalizerFormatter
private function stacktracesParserCustom(string $trace): string private function stacktracesParserCustom(string $trace): string
{ {
return implode("\n", array_filter(array_map($this->stacktracesParser, explode("\n", $trace)))); return implode("\n", array_filter(array_map($this->stacktracesParser, explode("\n", $trace)), fn ($line) => $line !== false && $line !== ''));
} }
} }

View file

@ -48,8 +48,6 @@ class LogstashFormatter extends NormalizerFormatter
* @param string|null $systemName The system/machine name, used as the "source" field of logstash, defaults to the hostname of the machine * @param string|null $systemName The system/machine name, used as the "source" field of logstash, defaults to the hostname of the machine
* @param string $extraKey The key for extra keys inside logstash "fields", defaults to extra * @param string $extraKey The key for extra keys inside logstash "fields", defaults to extra
* @param string $contextKey The key for context keys inside logstash "fields", defaults to context * @param string $contextKey The key for context keys inside logstash "fields", defaults to context
*
* @throws \RuntimeException If the function json_encode does not exist
*/ */
public function __construct(string $applicationName, ?string $systemName = null, string $extraKey = 'extra', string $contextKey = 'context') public function __construct(string $applicationName, ?string $systemName = null, string $extraKey = 'extra', string $contextKey = 'context')
{ {

View file

@ -150,7 +150,7 @@ class MongoDBFormatter implements FormatterInterface
{ {
$milliseconds = floor(((float) $value->format('U.u')) * 1000); $milliseconds = floor(((float) $value->format('U.u')) * 1000);
$milliseconds = (PHP_INT_SIZE == 8) //64-bit OS? $milliseconds = (PHP_INT_SIZE === 8) //64-bit OS?
? (int) $milliseconds ? (int) $milliseconds
: (string) $milliseconds; : (string) $milliseconds;

View file

@ -35,14 +35,10 @@ class NormalizerFormatter implements FormatterInterface
/** /**
* @param string|null $dateFormat The format of the timestamp: one supported by DateTime::format * @param string|null $dateFormat The format of the timestamp: one supported by DateTime::format
* @throws \RuntimeException If the function json_encode does not exist
*/ */
public function __construct(?string $dateFormat = null) public function __construct(?string $dateFormat = null)
{ {
$this->dateFormat = null === $dateFormat ? static::SIMPLE_DATE : $dateFormat; $this->dateFormat = null === $dateFormat ? static::SIMPLE_DATE : $dateFormat;
if (!\function_exists('json_encode')) {
throw new \RuntimeException('PHP\'s json extension is required to use Monolog\'s NormalizerFormatter');
}
} }
/** /**
@ -167,7 +163,7 @@ class NormalizerFormatter implements FormatterInterface
*/ */
protected function normalizeRecord(LogRecord $record): array protected function normalizeRecord(LogRecord $record): array
{ {
/** @var array<mixed> $normalized */ /** @var array<mixed[]|scalar|null> $normalized */
$normalized = $this->normalize($record->toArray()); $normalized = $this->normalize($record->toArray());
return $normalized; return $normalized;
@ -252,7 +248,7 @@ class NormalizerFormatter implements FormatterInterface
} }
/** /**
* @return mixed[] * @return array<string, string|int|array<string|int|array<string>>>|string
*/ */
protected function normalizeException(Throwable $e, int $depth = 0) protected function normalizeException(Throwable $e, int $depth = 0)
{ {

View file

@ -25,8 +25,6 @@ class WildfireFormatter extends NormalizerFormatter
{ {
/** /**
* @param string|null $dateFormat The format of the timestamp: one supported by DateTime::format * @param string|null $dateFormat The format of the timestamp: one supported by DateTime::format
*
* @throws \RuntimeException If the function json_encode does not exist
*/ */
public function __construct(?string $dateFormat = null) public function __construct(?string $dateFormat = null)
{ {

View file

@ -243,7 +243,7 @@ class BrowserConsoleHandler extends AbstractProcessingHandler
if (null === $style) { if (null === $style) {
$pcreErrorCode = preg_last_error(); $pcreErrorCode = preg_last_error();
throw new \RuntimeException('Failed to run preg_replace_callback: ' . $pcreErrorCode . ' / ' . Utils::pcreLastErrorMessage($pcreErrorCode)); throw new \RuntimeException('Failed to run preg_replace_callback: ' . $pcreErrorCode . ' / ' . preg_last_error_msg());
} }
return $style; return $style;
@ -256,7 +256,7 @@ class BrowserConsoleHandler extends AbstractProcessingHandler
private static function dump(string $title, array $dict): array private static function dump(string $title, array $dict): array
{ {
$script = []; $script = [];
$dict = array_filter($dict); $dict = array_filter($dict, fn ($value) => $value !== null);
if (\count($dict) === 0) { if (\count($dict) === 0) {
return $script; return $script;
} }

View file

@ -62,15 +62,9 @@ class ChromePHPHandler extends AbstractProcessingHandler
protected static bool $sendHeaders = true; protected static bool $sendHeaders = true;
/**
* @throws \RuntimeException If the function json_encode does not exist
*/
public function __construct(int|string|Level $level = Level::Debug, bool $bubble = true) public function __construct(int|string|Level $level = Level::Debug, bool $bubble = true)
{ {
parent::__construct($level, $bubble); parent::__construct($level, $bubble);
if (!\function_exists('json_encode')) {
throw new \RuntimeException('PHP\'s json extension is required to use Monolog\'s ChromePHPHandler');
}
} }
/** /**

View file

@ -11,6 +11,7 @@
namespace Monolog\Handler; namespace Monolog\Handler;
use Elastic\Transport\Exception\TransportException;
use Elastica\Document; use Elastica\Document;
use Monolog\Formatter\FormatterInterface; use Monolog\Formatter\FormatterInterface;
use Monolog\Formatter\ElasticaFormatter; use Monolog\Formatter\ElasticaFormatter;
@ -133,7 +134,7 @@ class ElasticaHandler extends AbstractProcessingHandler
{ {
try { try {
$this->client->addDocuments($documents); $this->client->addDocuments($documents);
} catch (ExceptionInterface $e) { } catch (ExceptionInterface | TransportException $e) {
if (!$this->options['ignore_error']) { if (!$this->options['ignore_error']) {
throw new \RuntimeException("Error sending messages to Elasticsearch", 0, $e); throw new \RuntimeException("Error sending messages to Elasticsearch", 0, $e);
} }

View file

@ -209,9 +209,13 @@ class ElasticsearchHandler extends AbstractProcessingHandler
return new ElasticInvalidArgumentException('Elasticsearch failed to index one or more records.'); return new ElasticInvalidArgumentException('Elasticsearch failed to index one or more records.');
} }
if (class_exists(ElasticsearchRuntimeException::class)) {
return new ElasticsearchRuntimeException('Elasticsearch failed to index one or more records.'); return new ElasticsearchRuntimeException('Elasticsearch failed to index one or more records.');
} }
throw new \LogicException('Unsupported elastic search client version');
}
/** /**
* Creates elasticsearch exception from error array * Creates elasticsearch exception from error array
* *
@ -225,6 +229,10 @@ class ElasticsearchHandler extends AbstractProcessingHandler
return new ElasticInvalidArgumentException($error['type'] . ': ' . $error['reason'], 0, $previous); return new ElasticInvalidArgumentException($error['type'] . ': ' . $error['reason'], 0, $previous);
} }
if (class_exists(ElasticsearchRuntimeException::class)) {
return new ElasticsearchRuntimeException($error['type'].': '.$error['reason'], 0, $previous); return new ElasticsearchRuntimeException($error['type'].': '.$error['reason'], 0, $previous);
} }
throw new \LogicException('Unsupported elastic search client version');
}
} }

View file

@ -27,11 +27,12 @@ class ErrorLogHandler extends AbstractProcessingHandler
public const OPERATING_SYSTEM = 0; public const OPERATING_SYSTEM = 0;
public const SAPI = 4; public const SAPI = 4;
/** @var 0|1|3|4 */
protected int $messageType; protected int $messageType;
protected bool $expandNewlines; protected bool $expandNewlines;
/** /**
* @param int $messageType Says where the error should go. * @param 0|1|3|4 $messageType Says where the error should go.
* @param bool $expandNewlines If set to true, newlines in the message will be expanded to be take multiple log entries * @param bool $expandNewlines If set to true, newlines in the message will be expanded to be take multiple log entries
* *
* @throws \InvalidArgumentException If an unsupported message type is set * @throws \InvalidArgumentException If an unsupported message type is set
@ -84,7 +85,7 @@ class ErrorLogHandler extends AbstractProcessingHandler
if ($lines === false) { if ($lines === false) {
$pcreErrorCode = preg_last_error(); $pcreErrorCode = preg_last_error();
throw new \RuntimeException('Failed to preg_split formatted string: ' . $pcreErrorCode . ' / '. Utils::pcreLastErrorMessage($pcreErrorCode)); throw new \RuntimeException('Failed to preg_split formatted string: ' . $pcreErrorCode . ' / '. preg_last_error_msg());
} }
foreach ($lines as $line) { foreach ($lines as $line) {
error_log($line, $this->messageType); error_log($line, $this->messageType);

View file

@ -67,16 +67,16 @@ class FingersCrossedHandler extends Handler implements ProcessableHandlerInterfa
* @phpstan-param (Closure(LogRecord|null, HandlerInterface): HandlerInterface)|HandlerInterface $handler * @phpstan-param (Closure(LogRecord|null, HandlerInterface): HandlerInterface)|HandlerInterface $handler
* *
* @param Closure|HandlerInterface $handler Handler or factory Closure($record|null, $fingersCrossedHandler). * @param Closure|HandlerInterface $handler Handler or factory Closure($record|null, $fingersCrossedHandler).
* @param int|string|Level|LogLevel::* $activationStrategy Strategy which determines when this handler takes action, or a level name/value at which the handler is activated * @param int|string|Level|LogLevel::*|null $activationStrategy Strategy which determines when this handler takes action, or a level name/value at which the handler is activated
* @param int $bufferSize How many entries should be buffered at most, beyond that the oldest items are removed from the buffer. * @param int $bufferSize How many entries should be buffered at most, beyond that the oldest items are removed from the buffer.
* @param bool $bubble Whether the messages that are handled can bubble up the stack or not * @param bool $bubble Whether the messages that are handled can bubble up the stack or not
* @param bool $stopBuffering Whether the handler should stop buffering after being triggered (default true) * @param bool $stopBuffering Whether the handler should stop buffering after being triggered (default true)
* @param int|string|Level|LogLevel::*|null $passthruLevel Minimum level to always flush to handler on close, even if strategy not triggered * @param int|string|Level|LogLevel::*|null $passthruLevel Minimum level to always flush to handler on close, even if strategy not triggered
* *
* @phpstan-param value-of<Level::VALUES>|value-of<Level::NAMES>|Level|LogLevel::*|ActivationStrategyInterface $activationStrategy * @phpstan-param value-of<Level::VALUES>|value-of<Level::NAMES>|Level|LogLevel::*|ActivationStrategyInterface|null $activationStrategy
* @phpstan-param value-of<Level::VALUES>|value-of<Level::NAMES>|Level|LogLevel::* $passthruLevel * @phpstan-param value-of<Level::VALUES>|value-of<Level::NAMES>|Level|LogLevel::*|null $passthruLevel
*/ */
public function __construct(Closure|HandlerInterface $handler, int|string|Level|ActivationStrategyInterface $activationStrategy = null, int $bufferSize = 0, bool $bubble = true, bool $stopBuffering = true, int|string|Level|null $passthruLevel = null) public function __construct(Closure|HandlerInterface $handler, int|string|Level|ActivationStrategyInterface|null $activationStrategy = null, int $bufferSize = 0, bool $bubble = true, bool $stopBuffering = true, int|string|Level|null $passthruLevel = null)
{ {
if (null === $activationStrategy) { if (null === $activationStrategy) {
$activationStrategy = new ErrorLevelActivationStrategy(Level::Warning); $activationStrategy = new ErrorLevelActivationStrategy(Level::Warning);

View file

@ -70,8 +70,8 @@ class MandrillHandler extends MailHandler
$ch = curl_init(); $ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'https://mandrillapp.com/api/1.0/messages/send-raw.json'); curl_setopt($ch, CURLOPT_URL, 'https://mandrillapp.com/api/1.0/messages/send-raw.json');
curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query([ curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query([
'key' => $this->apiKey, 'key' => $this->apiKey,
'raw_message' => (string) $message, 'raw_message' => (string) $message,

View file

@ -97,7 +97,7 @@ class OverflowHandler extends AbstractHandler implements FormattableHandlerInter
return false === $this->bubble; return false === $this->bubble;
} }
if ($this->thresholdMap[$level] == 0) { if ($this->thresholdMap[$level] === 0) {
// This current message is breaking the threshold. Flush the buffer and continue handling the current record // This current message is breaking the threshold. Flush the buffer and continue handling the current record
foreach ($this->buffer[$level] ?? [] as $buffered) { foreach ($this->buffer[$level] ?? [] as $buffered) {
$this->handler->handle($buffered); $this->handler->handle($buffered);

View file

@ -111,7 +111,7 @@ class PHPConsoleHandler extends AbstractProcessingHandler
'dumperItemSizeLimit' => 5000, // int Maximum length of any string or dumped array item 'dumperItemSizeLimit' => 5000, // int Maximum length of any string or dumped array item
'dumperDumpSizeLimit' => 500000, // int Maximum approximate size of dumped vars result formatted in JSON 'dumperDumpSizeLimit' => 500000, // int Maximum approximate size of dumped vars result formatted in JSON
'detectDumpTraceAndSource' => false, // bool Autodetect and append trace data to debug 'detectDumpTraceAndSource' => false, // bool Autodetect and append trace data to debug
'dataStorage' => null, // \PhpConsole\Storage|null Fixes problem with custom $_SESSION handler(see http://goo.gl/Ne8juJ) 'dataStorage' => null, // \PhpConsole\Storage|null Fixes problem with custom $_SESSION handler (see https://github.com/barbushin/php-console#troubleshooting-with-_session-handler-overridden-in-some-frameworks)
]; ];
private Connector $connector; private Connector $connector;

View file

@ -43,6 +43,8 @@ class ProcessHandler extends AbstractProcessingHandler
*/ */
private array $pipes = []; private array $pipes = [];
private float $timeout;
/** /**
* @var array<int, string[]> * @var array<int, string[]>
*/ */
@ -56,9 +58,10 @@ class ProcessHandler extends AbstractProcessingHandler
* @param string $command Command for the process to start. Absolute paths are recommended, * @param string $command Command for the process to start. Absolute paths are recommended,
* especially if you do not use the $cwd parameter. * especially if you do not use the $cwd parameter.
* @param string|null $cwd "Current working directory" (CWD) for the process to be executed in. * @param string|null $cwd "Current working directory" (CWD) for the process to be executed in.
* @param float $timeout The maximum timeout (in seconds) for the stream_select() function.
* @throws \InvalidArgumentException * @throws \InvalidArgumentException
*/ */
public function __construct(string $command, int|string|Level $level = Level::Debug, bool $bubble = true, ?string $cwd = null) public function __construct(string $command, int|string|Level $level = Level::Debug, bool $bubble = true, ?string $cwd = null, float $timeout = 1.0)
{ {
if ($command === '') { if ($command === '') {
throw new \InvalidArgumentException('The command argument must be a non-empty string.'); throw new \InvalidArgumentException('The command argument must be a non-empty string.');
@ -71,6 +74,7 @@ class ProcessHandler extends AbstractProcessingHandler
$this->command = $command; $this->command = $command;
$this->cwd = $cwd; $this->cwd = $cwd;
$this->timeout = $timeout;
} }
/** /**
@ -146,7 +150,8 @@ class ProcessHandler extends AbstractProcessingHandler
$empty = []; $empty = [];
$errorPipes = [$this->pipes[2]]; $errorPipes = [$this->pipes[2]];
return stream_select($errorPipes, $empty, $empty, 1); $seconds = (int) $this->timeout;
return stream_select($errorPipes, $empty, $empty, $seconds, (int) (($this->timeout - $seconds) * 1000000));
} }
/** /**

View file

@ -72,7 +72,7 @@ class RedisHandler extends AbstractProcessingHandler
$mode = \defined('Redis::MULTI') ? Redis::MULTI : 1; $mode = \defined('Redis::MULTI') ? Redis::MULTI : 1;
$this->redisClient->multi($mode) $this->redisClient->multi($mode)
->rPush($this->redisKey, $record->formatted) ->rPush($this->redisKey, $record->formatted)
->lTrim($this->redisKey, -$this->capSize, -1) ->ltrim($this->redisKey, -$this->capSize, -1)
->exec(); ->exec();
} else { } else {
$redisKey = $this->redisKey; $redisKey = $this->redisKey;

View file

@ -99,7 +99,6 @@ class RollbarHandler extends AbstractProcessingHandler
$toLog = $record->message; $toLog = $record->message;
} }
// @phpstan-ignore-next-line
$this->rollbarLogger->log($context['level'], $toLog, $context); $this->rollbarLogger->log($context['level'], $toLog, $context);
$this->hasRecords = true; $this->hasRecords = true;

View file

@ -71,10 +71,6 @@ class RotatingFileHandler extends StreamHandler
public function reset(): void public function reset(): void
{ {
parent::reset(); parent::reset();
if (true === $this->mustRotate) {
$this->rotate();
}
} }
/** /**
@ -100,17 +96,22 @@ class RotatingFileHandler extends StreamHandler
*/ */
protected function write(LogRecord $record): void protected function write(LogRecord $record): void
{ {
// on the first record written, if the log is new, we should rotate (once per day) // on the first record written, if the log is new, we rotate (once per day) after the log has been written so that the new file exists
if (null === $this->mustRotate) { if (null === $this->mustRotate) {
$this->mustRotate = null === $this->url || !file_exists($this->url); $this->mustRotate = null === $this->url || !file_exists($this->url);
} }
// if the next rotation is expired, then we rotate immediately
if ($this->nextRotation <= $record->datetime) { if ($this->nextRotation <= $record->datetime) {
$this->mustRotate = true; $this->mustRotate = true;
$this->close(); $this->close(); // triggers rotation
} }
parent::write($record); parent::write($record);
if (true === $this->mustRotate) {
$this->close(); // triggers rotation
}
} }
/** /**
@ -122,6 +123,8 @@ class RotatingFileHandler extends StreamHandler
$this->url = $this->getTimedFilename(); $this->url = $this->getTimedFilename();
$this->nextRotation = $this->getNextRotation(); $this->nextRotation = $this->getNextRotation();
$this->mustRotate = false;
// skip GC of old logs if files are unlimited // skip GC of old logs if files are unlimited
if (0 === $this->maxFiles) { if (0 === $this->maxFiles) {
return; return;
@ -154,8 +157,6 @@ class RotatingFileHandler extends StreamHandler
restore_error_handler(); restore_error_handler();
} }
} }
$this->mustRotate = false;
} }
protected function getTimedFilename(): string protected function getTimedFilename(): string

View file

@ -92,8 +92,8 @@ class SendGridHandler extends MailHandler
$ch = curl_init(); $ch = curl_init();
curl_setopt($ch, CURLOPT_URL, 'https://api.sendgrid.com/api/mail.send.json'); curl_setopt($ch, CURLOPT_URL, 'https://api.sendgrid.com/api/mail.send.json');
curl_setopt($ch, CURLOPT_POST, 1); curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($message)); curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($message));
Curl\Util::execute($ch, 2); Curl\Util::execute($ch, 2);
} }

View file

@ -206,7 +206,7 @@ class SlackRecord
*/ */
public function stringify(array $fields): string public function stringify(array $fields): string
{ {
/** @var array<mixed> $normalized */ /** @var array<array<mixed>|bool|float|int|string|null> $normalized */
$normalized = $this->normalizerFormatter->normalizeValue($fields); $normalized = $this->normalizerFormatter->normalizeValue($fields);
$hasSecondDimension = \count(array_filter($normalized, 'is_array')) > 0; $hasSecondDimension = \count(array_filter($normalized, 'is_array')) > 0;
@ -341,7 +341,7 @@ class SlackRecord
*/ */
private function generateAttachmentFields(array $data): array private function generateAttachmentFields(array $data): array
{ {
/** @var array<mixed> $normalized */ /** @var array<array<mixed>|string> $normalized */
$normalized = $this->normalizerFormatter->normalizeValue($data); $normalized = $this->normalizerFormatter->normalizeValue($data);
$fields = []; $fields = [];

View file

@ -386,7 +386,7 @@ class SocketHandler extends AbstractProcessingHandler
$sent = 0; $sent = 0;
$this->lastSentBytes = $sent; $this->lastSentBytes = $sent;
while ($this->isConnected() && $sent < $length) { while ($this->isConnected() && $sent < $length) {
if (0 == $sent) { if (0 === $sent) {
$chunk = $this->fwrite($data); $chunk = $this->fwrite($data);
} else { } else {
$chunk = $this->fwrite(substr($data, $sent)); $chunk = $this->fwrite(substr($data, $sent));
@ -412,7 +412,7 @@ class SocketHandler extends AbstractProcessingHandler
private function writingIsTimedOut(int $sent): bool private function writingIsTimedOut(int $sent): bool
{ {
// convert to ms // convert to ms
if (0.0 == $this->writingTimeout) { if (0.0 === $this->writingTimeout) {
return false; return false;
} }

View file

@ -34,17 +34,20 @@ class StreamHandler extends AbstractProcessingHandler
private string|null $errorMessage = null; private string|null $errorMessage = null;
protected int|null $filePermission; protected int|null $filePermission;
protected bool $useLocking; protected bool $useLocking;
protected string $fileOpenMode;
/** @var true|null */ /** @var true|null */
private bool|null $dirCreated = null; private bool|null $dirCreated = null;
private bool $retrying = false;
/** /**
* @param resource|string $stream If a missing path can't be created, an UnexpectedValueException will be thrown on first write * @param resource|string $stream If a missing path can't be created, an UnexpectedValueException will be thrown on first write
* @param int|null $filePermission Optional file permissions (default (0644) are only for owner read/write) * @param int|null $filePermission Optional file permissions (default (0644) are only for owner read/write)
* @param bool $useLocking Try to lock log file before doing any writes * @param bool $useLocking Try to lock log file before doing any writes
* @param string $fileOpenMode The fopen() mode used when opening a file, if $stream is a file path
* *
* @throws \InvalidArgumentException If stream is not a resource or string * @throws \InvalidArgumentException If stream is not a resource or string
*/ */
public function __construct($stream, int|string|Level $level = Level::Debug, bool $bubble = true, ?int $filePermission = null, bool $useLocking = false) public function __construct($stream, int|string|Level $level = Level::Debug, bool $bubble = true, ?int $filePermission = null, bool $useLocking = false, string $fileOpenMode = 'a')
{ {
parent::__construct($level, $bubble); parent::__construct($level, $bubble);
@ -71,10 +74,25 @@ class StreamHandler extends AbstractProcessingHandler
throw new \InvalidArgumentException('A stream must either be a resource or a string.'); throw new \InvalidArgumentException('A stream must either be a resource or a string.');
} }
$this->fileOpenMode = $fileOpenMode;
$this->filePermission = $filePermission; $this->filePermission = $filePermission;
$this->useLocking = $useLocking; $this->useLocking = $useLocking;
} }
/**
* @inheritDoc
*/
public function reset(): void
{
parent::reset();
// auto-close on reset to make sure we periodically close the file in long running processes
// as long as they correctly call reset() between jobs
if ($this->url !== null && $this->url !== 'php://memory') {
$this->close();
}
}
/** /**
* @inheritDoc * @inheritDoc
*/ */
@ -122,12 +140,10 @@ class StreamHandler extends AbstractProcessingHandler
} }
$this->createDir($url); $this->createDir($url);
$this->errorMessage = null; $this->errorMessage = null;
set_error_handler(function (...$args) { set_error_handler($this->customErrorHandler(...));
return $this->customErrorHandler(...$args);
});
try { try {
$stream = fopen($url, 'a'); $stream = fopen($url, $this->fileOpenMode);
if ($this->filePermission !== null) { if ($this->filePermission !== null) {
@chmod($url, $this->filePermission); @chmod($url, $this->filePermission);
} }
@ -149,8 +165,28 @@ class StreamHandler extends AbstractProcessingHandler
flock($stream, LOCK_EX); flock($stream, LOCK_EX);
} }
$this->errorMessage = null;
set_error_handler($this->customErrorHandler(...));
try {
$this->streamWrite($stream, $record); $this->streamWrite($stream, $record);
} finally {
restore_error_handler();
}
if ($this->errorMessage !== null) {
$error = $this->errorMessage;
// close the resource if possible to reopen it, and retry the failed write
if (!$this->retrying && $this->url !== null && $this->url !== 'php://memory') {
$this->retrying = true;
$this->close();
$this->write($record);
return;
}
throw new \UnexpectedValueException('Writing to the log file failed: '.$error . Utils::getRecordMessageForException($record));
}
$this->retrying = false;
if ($this->useLocking) { if ($this->useLocking) {
flock($stream, LOCK_UN); flock($stream, LOCK_UN);
} }
@ -167,7 +203,7 @@ class StreamHandler extends AbstractProcessingHandler
private function customErrorHandler(int $code, string $msg): bool private function customErrorHandler(int $code, string $msg): bool
{ {
$this->errorMessage = preg_replace('{^(fopen|mkdir)\(.*?\): }', '', $msg); $this->errorMessage = preg_replace('{^(fopen|mkdir|fwrite)\(.*?\): }', '', $msg);
return true; return true;
} }

View file

@ -96,7 +96,7 @@ class SyslogUdpHandler extends AbstractSyslogHandler
if (false === $lines) { if (false === $lines) {
$pcreErrorCode = preg_last_error(); $pcreErrorCode = preg_last_error();
throw new \RuntimeException('Could not preg_split: ' . $pcreErrorCode . ' / ' . Utils::pcreLastErrorMessage($pcreErrorCode)); throw new \RuntimeException('Could not preg_split: ' . $pcreErrorCode . ' / ' . preg_last_error_msg());
} }
return $lines; return $lines;

View file

@ -116,7 +116,7 @@ class TelegramBotHandler extends AbstractProcessingHandler
?bool $disableNotification = null, ?bool $disableNotification = null,
bool $splitLongMessages = false, bool $splitLongMessages = false,
bool $delayBetweenMessages = false, bool $delayBetweenMessages = false,
int $topic = null ?int $topic = null
) { ) {
if (!\extension_loaded('curl')) { if (!\extension_loaded('curl')) {
throw new MissingExtensionException('The curl extension is needed to use the TelegramBotHandler'); throw new MissingExtensionException('The curl extension is needed to use the TelegramBotHandler');
@ -196,7 +196,7 @@ class TelegramBotHandler extends AbstractProcessingHandler
/** /**
* @return $this * @return $this
*/ */
public function setTopic(int $topic = null): self public function setTopic(?int $topic = null): self
{ {
$this->topic = $topic; $this->topic = $topic;

View file

@ -23,14 +23,14 @@ use Monolog\LogRecord;
* *
* @author Jordi Boggiano <j.boggiano@seld.be> * @author Jordi Boggiano <j.boggiano@seld.be>
* *
* @method bool hasEmergency(string|array $recordAssertions) * @method bool hasEmergency(array{message: string, context?: mixed[]}|string $recordAssertions)
* @method bool hasAlert(string|array $recordAssertions) * @method bool hasAlert(array{message: string, context?: mixed[]}|string $recordAssertions)
* @method bool hasCritical(string|array $recordAssertions) * @method bool hasCritical(array{message: string, context?: mixed[]}|string $recordAssertions)
* @method bool hasError(string|array $recordAssertions) * @method bool hasError(array{message: string, context?: mixed[]}|string $recordAssertions)
* @method bool hasWarning(string|array $recordAssertions) * @method bool hasWarning(array{message: string, context?: mixed[]}|string $recordAssertions)
* @method bool hasNotice(string|array $recordAssertions) * @method bool hasNotice(array{message: string, context?: mixed[]}|string $recordAssertions)
* @method bool hasInfo(string|array $recordAssertions) * @method bool hasInfo(array{message: string, context?: mixed[]}|string $recordAssertions)
* @method bool hasDebug(string|array $recordAssertions) * @method bool hasDebug(array{message: string, context?: mixed[]}|string $recordAssertions)
* *
* @method bool hasEmergencyRecords() * @method bool hasEmergencyRecords()
* @method bool hasAlertRecords() * @method bool hasAlertRecords()
@ -179,7 +179,7 @@ class TestHandler extends AbstractProcessingHandler
*/ */
public function __call(string $method, array $args): bool public function __call(string $method, array $args): bool
{ {
if (preg_match('/(.*)(Debug|Info|Notice|Warning|Error|Critical|Alert|Emergency)(.*)/', $method, $matches) > 0) { if ((bool) preg_match('/(.*)(Debug|Info|Notice|Warning|Error|Critical|Alert|Emergency)(.*)/', $method, $matches)) {
$genericMethod = $matches[1] . ('Records' !== $matches[3] ? 'Record' : '') . $matches[3]; $genericMethod = $matches[1] . ('Records' !== $matches[3] ? 'Record' : '') . $matches[3];
$level = \constant(Level::class.'::' . $matches[2]); $level = \constant(Level::class.'::' . $matches[2]);
$callback = [$this, $genericMethod]; $callback = [$this, $genericMethod];

View file

@ -166,7 +166,7 @@ class Logger implements LoggerInterface, ResettableInterface
/** /**
* @param string $name The logging channel, a simple descriptive name that is attached to all log records * @param string $name The logging channel, a simple descriptive name that is attached to all log records
* @param HandlerInterface[] $handlers Optional stack of handlers, the first one in the array is called first, etc. * @param list<HandlerInterface> $handlers Optional stack of handlers, the first one in the array is called first, etc.
* @param callable[] $processors Optional array of processors * @param callable[] $processors Optional array of processors
* @param DateTimeZone|null $timezone Optional timezone, if not provided date_default_timezone_get() will be used * @param DateTimeZone|null $timezone Optional timezone, if not provided date_default_timezone_get() will be used
* *

View file

@ -29,18 +29,22 @@ use Monolog\LogRecord;
*/ */
class IntrospectionProcessor implements ProcessorInterface class IntrospectionProcessor implements ProcessorInterface
{ {
private Level $level; protected Level $level;
/** @var string[] */ /** @var string[] */
private array $skipClassesPartials; protected array $skipClassesPartials;
private int $skipStackFramesCount; protected int $skipStackFramesCount;
private const SKIP_FUNCTIONS = [ protected const SKIP_FUNCTIONS = [
'call_user_func', 'call_user_func',
'call_user_func_array', 'call_user_func_array',
]; ];
protected const SKIP_CLASSES = [
'Monolog\\',
];
/** /**
* @param string|int|Level $level The minimum logging level at which this Processor will be triggered * @param string|int|Level $level The minimum logging level at which this Processor will be triggered
* @param string[] $skipClassesPartials * @param string[] $skipClassesPartials
@ -50,7 +54,7 @@ class IntrospectionProcessor implements ProcessorInterface
public function __construct(int|string|Level $level = Level::Debug, array $skipClassesPartials = [], int $skipStackFramesCount = 0) public function __construct(int|string|Level $level = Level::Debug, array $skipClassesPartials = [], int $skipStackFramesCount = 0)
{ {
$this->level = Logger::toMonologLevel($level); $this->level = Logger::toMonologLevel($level);
$this->skipClassesPartials = array_merge(['Monolog\\'], $skipClassesPartials); $this->skipClassesPartials = array_merge(static::SKIP_CLASSES, $skipClassesPartials);
$this->skipStackFramesCount = $skipStackFramesCount; $this->skipStackFramesCount = $skipStackFramesCount;
} }

View file

@ -62,13 +62,18 @@ class MercurialProcessor implements ProcessorInterface
} }
$result = explode(' ', trim((string) shell_exec('hg id -nb'))); $result = explode(' ', trim((string) shell_exec('hg id -nb')));
if (\count($result) >= 3) { if (\count($result) >= 3) {
return self::$cache = [ return self::$cache = [
'branch' => $result[1], 'branch' => $result[1],
'revision' => $result[2], 'revision' => $result[2],
]; ];
} }
if (\count($result) === 2) {
return self::$cache = [
'branch' => $result[1],
'revision' => $result[0],
];
}
return self::$cache = []; return self::$cache = [];
} }

View file

@ -17,6 +17,7 @@ use Monolog\LogRecord;
use Monolog\DateTimeImmutable; use Monolog\DateTimeImmutable;
use Monolog\Formatter\FormatterInterface; use Monolog\Formatter\FormatterInterface;
use Psr\Log\LogLevel; use Psr\Log\LogLevel;
use ReflectionProperty;
/** /**
* Lets you easily generate log records and a dummy formatter for testing purposes * Lets you easily generate log records and a dummy formatter for testing purposes
@ -27,15 +28,6 @@ use Psr\Log\LogLevel;
*/ */
class TestCase extends \PHPUnit\Framework\TestCase class TestCase extends \PHPUnit\Framework\TestCase
{ {
public function tearDown(): void
{
parent::tearDown();
if (isset($this->handler)) {
unset($this->handler);
}
}
/** /**
* @param array<mixed> $context * @param array<mixed> $context
* @param array<mixed> $extra * @param array<mixed> $extra

View file

@ -140,25 +140,6 @@ final class Utils
return $json; return $json;
} }
/**
* @internal
*/
public static function pcreLastErrorMessage(int $code): string
{
if (PHP_VERSION_ID >= 80000) {
return preg_last_error_msg();
}
$constants = (get_defined_constants(true))['pcre'];
$constants = array_filter($constants, function ($key) {
return substr($key, -6) == '_ERROR';
}, ARRAY_FILTER_USE_KEY);
$constants = array_flip($constants);
return $constants[$code] ?? 'UNDEFINED_ERROR';
}
/** /**
* Throws an exception according to a given code with a customized message * Throws an exception according to a given code with a customized message
* *
@ -200,14 +181,16 @@ final class Utils
$data = preg_replace_callback( $data = preg_replace_callback(
'/[\x80-\xFF]+/', '/[\x80-\xFF]+/',
function (array $m): string { function (array $m): string {
return \function_exists('mb_convert_encoding') ? mb_convert_encoding($m[0], 'UTF-8', 'ISO-8859-1') : utf8_encode($m[0]); return \function_exists('mb_convert_encoding')
? mb_convert_encoding($m[0], 'UTF-8', 'ISO-8859-1')
: (\function_exists('utf8_encode') ? utf8_encode($m[0]) : '');
}, },
$data $data
); );
if (!\is_string($data)) { if (!\is_string($data)) {
$pcreErrorCode = preg_last_error(); $pcreErrorCode = preg_last_error();
throw new \RuntimeException('Failed to preg_replace_callback: ' . $pcreErrorCode . ' / ' . self::pcreLastErrorMessage($pcreErrorCode)); throw new \RuntimeException('Failed to preg_replace_callback: ' . $pcreErrorCode . ' / ' . preg_last_error_msg());
} }
$data = str_replace( $data = str_replace(
['¤', '¦', '¨', '´', '¸', '¼', '½', '¾'], ['¤', '¦', '¨', '´', '¸', '¼', '½', '¾'],
@ -234,12 +217,12 @@ final class Utils
return (int) $val; return (int) $val;
} }
if (preg_match('/^\s*(?<val>\d+)(?:\.\d+)?\s*(?<unit>[gmk]?)\s*$/i', $val, $match) !== 1) { if (!(bool) preg_match('/^\s*(?<val>\d+)(?:\.\d+)?\s*(?<unit>[gmk]?)\s*$/i', $val, $match)) {
return false; return false;
} }
$val = (int) $match['val']; $val = (int) $match['val'];
switch (strtolower($match['unit'] ?? '')) { switch (strtolower($match['unit'])) {
case 'g': case 'g':
$val *= 1024; $val *= 1024;
// no break // no break

View file

@ -9,6 +9,7 @@ $config = (new PhpCsFixer\Config())
->setRiskyAllowed(true) ->setRiskyAllowed(true)
->setRules([ ->setRules([
'@Symfony' => true, '@Symfony' => true,
'trailing_comma_in_multiline' => false, // for methods this is incompatible with PHP 7
]) ])
->setFinder($finder) ->setFinder($finder)
; ;

View file

@ -1,5 +1,11 @@
# Change Log # Change Log
## 1.20.0 - 2024-10-02
- [#268](https://github.com/php-http/discovery/pull/268) - Do not attempt to update lock file when it is not existing.
- [#267](https://github.com/php-http/discovery/pull/267) - Test with PHP 8.3 and 8.4
- [#266](https://github.com/php-http/discovery/pull/266) - If wrapped client implements factories, use those instead of discovering new factories.
## 1.19.4 - 2024-03-29 ## 1.19.4 - 2024-03-29
- [#264](https://github.com/php-http/discovery/pull/264) - Do not report a general conflict with `sebastian/comparator` but make sure we install the correct version for our tests. - [#264](https://github.com/php-http/discovery/pull/264) - Do not report a general conflict with `sebastian/comparator` but make sure we install the correct version for our tests.

View file

@ -452,12 +452,21 @@ EOPHP
private function updateComposerLock(Composer $composer, IOInterface $io) private function updateComposerLock(Composer $composer, IOInterface $io)
{ {
if (false === $composer->getConfig()->get('lock')) {
return;
}
$lock = substr(Factory::getComposerFile(), 0, -4).'lock'; $lock = substr(Factory::getComposerFile(), 0, -4).'lock';
$composerJson = file_get_contents(Factory::getComposerFile()); $composerJson = file_get_contents(Factory::getComposerFile());
$lockFile = new JsonFile($lock, null, $io); $lockFile = new JsonFile($lock, null, $io);
$locker = ClassDiscovery::safeClassExists(RepositorySet::class) $locker = ClassDiscovery::safeClassExists(RepositorySet::class)
? new Locker($io, $lockFile, $composer->getInstallationManager(), $composerJson) ? new Locker($io, $lockFile, $composer->getInstallationManager(), $composerJson)
: new Locker($io, $lockFile, $composer->getRepositoryManager(), $composer->getInstallationManager(), $composerJson); : new Locker($io, $lockFile, $composer->getRepositoryManager(), $composer->getInstallationManager(), $composerJson);
if (!$locker->isLocked()) {
return;
}
$lockData = $locker->getLockData(); $lockData = $locker->getLockData();
$lockData['content-hash'] = Locker::getContentHash($composerJson); $lockData['content-hash'] = Locker::getContentHash($composerJson);
$lockFile->write($lockData); $lockFile->write($lockData);

View file

@ -33,6 +33,13 @@ class Psr18Client extends Psr17Factory implements ClientInterface
?UploadedFileFactoryInterface $uploadedFileFactory = null, ?UploadedFileFactoryInterface $uploadedFileFactory = null,
?UriFactoryInterface $uriFactory = null ?UriFactoryInterface $uriFactory = null
) { ) {
$requestFactory ?? $requestFactory = $client instanceof RequestFactoryInterface ? $client : null;
$responseFactory ?? $responseFactory = $client instanceof ResponseFactoryInterface ? $client : null;
$serverRequestFactory ?? $serverRequestFactory = $client instanceof ServerRequestFactoryInterface ? $client : null;
$streamFactory ?? $streamFactory = $client instanceof StreamFactoryInterface ? $client : null;
$uploadedFileFactory ?? $uploadedFileFactory = $client instanceof UploadedFileFactoryInterface ? $client : null;
$uriFactory ?? $uriFactory = $client instanceof UriFactoryInterface ? $client : null;
parent::__construct($requestFactory, $responseFactory, $serverRequestFactory, $streamFactory, $uploadedFileFactory, $uriFactory); parent::__construct($requestFactory, $responseFactory, $serverRequestFactory, $streamFactory, $uploadedFileFactory, $uriFactory);
$this->client = $client ?? Psr18ClientDiscovery::find(); $this->client = $client ?? Psr18ClientDiscovery::find();

View file

@ -41,13 +41,13 @@ you should look at before rolling your own. Try [SwiftMailer](https://swiftmaile
, [Laminas/Mail](https://docs.laminas.dev/laminas-mail/), [ZetaComponents](https://github.com/zetacomponents/Mail), etc. , [Laminas/Mail](https://docs.laminas.dev/laminas-mail/), [ZetaComponents](https://github.com/zetacomponents/Mail), etc.
## License ## License
This software is distributed under the [LGPL 2.1](http://www.gnu.org/licenses/lgpl-2.1.html) license, along with the [GPL Cooperation Commitment](https://gplcc.github.io/gplcc/). Please read [LICENSE](https://github.com/PHPMailer/PHPMailer/blob/master/LICENSE) for information on the software availability and distribution. This software is distributed under the [LGPL 2.1](https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html) license, along with the [GPL Cooperation Commitment](https://gplcc.github.io/gplcc/). Please read [LICENSE](https://github.com/PHPMailer/PHPMailer/blob/master/LICENSE) for information on the software availability and distribution.
## Installation & loading ## Installation & loading
PHPMailer is available on [Packagist](https://packagist.org/packages/phpmailer/phpmailer) (using semantic versioning), and installation via [Composer](https://getcomposer.org) is the recommended way to install PHPMailer. Just add this line to your `composer.json` file: PHPMailer is available on [Packagist](https://packagist.org/packages/phpmailer/phpmailer) (using semantic versioning), and installation via [Composer](https://getcomposer.org) is the recommended way to install PHPMailer. Just add this line to your `composer.json` file:
```json ```json
"phpmailer/phpmailer": "^6.9.1" "phpmailer/phpmailer": "^6.9.2"
``` ```
or run or run
@ -144,7 +144,7 @@ If you are re-using the instance (e.g. when sending to a mailing list), you may
That's it. You should now be ready to use PHPMailer! That's it. You should now be ready to use PHPMailer!
## Localization ## Localization
PHPMailer defaults to English, but in the [language](https://github.com/PHPMailer/PHPMailer/tree/master/language/) folder, you'll find many translations for PHPMailer error messages that you may encounter. Their filenames contain [ISO 639-1](http://en.wikipedia.org/wiki/ISO_639-1) language code for the translations, for example `fr` for French. To specify a language, you need to tell PHPMailer which one to use, like this: PHPMailer defaults to English, but in the [language](https://github.com/PHPMailer/PHPMailer/tree/master/language/) folder, you'll find many translations for PHPMailer error messages that you may encounter. Their filenames contain [ISO 639-1](https://en.wikipedia.org/wiki/ISO_639-1) language code for the translations, for example `fr` for French. To specify a language, you need to tell PHPMailer which one to use, like this:
```php ```php
//To load the French version //To load the French version
@ -162,9 +162,9 @@ To reduce PHPMailer's deployed code footprint, examples are not included if you
Complete generated API documentation is [available online](https://phpmailer.github.io/PHPMailer/). Complete generated API documentation is [available online](https://phpmailer.github.io/PHPMailer/).
You can generate complete API-level documentation by running `phpdoc` in the top-level folder, and documentation will appear in the `docs` folder, though you'll need to have [PHPDocumentor](http://www.phpdoc.org) installed. You may find [the unit tests](https://github.com/PHPMailer/PHPMailer/blob/master/test/PHPMailerTest.php) a good reference for how to do various operations such as encryption. You can generate complete API-level documentation by running `phpdoc` in the top-level folder, and documentation will appear in the `docs` folder, though you'll need to have [PHPDocumentor](https://www.phpdoc.org) installed. You may find [the unit tests](https://github.com/PHPMailer/PHPMailer/blob/master/test/PHPMailer/PHPMailerTest.php) a good reference for how to do various operations such as encryption.
If the documentation doesn't cover what you need, search the [many questions on Stack Overflow](http://stackoverflow.com/questions/tagged/phpmailer), and before you ask a question about "SMTP Error: Could not connect to SMTP host.", [read the troubleshooting guide](https://github.com/PHPMailer/PHPMailer/wiki/Troubleshooting). If the documentation doesn't cover what you need, search the [many questions on Stack Overflow](https://stackoverflow.com/questions/tagged/phpmailer), and before you ask a question about "SMTP Error: Could not connect to SMTP host.", [read the troubleshooting guide](https://github.com/PHPMailer/PHPMailer/wiki/Troubleshooting).
## Tests ## Tests
[PHPMailer tests](https://github.com/PHPMailer/PHPMailer/tree/master/test/) use PHPUnit 9, with [a polyfill](https://github.com/Yoast/PHPUnit-Polyfills) to let 9-style tests run on older PHPUnit and PHP versions. [PHPMailer tests](https://github.com/PHPMailer/PHPMailer/tree/master/test/) use PHPUnit 9, with [a polyfill](https://github.com/Yoast/PHPUnit-Polyfills) to let 9-style tests run on older PHPUnit and PHP versions.
@ -213,7 +213,7 @@ use. [Learn more.](https://tidelift.com/subscription/pkg/packagist-phpmailer-php
See [changelog](changelog.md). See [changelog](changelog.md).
## History ## History
- PHPMailer was originally written in 2001 by Brent R. Matzelle as a [SourceForge project](http://sourceforge.net/projects/phpmailer/). - PHPMailer was originally written in 2001 by Brent R. Matzelle as a [SourceForge project](https://sourceforge.net/projects/phpmailer/).
- [Marcus Bointon](https://github.com/Synchro) (`coolbru` on SF) and Andy Prevost (`codeworxtech`) took over the project in 2004. - [Marcus Bointon](https://github.com/Synchro) (`coolbru` on SF) and Andy Prevost (`codeworxtech`) took over the project in 2004.
- Became an Apache incubator project on Google Code in 2010, managed by Jim Jagielski. - Became an Apache incubator project on Google Code in 2010, managed by Jim Jagielski.
- Marcus created [his fork on GitHub](https://github.com/Synchro/PHPMailer) in 2008. - Marcus created [his fork on GitHub](https://github.com/Synchro/PHPMailer) in 2008.

View file

@ -13,13 +13,13 @@ PHPMailer versions 6.1.5 and earlier contain an output escaping bug that occurs
PHPMailer versions prior to 6.0.6 and 5.2.27 are vulnerable to an object injection attack by passing `phar://` paths into `addAttachment()` and other functions that may receive unfiltered local paths, possibly leading to RCE. Recorded as [CVE-2018-19296](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2018-19296). See [this article](https://knasmueller.net/5-answers-about-php-phar-exploitation) for more info on this type of vulnerability. Mitigated by blocking the use of paths containing URL-protocol style prefixes such as `phar://`. Reported by Sehun Oh of cyberone.kr. PHPMailer versions prior to 6.0.6 and 5.2.27 are vulnerable to an object injection attack by passing `phar://` paths into `addAttachment()` and other functions that may receive unfiltered local paths, possibly leading to RCE. Recorded as [CVE-2018-19296](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2018-19296). See [this article](https://knasmueller.net/5-answers-about-php-phar-exploitation) for more info on this type of vulnerability. Mitigated by blocking the use of paths containing URL-protocol style prefixes such as `phar://`. Reported by Sehun Oh of cyberone.kr.
PHPMailer versions prior to 5.2.24 (released July 26th 2017) have an XSS vulnerability in one of the code examples, [CVE-2017-11503](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2017-11503). The `code_generator.phps` example did not filter user input prior to output. This file is distributed with a `.phps` extension, so it it not normally executable unless it is explicitly renamed, and the file is not included when PHPMailer is loaded through composer, so it is safe by default. There was also an undisclosed potential XSS vulnerability in the default exception handler (unused by default). Patches for both issues kindly provided by Patrick Monnerat of the Fedora Project. PHPMailer versions prior to 5.2.24 (released July 26th 2017) have an XSS vulnerability in one of the code examples, [CVE-2017-11503](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2017-11503). The `code_generator.phps` example did not filter user input prior to output. This file is distributed with a `.phps` extension, so it is not normally executable unless it is explicitly renamed, and the file is not included when PHPMailer is loaded through composer, so it is safe by default. There was also an undisclosed potential XSS vulnerability in the default exception handler (unused by default). Patches for both issues kindly provided by Patrick Monnerat of the Fedora Project.
PHPMailer versions prior to 5.2.22 (released January 9th 2017) have a local file disclosure vulnerability, [CVE-2017-5223](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2017-5223). If content passed into `msgHTML()` is sourced from unfiltered user input, relative paths can map to absolute local file paths and added as attachments. Also note that `addAttachment` (just like `file_get_contents`, `passthru`, `unlink`, etc) should not be passed user-sourced params either! Reported by Yongxiang Li of Asiasecurity. PHPMailer versions prior to 5.2.22 (released January 9th 2017) have a local file disclosure vulnerability, [CVE-2017-5223](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2017-5223). If content passed into `msgHTML()` is sourced from unfiltered user input, relative paths can map to absolute local file paths and added as attachments. Also note that `addAttachment` (just like `file_get_contents`, `passthru`, `unlink`, etc) should not be passed user-sourced params either! Reported by Yongxiang Li of Asiasecurity.
PHPMailer versions prior to 5.2.20 (released December 28th 2016) are vulnerable to [CVE-2016-10045](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2016-10045) a remote code execution vulnerability, responsibly reported by [Dawid Golunski](https://legalhackers.com/advisories/PHPMailer-Exploit-Remote-Code-Exec-CVE-2016-10045-Vuln-Patch-Bypass.html), and patched by Paul Buonopane (@Zenexer). PHPMailer versions prior to 5.2.20 (released December 28th 2016) are vulnerable to [CVE-2016-10045](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2016-10045) a remote code execution vulnerability, responsibly reported by [Dawid Golunski](https://legalhackers.com/advisories/PHPMailer-Exploit-Remote-Code-Exec-CVE-2016-10045-Vuln-Patch-Bypass.html), and patched by Paul Buonopane (@Zenexer).
PHPMailer versions prior to 5.2.18 (released December 2016) are vulnerable to [CVE-2016-10033](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2016-10033) a remote code execution vulnerability, responsibly reported by [Dawid Golunski](http://legalhackers.com/advisories/PHPMailer-Exploit-Remote-Code-Exec-CVE-2016-10033-Vuln.html). PHPMailer versions prior to 5.2.18 (released December 2016) are vulnerable to [CVE-2016-10033](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2016-10033) a remote code execution vulnerability, responsibly reported by [Dawid Golunski](https://legalhackers.com/advisories/PHPMailer-Exploit-Remote-Code-Exec-CVE-2016-10033-Vuln.html).
PHPMailer versions prior to 5.2.14 (released November 2015) are vulnerable to [CVE-2015-8476](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2015-8476) an SMTP CRLF injection bug permitting arbitrary message sending. PHPMailer versions prior to 5.2.14 (released November 2015) are vulnerable to [CVE-2015-8476](https://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2015-8476) an SMTP CRLF injection bug permitting arbitrary message sending.

View file

@ -1 +1 @@
6.9.1 6.9.3

View file

@ -28,7 +28,8 @@
"config": { "config": {
"allow-plugins": { "allow-plugins": {
"dealerdirect/phpcodesniffer-composer-installer": true "dealerdirect/phpcodesniffer-composer-installer": true
} },
"lock": false
}, },
"require": { "require": {
"php": ">=5.5.0", "php": ">=5.5.0",

View file

@ -12,7 +12,7 @@
* @copyright 2012 - 2020 Marcus Bointon * @copyright 2012 - 2020 Marcus Bointon
* @copyright 2010 - 2012 Jim Jagielski * @copyright 2010 - 2012 Jim Jagielski
* @copyright 2004 - 2009 Andy Prevost * @copyright 2004 - 2009 Andy Prevost
* @license http://www.gnu.org/copyleft/lesser.html GNU Lesser General Public License * @license https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html GNU Lesser General Public License
* @note This program is distributed in the hope that it will be useful - WITHOUT * @note This program is distributed in the hope that it will be useful - WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. * FITNESS FOR A PARTICULAR PURPOSE.
@ -36,7 +36,7 @@ namespace PHPMailer\PHPMailer;
* Aliases for League Provider Classes * Aliases for League Provider Classes
* Make sure you have added these to your composer.json and run `composer install` * Make sure you have added these to your composer.json and run `composer install`
* Plenty to choose from here: * Plenty to choose from here:
* @see http://oauth2-client.thephpleague.com/providers/thirdparty/ * @see https://oauth2-client.thephpleague.com/providers/thirdparty/
*/ */
//@see https://github.com/thephpleague/oauth2-google //@see https://github.com/thephpleague/oauth2-google
use League\OAuth2\Client\Provider\Google; use League\OAuth2\Client\Provider\Google;
@ -178,5 +178,5 @@ if (!isset($_GET['code'])) {
); );
//Use this to interact with an API on the users behalf //Use this to interact with an API on the users behalf
//Use this to get a new access token if the old one expires //Use this to get a new access token if the old one expires
echo 'Refresh Token: ', $token->getRefreshToken(); echo 'Refresh Token: ', htmlspecialchars($token->getRefreshToken());
} }

View file

@ -5,27 +5,32 @@
* @package PHPMailer * @package PHPMailer
* @author Matt Sturdy <matt.sturdy@gmail.com> * @author Matt Sturdy <matt.sturdy@gmail.com>
* @author Crystopher Glodzienski Cardoso <crystopher.glodzienski@gmail.com> * @author Crystopher Glodzienski Cardoso <crystopher.glodzienski@gmail.com>
* @author Daniel Cruz <danicruz0415@gmail.com>
*/ */
$PHPMAILER_LANG['authenticate'] = 'Error SMTP: Imposible autentificar.'; $PHPMAILER_LANG['authenticate'] = 'Error SMTP: Imposible autentificar.';
$PHPMAILER_LANG['buggy_php'] = 'Tu versión de PHP está afectada por un bug que puede resultar en mensajes corruptos. Para arreglarlo, cambia a enviar usando SMTP, deshabilita la opción mail.add_x_header en tu php.ini, cambia a MacOS o Linux, o actualiza tu PHP a la versión 7.0.17+ o 7.1.3+.';
$PHPMAILER_LANG['connect_host'] = 'Error SMTP: Imposible conectar al servidor SMTP.'; $PHPMAILER_LANG['connect_host'] = 'Error SMTP: Imposible conectar al servidor SMTP.';
$PHPMAILER_LANG['data_not_accepted'] = 'Error SMTP: Datos no aceptados.'; $PHPMAILER_LANG['data_not_accepted'] = 'Error SMTP: Datos no aceptados.';
$PHPMAILER_LANG['empty_message'] = 'El cuerpo del mensaje está vacío.'; $PHPMAILER_LANG['empty_message'] = 'El cuerpo del mensaje está vacío.';
$PHPMAILER_LANG['encoding'] = 'Codificación desconocida: '; $PHPMAILER_LANG['encoding'] = 'Codificación desconocida: ';
$PHPMAILER_LANG['execute'] = 'Imposible ejecutar: '; $PHPMAILER_LANG['execute'] = 'Imposible ejecutar: ';
$PHPMAILER_LANG['extension_missing'] = 'Extensión faltante: ';
$PHPMAILER_LANG['file_access'] = 'Imposible acceder al archivo: '; $PHPMAILER_LANG['file_access'] = 'Imposible acceder al archivo: ';
$PHPMAILER_LANG['file_open'] = 'Error de Archivo: Imposible abrir el archivo: '; $PHPMAILER_LANG['file_open'] = 'Error de Archivo: Imposible abrir el archivo: ';
$PHPMAILER_LANG['from_failed'] = 'La(s) siguiente(s) direcciones de remitente fallaron: '; $PHPMAILER_LANG['from_failed'] = 'La(s) siguiente(s) direcciones de remitente fallaron: ';
$PHPMAILER_LANG['instantiate'] = 'Imposible crear una instancia de la función Mail.'; $PHPMAILER_LANG['instantiate'] = 'Imposible crear una instancia de la función Mail.';
$PHPMAILER_LANG['invalid_address'] = 'Imposible enviar: dirección de email inválido: '; $PHPMAILER_LANG['invalid_address'] = 'Imposible enviar: dirección de email inválido: ';
$PHPMAILER_LANG['invalid_header'] = 'Nombre o valor de encabezado no válido';
$PHPMAILER_LANG['invalid_hostentry'] = 'Hostentry inválido: ';
$PHPMAILER_LANG['invalid_host'] = 'Host inválido: ';
$PHPMAILER_LANG['mailer_not_supported'] = ' mailer no está soportado.'; $PHPMAILER_LANG['mailer_not_supported'] = ' mailer no está soportado.';
$PHPMAILER_LANG['provide_address'] = 'Debe proporcionar al menos una dirección de email de destino.'; $PHPMAILER_LANG['provide_address'] = 'Debe proporcionar al menos una dirección de email de destino.';
$PHPMAILER_LANG['recipients_failed'] = 'Error SMTP: Los siguientes destinos fallaron: '; $PHPMAILER_LANG['recipients_failed'] = 'Error SMTP: Los siguientes destinos fallaron: ';
$PHPMAILER_LANG['signing'] = 'Error al firmar: '; $PHPMAILER_LANG['signing'] = 'Error al firmar: ';
$PHPMAILER_LANG['smtp_connect_failed'] = 'SMTP Connect() falló.';
$PHPMAILER_LANG['smtp_error'] = 'Error del servidor SMTP: ';
$PHPMAILER_LANG['variable_set'] = 'No se pudo configurar la variable: ';
$PHPMAILER_LANG['extension_missing'] = 'Extensión faltante: ';
$PHPMAILER_LANG['smtp_code'] = 'Código del servidor SMTP: '; $PHPMAILER_LANG['smtp_code'] = 'Código del servidor SMTP: ';
$PHPMAILER_LANG['smtp_code_ex'] = 'Información adicional del servidor SMTP: '; $PHPMAILER_LANG['smtp_code_ex'] = 'Información adicional del servidor SMTP: ';
$PHPMAILER_LANG['invalid_header'] = 'Nombre o valor de encabezado no válido'; $PHPMAILER_LANG['smtp_connect_failed'] = 'SMTP Connect() falló.';
$PHPMAILER_LANG['smtp_detail'] = 'Detalle: ';
$PHPMAILER_LANG['smtp_error'] = 'Error del servidor SMTP: ';
$PHPMAILER_LANG['variable_set'] = 'No se pudo configurar la variable: ';

View file

@ -6,7 +6,6 @@
* Some French punctuation requires a thin non-breaking space (U+202F) character before it, * Some French punctuation requires a thin non-breaking space (U+202F) character before it,
* for example before a colon or exclamation mark. * for example before a colon or exclamation mark.
* There is one of these characters between these quotes: "" * There is one of these characters between these quotes: ""
* @see http://unicode.org/udhr/n/notes_fra.html
*/ */
$PHPMAILER_LANG['authenticate'] = 'Erreur SMTP: échec de lauthentification.'; $PHPMAILER_LANG['authenticate'] = 'Erreur SMTP: échec de lauthentification.';
@ -31,7 +30,7 @@ $PHPMAILER_LANG['recipients_failed'] = 'Erreur SMTP:les destinataires s
$PHPMAILER_LANG['signing'] = 'Erreur de signature: '; $PHPMAILER_LANG['signing'] = 'Erreur de signature: ';
$PHPMAILER_LANG['smtp_code'] = 'Code SMTP: '; $PHPMAILER_LANG['smtp_code'] = 'Code SMTP: ';
$PHPMAILER_LANG['smtp_code_ex'] = 'Informations supplémentaires SMTP: '; $PHPMAILER_LANG['smtp_code_ex'] = 'Informations supplémentaires SMTP: ';
$PHPMAILER_LANG['smtp_connect_failed'] = 'La fonction SMTP connect() a échouée.'; $PHPMAILER_LANG['smtp_connect_failed'] = 'La fonction SMTP connect() a échoué.';
$PHPMAILER_LANG['smtp_detail'] = 'Détails: '; $PHPMAILER_LANG['smtp_detail'] = 'Détails: ';
$PHPMAILER_LANG['smtp_error'] = 'Erreur du serveur SMTP: '; $PHPMAILER_LANG['smtp_error'] = 'Erreur du serveur SMTP: ';
$PHPMAILER_LANG['variable_set'] = 'Impossible dinitialiser ou de réinitialiser une variable: '; $PHPMAILER_LANG['variable_set'] = 'Impossible dinitialiser ou de réinitialiser une variable: ';

View file

@ -3,27 +3,35 @@
/** /**
* Japanese PHPMailer language file: refer to English translation for definitive list * Japanese PHPMailer language file: refer to English translation for definitive list
* @package PHPMailer * @package PHPMailer
* @author Mitsuhiro Yoshida <http://mitstek.com/> * @author Mitsuhiro Yoshida <https://mitstek.com>
* @author Yoshi Sakai <http://bluemooninc.jp/> * @author Yoshi Sakai <http://bluemooninc.jp/>
* @author Arisophy <https://github.com/arisophy/> * @author Arisophy <https://github.com/arisophy/>
* @author ARAKI Musashi <https://github.com/arakim/>
*/ */
$PHPMAILER_LANG['authenticate'] = 'SMTPエラー: 認証できませんでした。'; $PHPMAILER_LANG['authenticate'] = 'SMTPエラー: 認証できませんでした。';
$PHPMAILER_LANG['buggy_php'] = 'ご利用のバージョンのPHPには不具合があり、メッセージが破損するおそれがあります。問題の解決は以下のいずれかを行ってください。SMTPでの送信に切り替える。php.iniのmail.add_x_headerをoffにする。MacOSまたはLinuxに切り替える。PHPバージョン7.0.17以降または7.1.3以降にアップグレードする。';
$PHPMAILER_LANG['connect_host'] = 'SMTPエラー: SMTPホストに接続できませんでした。'; $PHPMAILER_LANG['connect_host'] = 'SMTPエラー: SMTPホストに接続できませんでした。';
$PHPMAILER_LANG['data_not_accepted'] = 'SMTPエラー: データが受け付けられませんでした。'; $PHPMAILER_LANG['data_not_accepted'] = 'SMTPエラー: データが受け付けられませんでした。';
$PHPMAILER_LANG['empty_message'] = 'メール本文が空です。'; $PHPMAILER_LANG['empty_message'] = 'メール本文が空です。';
$PHPMAILER_LANG['encoding'] = '不明なエンコーディング: '; $PHPMAILER_LANG['encoding'] = '不明なエンコーディング: ';
$PHPMAILER_LANG['execute'] = '実行できませんでした: '; $PHPMAILER_LANG['execute'] = '実行できませんでした: ';
$PHPMAILER_LANG['extension_missing'] = '拡張機能が見つかりません: ';
$PHPMAILER_LANG['file_access'] = 'ファイルにアクセスできません: '; $PHPMAILER_LANG['file_access'] = 'ファイルにアクセスできません: ';
$PHPMAILER_LANG['file_open'] = 'ファイルエラー: ファイルを開けません: '; $PHPMAILER_LANG['file_open'] = 'ファイルエラー: ファイルを開けません: ';
$PHPMAILER_LANG['from_failed'] = 'Fromアドレスを登録する際にエラーが発生しました: '; $PHPMAILER_LANG['from_failed'] = 'Fromアドレスを登録する際にエラーが発生しました: ';
$PHPMAILER_LANG['instantiate'] = 'メール関数が正常に動作しませんでした。'; $PHPMAILER_LANG['instantiate'] = 'メール関数が正常に動作しませんでした。';
$PHPMAILER_LANG['invalid_address'] = '不正なメールアドレス: '; $PHPMAILER_LANG['invalid_address'] = '不正なメールアドレス: ';
$PHPMAILER_LANG['provide_address'] = '少なくとも1つメールアドレスを 指定する必要があります。'; $PHPMAILER_LANG['invalid_header'] = '不正なヘッダー名またはその内容';
$PHPMAILER_LANG['invalid_hostentry'] = '不正なホストエントリー: ';
$PHPMAILER_LANG['invalid_host'] = '不正なホスト: ';
$PHPMAILER_LANG['mailer_not_supported'] = ' メーラーがサポートされていません。'; $PHPMAILER_LANG['mailer_not_supported'] = ' メーラーがサポートされていません。';
$PHPMAILER_LANG['provide_address'] = '少なくとも1つメールアドレスを 指定する必要があります。';
$PHPMAILER_LANG['recipients_failed'] = 'SMTPエラー: 次の受信者アドレスに 間違いがあります: '; $PHPMAILER_LANG['recipients_failed'] = 'SMTPエラー: 次の受信者アドレスに 間違いがあります: ';
$PHPMAILER_LANG['signing'] = '署名エラー: '; $PHPMAILER_LANG['signing'] = '署名エラー: ';
$PHPMAILER_LANG['smtp_code'] = 'SMTPコード: ';
$PHPMAILER_LANG['smtp_code_ex'] = 'SMTP追加情報: ';
$PHPMAILER_LANG['smtp_connect_failed'] = 'SMTP接続に失敗しました。'; $PHPMAILER_LANG['smtp_connect_failed'] = 'SMTP接続に失敗しました。';
$PHPMAILER_LANG['smtp_detail'] = '詳細: ';
$PHPMAILER_LANG['smtp_error'] = 'SMTPサーバーエラー: '; $PHPMAILER_LANG['smtp_error'] = 'SMTPサーバーエラー: ';
$PHPMAILER_LANG['variable_set'] = '変数が存在しません: '; $PHPMAILER_LANG['variable_set'] = '変数が存在しません: ';
$PHPMAILER_LANG['extension_missing'] = '拡張機能が見つかりません: ';

View file

@ -0,0 +1,27 @@
<?php
/**
* Kurdish (Sorani) PHPMailer language file: refer to English translation for definitive list
* @package PHPMailer
* @author Halo Salman <halo@home4t.com>
*/
$PHPMAILER_LANG['authenticate'] = 'هەڵەی SMTP : نەتوانرا کۆدەکە پشتڕاست بکرێتەوە ';
$PHPMAILER_LANG['connect_host'] = 'هەڵەی SMTP: نەتوانرا پەیوەندی بە سێرڤەرەوە بکات SMTP.';
$PHPMAILER_LANG['data_not_accepted'] = 'هەڵەی SMTP: ئەو زانیاریانە قبوڵ نەکرا.';
$PHPMAILER_LANG['empty_message'] = 'پەیامەکە بەتاڵە';
$PHPMAILER_LANG['encoding'] = 'کۆدکردنی نەزانراو : ';
$PHPMAILER_LANG['execute'] = 'ناتوانرێت جێبەجێ بکرێت: ';
$PHPMAILER_LANG['file_access'] = 'ناتوانرێت دەستت بگات بە فایلەکە: ';
$PHPMAILER_LANG['file_open'] = 'هەڵەی پەڕگە(فایل): ناتوانرێت بکرێتەوە: ';
$PHPMAILER_LANG['from_failed'] = 'هەڵە لە ئاستی ناونیشانی نێرەر: ';
$PHPMAILER_LANG['instantiate'] = 'ناتوانرێت خزمەتگوزاری پۆستە پێشکەش بکرێت.';
$PHPMAILER_LANG['invalid_address'] = 'نەتوانرا بنێردرێت ، چونکە ناونیشانی ئیمەیڵەکە نادروستە: ';
$PHPMAILER_LANG['mailer_not_supported'] = ' مەیلەر پشتگیری ناکات';
$PHPMAILER_LANG['provide_address'] = 'دەبێت ناونیشانی ئیمەیڵی لانیکەم یەک وەرگر دابین بکرێت.';
$PHPMAILER_LANG['recipients_failed'] = ' هەڵەی SMTP: ئەم هەڵانەی خوارەوەشکستی هێنا لە ناردن بۆ هەردووکیان: ';
$PHPMAILER_LANG['signing'] = 'هەڵەی واژۆ: ';
$PHPMAILER_LANG['smtp_connect_failed'] = 'SMTP Connect()پەیوەندی شکستی هێنا .';
$PHPMAILER_LANG['smtp_error'] = 'هەڵەی ئاستی سێرڤەری SMTP: ';
$PHPMAILER_LANG['variable_set'] = 'ناتوانرێت بیگۆڕیت یان دوبارە بینێریتەوە: ';
$PHPMAILER_LANG['extension_missing'] = 'درێژکراوە نەماوە: ';

View file

@ -5,24 +5,32 @@
* @package PHPMailer * @package PHPMailer
* @author Alexey Chumakov <alex@chumakov.ru> * @author Alexey Chumakov <alex@chumakov.ru>
* @author Foster Snowhill <i18n@forstwoof.ru> * @author Foster Snowhill <i18n@forstwoof.ru>
* @author ProjectSoft <projectsoft2009@yandex.ru>
*/ */
$PHPMAILER_LANG['authenticate'] = 'Ошибка SMTP: ошибка авторизации.'; $PHPMAILER_LANG['authenticate'] = 'Ошибка SMTP: не удалось пройти аутентификацию.';
$PHPMAILER_LANG['buggy_php'] = 'В вашей версии PHP есть ошибка, которая может привести к повреждению сообщений. Чтобы исправить, переключитесь на отправку по SMTP, отключите опцию mail.add_x_header в ваш php.ini, переключитесь на MacOS или Linux или обновите PHP до версии 7.0.17+ или 7.1.3+.';
$PHPMAILER_LANG['connect_host'] = 'Ошибка SMTP: не удается подключиться к SMTP-серверу.'; $PHPMAILER_LANG['connect_host'] = 'Ошибка SMTP: не удается подключиться к SMTP-серверу.';
$PHPMAILER_LANG['data_not_accepted'] = 'Ошибка SMTP: данные не приняты.'; $PHPMAILER_LANG['data_not_accepted'] = 'Ошибка SMTP: данные не приняты.';
$PHPMAILER_LANG['empty_message'] = 'Пустое сообщение';
$PHPMAILER_LANG['encoding'] = 'Неизвестная кодировка: '; $PHPMAILER_LANG['encoding'] = 'Неизвестная кодировка: ';
$PHPMAILER_LANG['execute'] = 'Невозможно выполнить команду: '; $PHPMAILER_LANG['execute'] = 'Невозможно выполнить команду: ';
$PHPMAILER_LANG['extension_missing'] = 'Расширение отсутствует: ';
$PHPMAILER_LANG['file_access'] = 'Нет доступа к файлу: '; $PHPMAILER_LANG['file_access'] = 'Нет доступа к файлу: ';
$PHPMAILER_LANG['file_open'] = 'Файловая ошибка: не удаётся открыть файл: '; $PHPMAILER_LANG['file_open'] = 'Файловая ошибка: не удаётся открыть файл: ';
$PHPMAILER_LANG['from_failed'] = 'Неверный адрес отправителя: '; $PHPMAILER_LANG['from_failed'] = 'Неверный адрес отправителя: ';
$PHPMAILER_LANG['instantiate'] = 'Невозможно запустить функцию mail().'; $PHPMAILER_LANG['instantiate'] = 'Невозможно запустить функцию mail().';
$PHPMAILER_LANG['provide_address'] = 'Пожалуйста, введите хотя бы один email-адрес получателя.';
$PHPMAILER_LANG['mailer_not_supported'] = ' — почтовый сервер не поддерживается.';
$PHPMAILER_LANG['recipients_failed'] = 'Ошибка SMTP: не удалась отправка таким адресатам: ';
$PHPMAILER_LANG['empty_message'] = 'Пустое сообщение';
$PHPMAILER_LANG['invalid_address'] = 'Не отправлено из-за неправильного формата email-адреса: '; $PHPMAILER_LANG['invalid_address'] = 'Не отправлено из-за неправильного формата email-адреса: ';
$PHPMAILER_LANG['invalid_header'] = 'Неверное имя или значение заголовка';
$PHPMAILER_LANG['invalid_hostentry'] = 'Неверная запись хоста: ';
$PHPMAILER_LANG['invalid_host'] = 'Неверный хост: ';
$PHPMAILER_LANG['mailer_not_supported'] = ' — почтовый сервер не поддерживается.';
$PHPMAILER_LANG['provide_address'] = 'Вы должны указать хотя бы один адрес электронной почты получателя.';
$PHPMAILER_LANG['recipients_failed'] = 'Ошибка SMTP: Ошибка следующих получателей: ';
$PHPMAILER_LANG['signing'] = 'Ошибка подписи: '; $PHPMAILER_LANG['signing'] = 'Ошибка подписи: ';
$PHPMAILER_LANG['smtp_connect_failed'] = 'Ошибка соединения с SMTP-сервером'; $PHPMAILER_LANG['smtp_code'] = 'Код SMTP: ';
$PHPMAILER_LANG['smtp_code_ex'] = 'Дополнительная информация SMTP: ';
$PHPMAILER_LANG['smtp_connect_failed'] = 'Ошибка соединения с SMTP-сервером.';
$PHPMAILER_LANG['smtp_detail'] = 'Детали: ';
$PHPMAILER_LANG['smtp_error'] = 'Ошибка SMTP-сервера: '; $PHPMAILER_LANG['smtp_error'] = 'Ошибка SMTP-сервера: ';
$PHPMAILER_LANG['variable_set'] = 'Невозможно установить или сбросить переменную: '; $PHPMAILER_LANG['variable_set'] = 'Невозможно установить или сбросить переменную: ';
$PHPMAILER_LANG['extension_missing'] = 'Расширение отсутствует: ';

View file

@ -11,21 +11,28 @@
*/ */
$PHPMAILER_LANG['authenticate'] = 'SMTP Hatası: Oturum açılamadı.'; $PHPMAILER_LANG['authenticate'] = 'SMTP Hatası: Oturum açılamadı.';
$PHPMAILER_LANG['buggy_php'] = 'PHP sürümünüz iletilerin bozulmasına neden olabilecek bir hatadan etkileniyor. Bunu düzeltmek için, SMTP kullanarak göndermeye geçin, mail.add_x_header seçeneğini devre dışı bırakın php.ini dosyanızdaki mail.add_x_header seçeneğini devre dışı bırakın, MacOS veya Linux geçin veya PHP sürümünü 7.0.17+ veya 7.1.3+ sürümüne yükseltin,';
$PHPMAILER_LANG['connect_host'] = 'SMTP Hatası: SMTP sunucusuna bağlanılamadı.'; $PHPMAILER_LANG['connect_host'] = 'SMTP Hatası: SMTP sunucusuna bağlanılamadı.';
$PHPMAILER_LANG['data_not_accepted'] = 'SMTP Hatası: Veri kabul edilmedi.'; $PHPMAILER_LANG['data_not_accepted'] = 'SMTP Hatası: Veri kabul edilmedi.';
$PHPMAILER_LANG['empty_message'] = 'Mesajın içeriği boş'; $PHPMAILER_LANG['empty_message'] = 'Mesajın içeriği boş';
$PHPMAILER_LANG['encoding'] = 'Bilinmeyen karakter kodlama: '; $PHPMAILER_LANG['encoding'] = 'Bilinmeyen karakter kodlama: ';
$PHPMAILER_LANG['execute'] = 'Çalıştırılamadı: '; $PHPMAILER_LANG['execute'] = 'Çalıştırılamadı: ';
$PHPMAILER_LANG['extension_missing'] = 'Eklenti bulunamadı: ';
$PHPMAILER_LANG['file_access'] = 'Dosyaya erişilemedi: '; $PHPMAILER_LANG['file_access'] = 'Dosyaya erişilemedi: ';
$PHPMAILER_LANG['file_open'] = 'Dosya Hatası: Dosya açılamadı: '; $PHPMAILER_LANG['file_open'] = 'Dosya Hatası: Dosya açılamadı: ';
$PHPMAILER_LANG['from_failed'] = 'Belirtilen adreslere gönderme başarısız: '; $PHPMAILER_LANG['from_failed'] = 'Belirtilen adreslere gönderme başarısız: ';
$PHPMAILER_LANG['instantiate'] = 'Örnek e-posta fonksiyonu oluşturulamadı.'; $PHPMAILER_LANG['instantiate'] = 'Örnek e-posta fonksiyonu oluşturulamadı.';
$PHPMAILER_LANG['invalid_address'] = 'Geçersiz e-posta adresi: '; $PHPMAILER_LANG['invalid_address'] = 'Geçersiz e-posta adresi: ';
$PHPMAILER_LANG['invalid_header'] = 'Geçersiz başlık adı veya değeri: ';
$PHPMAILER_LANG['invalid_hostentry'] = 'Geçersiz ana bilgisayar girişi: ';
$PHPMAILER_LANG['invalid_host'] = 'Geçersiz ana bilgisayar: ';
$PHPMAILER_LANG['mailer_not_supported'] = ' e-posta kütüphanesi desteklenmiyor.'; $PHPMAILER_LANG['mailer_not_supported'] = ' e-posta kütüphanesi desteklenmiyor.';
$PHPMAILER_LANG['provide_address'] = 'En az bir alıcı e-posta adresi belirtmelisiniz.'; $PHPMAILER_LANG['provide_address'] = 'En az bir alıcı e-posta adresi belirtmelisiniz.';
$PHPMAILER_LANG['recipients_failed'] = 'SMTP Hatası: Belirtilen alıcılara ulaşılamadı: '; $PHPMAILER_LANG['recipients_failed'] = 'SMTP Hatası: Belirtilen alıcılara ulaşılamadı: ';
$PHPMAILER_LANG['signing'] = 'İmzalama hatası: '; $PHPMAILER_LANG['signing'] = 'İmzalama hatası: ';
$PHPMAILER_LANG['smtp_code'] = 'SMTP kodu: ';
$PHPMAILER_LANG['smtp_code_ex'] = 'ek SMTP bilgileri: ';
$PHPMAILER_LANG['smtp_connect_failed'] = 'SMTP connect() fonksiyonu başarısız.'; $PHPMAILER_LANG['smtp_connect_failed'] = 'SMTP connect() fonksiyonu başarısız.';
$PHPMAILER_LANG['smtp_detail'] = 'SMTP SMTP Detayı: ';
$PHPMAILER_LANG['smtp_error'] = 'SMTP sunucu hatası: '; $PHPMAILER_LANG['smtp_error'] = 'SMTP sunucu hatası: ';
$PHPMAILER_LANG['variable_set'] = 'Değişken ayarlanamadı ya da sıfırlanamadı: '; $PHPMAILER_LANG['variable_set'] = 'Değişken ayarlanamadı ya da sıfırlanamadı: ';
$PHPMAILER_LANG['extension_missing'] = 'Eklenti bulunamadı: ';

View file

@ -0,0 +1,30 @@
<?php
/**
* Urdu PHPMailer language file: refer to English translation for definitive list
* @package PHPMailer
* @author Saqib Ali Siddiqui <saqibsra@gmail.com>
*/
$PHPMAILER_LANG['authenticate'] = 'SMTP خرابی: تصدیق کرنے سے قاصر۔';
$PHPMAILER_LANG['connect_host'] = 'SMTP خرابی: سرور سے منسلک ہونے سے قاصر۔';
$PHPMAILER_LANG['data_not_accepted'] = 'SMTP خرابی: ڈیٹا قبول نہیں کیا گیا۔';
$PHPMAILER_LANG['empty_message'] = 'پیغام کی باڈی خالی ہے۔';
$PHPMAILER_LANG['encoding'] = 'نامعلوم انکوڈنگ: ';
$PHPMAILER_LANG['execute'] = 'عمل کرنے کے قابل نہیں ';
$PHPMAILER_LANG['file_access'] = 'فائل تک رسائی سے قاصر:';
$PHPMAILER_LANG['file_open'] = 'فائل کی خرابی: فائل کو کھولنے سے قاصر:';
$PHPMAILER_LANG['from_failed'] = 'درج ذیل بھیجنے والے کا پتہ ناکام ہو گیا:';
$PHPMAILER_LANG['instantiate'] = 'میل فنکشن کی مثال بنانے سے قاصر۔';
$PHPMAILER_LANG['invalid_address'] = 'بھیجنے سے قاصر: غلط ای میل پتہ:';
$PHPMAILER_LANG['mailer_not_supported'] = ' میلر تعاون یافتہ نہیں ہے۔';
$PHPMAILER_LANG['provide_address'] = 'آپ کو کم از کم ایک منزل کا ای میل پتہ فراہم کرنا چاہیے۔';
$PHPMAILER_LANG['recipients_failed'] = 'SMTP خرابی: درج ذیل پتہ پر نہیں بھیجا جاسکا: ';
$PHPMAILER_LANG['signing'] = 'دستخط کی خرابی: ';
$PHPMAILER_LANG['smtp_connect_failed'] = 'SMTP ملنا ناکام ہوا';
$PHPMAILER_LANG['smtp_error'] = 'SMTP سرور کی خرابی: ';
$PHPMAILER_LANG['variable_set'] = 'متغیر سیٹ نہیں کیا جا سکا: ';
$PHPMAILER_LANG['extension_missing'] = 'ایکٹینشن موجود نہیں ہے۔ ';
$PHPMAILER_LANG['smtp_code'] = 'SMTP سرور کوڈ: ';
$PHPMAILER_LANG['smtp_code_ex'] = 'اضافی SMTP سرور کی معلومات:';
$PHPMAILER_LANG['invalid_header'] = 'غلط ہیڈر کا نام یا قدر';

View file

@ -13,7 +13,7 @@
* @copyright 2012 - 2023 Marcus Bointon * @copyright 2012 - 2023 Marcus Bointon
* @copyright 2010 - 2012 Jim Jagielski * @copyright 2010 - 2012 Jim Jagielski
* @copyright 2004 - 2009 Andy Prevost * @copyright 2004 - 2009 Andy Prevost
* @license http://www.gnu.org/copyleft/lesser.html GNU Lesser General Public License * @license https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html GNU Lesser General Public License
* @note This program is distributed in the hope that it will be useful - WITHOUT * @note This program is distributed in the hope that it will be useful - WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. * FITNESS FOR A PARTICULAR PURPOSE.

View file

@ -13,7 +13,7 @@
* @copyright 2012 - 2020 Marcus Bointon * @copyright 2012 - 2020 Marcus Bointon
* @copyright 2010 - 2012 Jim Jagielski * @copyright 2010 - 2012 Jim Jagielski
* @copyright 2004 - 2009 Andy Prevost * @copyright 2004 - 2009 Andy Prevost
* @license http://www.gnu.org/copyleft/lesser.html GNU Lesser General Public License * @license https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html GNU Lesser General Public License
* @note This program is distributed in the hope that it will be useful - WITHOUT * @note This program is distributed in the hope that it will be useful - WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. * FITNESS FOR A PARTICULAR PURPOSE.

View file

@ -13,7 +13,7 @@
* @copyright 2012 - 2020 Marcus Bointon * @copyright 2012 - 2020 Marcus Bointon
* @copyright 2010 - 2012 Jim Jagielski * @copyright 2010 - 2012 Jim Jagielski
* @copyright 2004 - 2009 Andy Prevost * @copyright 2004 - 2009 Andy Prevost
* @license http://www.gnu.org/copyleft/lesser.html GNU Lesser General Public License * @license https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html GNU Lesser General Public License
* @note This program is distributed in the hope that it will be useful - WITHOUT * @note This program is distributed in the hope that it will be useful - WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. * FITNESS FOR A PARTICULAR PURPOSE.
@ -29,7 +29,7 @@ use League\OAuth2\Client\Token\AccessToken;
* OAuth - OAuth2 authentication wrapper class. * OAuth - OAuth2 authentication wrapper class.
* Uses the oauth2-client package from the League of Extraordinary Packages. * Uses the oauth2-client package from the League of Extraordinary Packages.
* *
* @see http://oauth2-client.thephpleague.com * @see https://oauth2-client.thephpleague.com
* *
* @author Marcus Bointon (Synchro/coolbru) <phpmailer@synchromedia.co.uk> * @author Marcus Bointon (Synchro/coolbru) <phpmailer@synchromedia.co.uk>
*/ */

View file

@ -13,7 +13,7 @@
* @copyright 2012 - 2020 Marcus Bointon * @copyright 2012 - 2020 Marcus Bointon
* @copyright 2010 - 2012 Jim Jagielski * @copyright 2010 - 2012 Jim Jagielski
* @copyright 2004 - 2009 Andy Prevost * @copyright 2004 - 2009 Andy Prevost
* @license http://www.gnu.org/copyleft/lesser.html GNU Lesser General Public License * @license https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html GNU Lesser General Public License
* @note This program is distributed in the hope that it will be useful - WITHOUT * @note This program is distributed in the hope that it will be useful - WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. * FITNESS FOR A PARTICULAR PURPOSE.

View file

@ -13,7 +13,7 @@
* @copyright 2012 - 2020 Marcus Bointon * @copyright 2012 - 2020 Marcus Bointon
* @copyright 2010 - 2012 Jim Jagielski * @copyright 2010 - 2012 Jim Jagielski
* @copyright 2004 - 2009 Andy Prevost * @copyright 2004 - 2009 Andy Prevost
* @license http://www.gnu.org/copyleft/lesser.html GNU Lesser General Public License * @license https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html GNU Lesser General Public License
* @note This program is distributed in the hope that it will be useful - WITHOUT * @note This program is distributed in the hope that it will be useful - WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. * FITNESS FOR A PARTICULAR PURPOSE.
@ -152,8 +152,7 @@ class PHPMailer
* Only supported in simple alt or alt_inline message types * Only supported in simple alt or alt_inline message types
* To generate iCal event structures, use classes like EasyPeasyICS or iCalcreator. * To generate iCal event structures, use classes like EasyPeasyICS or iCalcreator.
* *
* @see http://sprain.ch/blog/downloads/php-class-easypeasyics-create-ical-files-with-php/ * @see https://kigkonsult.se/iCalcreator/
* @see http://kigkonsult.se/iCalcreator/
* *
* @var string * @var string
*/ */
@ -254,7 +253,7 @@ class PHPMailer
* You can set your own, but it must be in the format "<id@domain>", * You can set your own, but it must be in the format "<id@domain>",
* as defined in RFC5322 section 3.6.4 or it will be ignored. * as defined in RFC5322 section 3.6.4 or it will be ignored.
* *
* @see https://tools.ietf.org/html/rfc5322#section-3.6.4 * @see https://www.rfc-editor.org/rfc/rfc5322#section-3.6.4
* *
* @var string * @var string
*/ */
@ -358,7 +357,7 @@ class PHPMailer
public $AuthType = ''; public $AuthType = '';
/** /**
* SMTP SMTPXClient command attibutes * SMTP SMTPXClient command attributes
* *
* @var array * @var array
*/ */
@ -388,7 +387,7 @@ class PHPMailer
* 'DELAY' will notify you if there is an unusual delay in delivery, but the actual * 'DELAY' will notify you if there is an unusual delay in delivery, but the actual
* delivery's outcome (success or failure) is not yet decided. * delivery's outcome (success or failure) is not yet decided.
* *
* @see https://tools.ietf.org/html/rfc3461 See section 4.1 for more information about NOTIFY * @see https://www.rfc-editor.org/rfc/rfc3461.html#section-4.1 for more information about NOTIFY
*/ */
public $dsn = ''; public $dsn = '';
@ -468,7 +467,7 @@ class PHPMailer
* Only applicable when sending via SMTP. * Only applicable when sending via SMTP.
* *
* @see https://en.wikipedia.org/wiki/Variable_envelope_return_path * @see https://en.wikipedia.org/wiki/Variable_envelope_return_path
* @see http://www.postfix.org/VERP_README.html Postfix VERP info * @see https://www.postfix.org/VERP_README.html Postfix VERP info
* *
* @var bool * @var bool
*/ */
@ -551,7 +550,7 @@ class PHPMailer
* The function that handles the result of the send email action. * The function that handles the result of the send email action.
* It is called out by send() for each email sent. * It is called out by send() for each email sent.
* *
* Value can be any php callable: http://www.php.net/is_callable * Value can be any php callable: https://www.php.net/is_callable
* *
* Parameters: * Parameters:
* bool $result result of the send action * bool $result result of the send action
@ -757,7 +756,7 @@ class PHPMailer
* *
* @var string * @var string
*/ */
const VERSION = '6.9.1'; const VERSION = '6.9.3';
/** /**
* Error severity: message only, continue processing. * Error severity: message only, continue processing.
@ -903,7 +902,7 @@ class PHPMailer
} }
//Is this a PSR-3 logger? //Is this a PSR-3 logger?
if ($this->Debugoutput instanceof \Psr\Log\LoggerInterface) { if ($this->Debugoutput instanceof \Psr\Log\LoggerInterface) {
$this->Debugoutput->debug($str); $this->Debugoutput->debug(rtrim($str, "\r\n"));
return; return;
} }
@ -1072,7 +1071,7 @@ class PHPMailer
* be modified after calling this function), addition of such addresses is delayed until send(). * be modified after calling this function), addition of such addresses is delayed until send().
* Addresses that have been added already return false, but do not throw exceptions. * Addresses that have been added already return false, but do not throw exceptions.
* *
* @param string $kind One of 'to', 'cc', 'bcc', or 'ReplyTo' * @param string $kind One of 'to', 'cc', 'bcc', or 'Reply-To'
* @param string $address The email address * @param string $address The email address
* @param string $name An optional username associated with the address * @param string $name An optional username associated with the address
* *
@ -1212,7 +1211,7 @@ class PHPMailer
* Uses the imap_rfc822_parse_adrlist function if the IMAP extension is available. * Uses the imap_rfc822_parse_adrlist function if the IMAP extension is available.
* Note that quotes in the name part are removed. * Note that quotes in the name part are removed.
* *
* @see http://www.andrew.cmu.edu/user/agreen1/testing/mrbs/web/Mail/RFC822.php A more careful implementation * @see https://www.andrew.cmu.edu/user/agreen1/testing/mrbs/web/Mail/RFC822.php A more careful implementation
* *
* @param string $addrstr The address list string * @param string $addrstr The address list string
* @param bool $useimap Whether to use the IMAP extension to parse the list * @param bool $useimap Whether to use the IMAP extension to parse the list
@ -1407,7 +1406,6 @@ class PHPMailer
* * IPv6 literals: 'first.last@[IPv6:a1::]' * * IPv6 literals: 'first.last@[IPv6:a1::]'
* Not all of these will necessarily work for sending! * Not all of these will necessarily work for sending!
* *
* @see http://squiloople.com/2009/12/20/email-address-validation/
* @copyright 2009-2010 Michael Rushton * @copyright 2009-2010 Michael Rushton
* Feel free to use and redistribute this code. But please keep this copyright notice. * Feel free to use and redistribute this code. But please keep this copyright notice.
*/ */
@ -1734,9 +1732,8 @@ class PHPMailer
//This sets the SMTP envelope sender which gets turned into a return-path header by the receiver //This sets the SMTP envelope sender which gets turned into a return-path header by the receiver
//A space after `-f` is optional, but there is a long history of its presence //A space after `-f` is optional, but there is a long history of its presence
//causing problems, so we don't use one //causing problems, so we don't use one
//Exim docs: http://www.exim.org/exim-html-current/doc/html/spec_html/ch-the_exim_command_line.html //Exim docs: https://www.exim.org/exim-html-current/doc/html/spec_html/ch-the_exim_command_line.html
//Sendmail docs: http://www.sendmail.org/~ca/email/man/sendmail.html //Sendmail docs: https://www.sendmail.org/~ca/email/man/sendmail.html
//Qmail docs: http://www.qmail.org/man/man8/qmail-inject.html
//Example problem: https://www.drupal.org/node/1057954 //Example problem: https://www.drupal.org/node/1057954
//PHP 5.6 workaround //PHP 5.6 workaround
@ -1874,7 +1871,7 @@ class PHPMailer
*/ */
protected static function isPermittedPath($path) protected static function isPermittedPath($path)
{ {
//Matches scheme definition from https://tools.ietf.org/html/rfc3986#section-3.1 //Matches scheme definition from https://www.rfc-editor.org/rfc/rfc3986#section-3.1
return !preg_match('#^[a-z][a-z\d+.-]*://#i', $path); return !preg_match('#^[a-z][a-z\d+.-]*://#i', $path);
} }
@ -1901,7 +1898,7 @@ class PHPMailer
/** /**
* Send mail using the PHP mail() function. * Send mail using the PHP mail() function.
* *
* @see http://www.php.net/manual/en/book.mail.php * @see https://www.php.net/manual/en/book.mail.php
* *
* @param string $header The message headers * @param string $header The message headers
* @param string $body The message body * @param string $body The message body
@ -1931,9 +1928,8 @@ class PHPMailer
//This sets the SMTP envelope sender which gets turned into a return-path header by the receiver //This sets the SMTP envelope sender which gets turned into a return-path header by the receiver
//A space after `-f` is optional, but there is a long history of its presence //A space after `-f` is optional, but there is a long history of its presence
//causing problems, so we don't use one //causing problems, so we don't use one
//Exim docs: http://www.exim.org/exim-html-current/doc/html/spec_html/ch-the_exim_command_line.html //Exim docs: https://www.exim.org/exim-html-current/doc/html/spec_html/ch-the_exim_command_line.html
//Sendmail docs: http://www.sendmail.org/~ca/email/man/sendmail.html //Sendmail docs: https://www.sendmail.org/~ca/email/man/sendmail.html
//Qmail docs: http://www.qmail.org/man/man8/qmail-inject.html
//Example problem: https://www.drupal.org/node/1057954 //Example problem: https://www.drupal.org/node/1057954
//CVE-2016-10033, CVE-2016-10045: Don't pass -f if characters will be escaped. //CVE-2016-10033, CVE-2016-10045: Don't pass -f if characters will be escaped.
@ -2709,7 +2705,7 @@ class PHPMailer
} }
//Only allow a custom message ID if it conforms to RFC 5322 section 3.6.4 //Only allow a custom message ID if it conforms to RFC 5322 section 3.6.4
//https://tools.ietf.org/html/rfc5322#section-3.6.4 //https://www.rfc-editor.org/rfc/rfc5322#section-3.6.4
if ( if (
'' !== $this->MessageID && '' !== $this->MessageID &&
preg_match( preg_match(
@ -3634,7 +3630,7 @@ class PHPMailer
* without breaking lines within a character. * without breaking lines within a character.
* Adapted from a function by paravoid. * Adapted from a function by paravoid.
* *
* @see http://www.php.net/manual/en/function.mb-encode-mimeheader.php#60283 * @see https://www.php.net/manual/en/function.mb-encode-mimeheader.php#60283
* *
* @param string $str multi-byte text to wrap encode * @param string $str multi-byte text to wrap encode
* @param string $linebreak string to use as linefeed/end-of-line * @param string $linebreak string to use as linefeed/end-of-line
@ -3690,7 +3686,7 @@ class PHPMailer
/** /**
* Encode a string using Q encoding. * Encode a string using Q encoding.
* *
* @see http://tools.ietf.org/html/rfc2047#section-4.2 * @see https://www.rfc-editor.org/rfc/rfc2047#section-4.2
* *
* @param string $str the text to encode * @param string $str the text to encode
* @param string $position Where the text is going to be used, see the RFC for what that means * @param string $position Where the text is going to be used, see the RFC for what that means
@ -4228,7 +4224,7 @@ class PHPMailer
$result = $_SERVER['SERVER_NAME']; $result = $_SERVER['SERVER_NAME'];
} elseif (function_exists('gethostname') && gethostname() !== false) { } elseif (function_exists('gethostname') && gethostname() !== false) {
$result = gethostname(); $result = gethostname();
} elseif (php_uname('n') !== false) { } elseif (php_uname('n') !== '') {
$result = php_uname('n'); $result = php_uname('n');
} }
if (!static::isValidHost($result)) { if (!static::isValidHost($result)) {
@ -4253,7 +4249,7 @@ class PHPMailer
empty($host) empty($host)
|| !is_string($host) || !is_string($host)
|| strlen($host) > 256 || strlen($host) > 256
|| !preg_match('/^([a-zA-Z\d.-]*|\[[a-fA-F\d:]+\])$/', $host) || !preg_match('/^([a-z\d.-]*|\[[a-f\d:]+\])$/i', $host)
) { ) {
return false; return false;
} }
@ -4267,8 +4263,8 @@ class PHPMailer
//Is it a valid IPv4 address? //Is it a valid IPv4 address?
return filter_var($host, FILTER_VALIDATE_IP, FILTER_FLAG_IPV4) !== false; return filter_var($host, FILTER_VALIDATE_IP, FILTER_FLAG_IPV4) !== false;
} }
//Is it a syntactically valid hostname (when embeded in a URL)? //Is it a syntactically valid hostname (when embedded in a URL)?
return filter_var('http://' . $host, FILTER_VALIDATE_URL) !== false; return filter_var('https://' . $host, FILTER_VALIDATE_URL) !== false;
} }
/** /**
@ -4679,7 +4675,7 @@ class PHPMailer
* Multi-byte-safe pathinfo replacement. * Multi-byte-safe pathinfo replacement.
* Drop-in replacement for pathinfo(), but multibyte- and cross-platform-safe. * Drop-in replacement for pathinfo(), but multibyte- and cross-platform-safe.
* *
* @see http://www.php.net/manual/en/function.pathinfo.php#107461 * @see https://www.php.net/manual/en/function.pathinfo.php#107461
* *
* @param string $path A filename or path, does not need to exist as a file * @param string $path A filename or path, does not need to exist as a file
* @param int|string $options Either a PATHINFO_* constant, * @param int|string $options Either a PATHINFO_* constant,
@ -4914,7 +4910,7 @@ class PHPMailer
* Uses the 'relaxed' algorithm from RFC6376 section 3.4.2. * Uses the 'relaxed' algorithm from RFC6376 section 3.4.2.
* Canonicalized headers should *always* use CRLF, regardless of mailer setting. * Canonicalized headers should *always* use CRLF, regardless of mailer setting.
* *
* @see https://tools.ietf.org/html/rfc6376#section-3.4.2 * @see https://www.rfc-editor.org/rfc/rfc6376#section-3.4.2
* *
* @param string $signHeader Header * @param string $signHeader Header
* *
@ -4926,7 +4922,7 @@ class PHPMailer
$signHeader = static::normalizeBreaks($signHeader, self::CRLF); $signHeader = static::normalizeBreaks($signHeader, self::CRLF);
//Unfold header lines //Unfold header lines
//Note PCRE \s is too broad a definition of whitespace; RFC5322 defines it as `[ \t]` //Note PCRE \s is too broad a definition of whitespace; RFC5322 defines it as `[ \t]`
//@see https://tools.ietf.org/html/rfc5322#section-2.2 //@see https://www.rfc-editor.org/rfc/rfc5322#section-2.2
//That means this may break if you do something daft like put vertical tabs in your headers. //That means this may break if you do something daft like put vertical tabs in your headers.
$signHeader = preg_replace('/\r\n[ \t]+/', ' ', $signHeader); $signHeader = preg_replace('/\r\n[ \t]+/', ' ', $signHeader);
//Break headers out into an array //Break headers out into an array
@ -4958,7 +4954,7 @@ class PHPMailer
* Uses the 'simple' algorithm from RFC6376 section 3.4.3. * Uses the 'simple' algorithm from RFC6376 section 3.4.3.
* Canonicalized bodies should *always* use CRLF, regardless of mailer setting. * Canonicalized bodies should *always* use CRLF, regardless of mailer setting.
* *
* @see https://tools.ietf.org/html/rfc6376#section-3.4.3 * @see https://www.rfc-editor.org/rfc/rfc6376#section-3.4.3
* *
* @param string $body Message Body * @param string $body Message Body
* *
@ -4994,7 +4990,7 @@ class PHPMailer
$DKIMquery = 'dns/txt'; //Query method $DKIMquery = 'dns/txt'; //Query method
$DKIMtime = time(); $DKIMtime = time();
//Always sign these headers without being asked //Always sign these headers without being asked
//Recommended list from https://tools.ietf.org/html/rfc6376#section-5.4.1 //Recommended list from https://www.rfc-editor.org/rfc/rfc6376#section-5.4.1
$autoSignHeaders = [ $autoSignHeaders = [
'from', 'from',
'to', 'to',
@ -5100,7 +5096,7 @@ class PHPMailer
} }
//The DKIM-Signature header is included in the signature *except for* the value of the `b` tag //The DKIM-Signature header is included in the signature *except for* the value of the `b` tag
//which is appended after calculating the signature //which is appended after calculating the signature
//https://tools.ietf.org/html/rfc6376#section-3.5 //https://www.rfc-editor.org/rfc/rfc6376#section-3.5
$dkimSignatureHeader = 'DKIM-Signature: v=1;' . $dkimSignatureHeader = 'DKIM-Signature: v=1;' .
' d=' . $this->DKIM_domain . ';' . ' d=' . $this->DKIM_domain . ';' .
' s=' . $this->DKIM_selector . ';' . static::$LE . ' s=' . $this->DKIM_selector . ';' . static::$LE .

View file

@ -13,7 +13,7 @@
* @copyright 2012 - 2020 Marcus Bointon * @copyright 2012 - 2020 Marcus Bointon
* @copyright 2010 - 2012 Jim Jagielski * @copyright 2010 - 2012 Jim Jagielski
* @copyright 2004 - 2009 Andy Prevost * @copyright 2004 - 2009 Andy Prevost
* @license http://www.gnu.org/copyleft/lesser.html GNU Lesser General Public License * @license https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html GNU Lesser General Public License
* @note This program is distributed in the hope that it will be useful - WITHOUT * @note This program is distributed in the hope that it will be useful - WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. * FITNESS FOR A PARTICULAR PURPOSE.
@ -46,7 +46,7 @@ class POP3
* *
* @var string * @var string
*/ */
const VERSION = '6.9.1'; const VERSION = '6.9.3';
/** /**
* Default POP3 port number. * Default POP3 port number.
@ -250,7 +250,9 @@ class POP3
//On Windows this will raise a PHP Warning error if the hostname doesn't exist. //On Windows this will raise a PHP Warning error if the hostname doesn't exist.
//Rather than suppress it with @fsockopen, capture it cleanly instead //Rather than suppress it with @fsockopen, capture it cleanly instead
set_error_handler([$this, 'catchWarning']); set_error_handler(function () {
call_user_func_array([$this, 'catchWarning'], func_get_args());
});
if (false === $port) { if (false === $port) {
$port = static::DEFAULT_PORT; $port = static::DEFAULT_PORT;

View file

@ -13,7 +13,7 @@
* @copyright 2012 - 2020 Marcus Bointon * @copyright 2012 - 2020 Marcus Bointon
* @copyright 2010 - 2012 Jim Jagielski * @copyright 2010 - 2012 Jim Jagielski
* @copyright 2004 - 2009 Andy Prevost * @copyright 2004 - 2009 Andy Prevost
* @license http://www.gnu.org/copyleft/lesser.html GNU Lesser General Public License * @license https://www.gnu.org/licenses/old-licenses/lgpl-2.1.html GNU Lesser General Public License
* @note This program is distributed in the hope that it will be useful - WITHOUT * @note This program is distributed in the hope that it will be useful - WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. * FITNESS FOR A PARTICULAR PURPOSE.
@ -35,7 +35,7 @@ class SMTP
* *
* @var string * @var string
*/ */
const VERSION = '6.9.1'; const VERSION = '6.9.3';
/** /**
* SMTP line break constant. * SMTP line break constant.
@ -62,7 +62,7 @@ class SMTP
* The maximum line length allowed by RFC 5321 section 4.5.3.1.6, * The maximum line length allowed by RFC 5321 section 4.5.3.1.6,
* *excluding* a trailing CRLF break. * *excluding* a trailing CRLF break.
* *
* @see https://tools.ietf.org/html/rfc5321#section-4.5.3.1.6 * @see https://www.rfc-editor.org/rfc/rfc5321#section-4.5.3.1.6
* *
* @var int * @var int
*/ */
@ -72,7 +72,7 @@ class SMTP
* The maximum line length allowed for replies in RFC 5321 section 4.5.3.1.5, * The maximum line length allowed for replies in RFC 5321 section 4.5.3.1.5,
* *including* a trailing CRLF line break. * *including* a trailing CRLF line break.
* *
* @see https://tools.ietf.org/html/rfc5321#section-4.5.3.1.5 * @see https://www.rfc-editor.org/rfc/rfc5321#section-4.5.3.1.5
* *
* @var int * @var int
*/ */
@ -152,8 +152,8 @@ class SMTP
/** /**
* Whether to use VERP. * Whether to use VERP.
* *
* @see http://en.wikipedia.org/wiki/Variable_envelope_return_path * @see https://en.wikipedia.org/wiki/Variable_envelope_return_path
* @see http://www.postfix.org/VERP_README.html Info on VERP * @see https://www.postfix.org/VERP_README.html Info on VERP
* *
* @var bool * @var bool
*/ */
@ -164,7 +164,7 @@ class SMTP
* Default of 5 minutes (300sec) is from RFC2821 section 4.5.3.2. * Default of 5 minutes (300sec) is from RFC2821 section 4.5.3.2.
* This needs to be quite high to function correctly with hosts using greetdelay as an anti-spam measure. * This needs to be quite high to function correctly with hosts using greetdelay as an anti-spam measure.
* *
* @see http://tools.ietf.org/html/rfc2821#section-4.5.3.2 * @see https://www.rfc-editor.org/rfc/rfc2821#section-4.5.3.2
* *
* @var int * @var int
*/ */
@ -187,12 +187,12 @@ class SMTP
*/ */
protected $smtp_transaction_id_patterns = [ protected $smtp_transaction_id_patterns = [
'exim' => '/[\d]{3} OK id=(.*)/', 'exim' => '/[\d]{3} OK id=(.*)/',
'sendmail' => '/[\d]{3} 2.0.0 (.*) Message/', 'sendmail' => '/[\d]{3} 2\.0\.0 (.*) Message/',
'postfix' => '/[\d]{3} 2.0.0 Ok: queued as (.*)/', 'postfix' => '/[\d]{3} 2\.0\.0 Ok: queued as (.*)/',
'Microsoft_ESMTP' => '/[0-9]{3} 2.[\d].0 (.*)@(?:.*) Queued mail for delivery/', 'Microsoft_ESMTP' => '/[0-9]{3} 2\.[\d]\.0 (.*)@(?:.*) Queued mail for delivery/',
'Amazon_SES' => '/[\d]{3} Ok (.*)/', 'Amazon_SES' => '/[\d]{3} Ok (.*)/',
'SendGrid' => '/[\d]{3} Ok: queued as (.*)/', 'SendGrid' => '/[\d]{3} Ok: queued as (.*)/',
'CampaignMonitor' => '/[\d]{3} 2.0.0 OK:([a-zA-Z\d]{48})/', 'CampaignMonitor' => '/[\d]{3} 2\.0\.0 OK:([a-zA-Z\d]{48})/',
'Haraka' => '/[\d]{3} Message Queued \((.*)\)/', 'Haraka' => '/[\d]{3} Message Queued \((.*)\)/',
'ZoneMTA' => '/[\d]{3} Message queued as (.*)/', 'ZoneMTA' => '/[\d]{3} Message queued as (.*)/',
'Mailjet' => '/[\d]{3} OK queued as (.*)/', 'Mailjet' => '/[\d]{3} OK queued as (.*)/',
@ -280,7 +280,8 @@ class SMTP
} }
//Is this a PSR-3 logger? //Is this a PSR-3 logger?
if ($this->Debugoutput instanceof \Psr\Log\LoggerInterface) { if ($this->Debugoutput instanceof \Psr\Log\LoggerInterface) {
$this->Debugoutput->debug($str); //Remove trailing line breaks potentially added by calls to SMTP::client_send()
$this->Debugoutput->debug(rtrim($str, "\r\n"));
return; return;
} }
@ -293,6 +294,7 @@ class SMTP
switch ($this->Debugoutput) { switch ($this->Debugoutput) {
case 'error_log': case 'error_log':
//Don't output, just log //Don't output, just log
/** @noinspection ForgottenDebugOutputInspection */
error_log($str); error_log($str);
break; break;
case 'html': case 'html':
@ -371,7 +373,7 @@ class SMTP
} }
//Anything other than a 220 response means something went wrong //Anything other than a 220 response means something went wrong
//RFC 5321 says the server will wait for us to send a QUIT in response to a 554 error //RFC 5321 says the server will wait for us to send a QUIT in response to a 554 error
//https://tools.ietf.org/html/rfc5321#section-3.1 //https://www.rfc-editor.org/rfc/rfc5321#section-3.1
if ($responseCode === 554) { if ($responseCode === 554) {
$this->quit(); $this->quit();
} }
@ -404,7 +406,9 @@ class SMTP
$errstr = ''; $errstr = '';
if ($streamok) { if ($streamok) {
$socket_context = stream_context_create($options); $socket_context = stream_context_create($options);
set_error_handler([$this, 'errorHandler']); set_error_handler(function () {
call_user_func_array([$this, 'errorHandler'], func_get_args());
});
$connection = stream_socket_client( $connection = stream_socket_client(
$host . ':' . $port, $host . ':' . $port,
$errno, $errno,
@ -419,7 +423,9 @@ class SMTP
'Connection: stream_socket_client not available, falling back to fsockopen', 'Connection: stream_socket_client not available, falling back to fsockopen',
self::DEBUG_CONNECTION self::DEBUG_CONNECTION
); );
set_error_handler([$this, 'errorHandler']); set_error_handler(function () {
call_user_func_array([$this, 'errorHandler'], func_get_args());
});
$connection = fsockopen( $connection = fsockopen(
$host, $host,
$port, $port,
@ -483,7 +489,9 @@ class SMTP
} }
//Begin encrypted connection //Begin encrypted connection
set_error_handler([$this, 'errorHandler']); set_error_handler(function () {
call_user_func_array([$this, 'errorHandler'], func_get_args());
});
$crypto_ok = stream_socket_enable_crypto( $crypto_ok = stream_socket_enable_crypto(
$this->smtp_conn, $this->smtp_conn,
true, true,
@ -574,7 +582,7 @@ class SMTP
} }
//Send encoded username and password //Send encoded username and password
if ( if (
//Format from https://tools.ietf.org/html/rfc4616#section-2 //Format from https://www.rfc-editor.org/rfc/rfc4616#section-2
//We skip the first field (it's forgery), so the string starts with a null byte //We skip the first field (it's forgery), so the string starts with a null byte
!$this->sendCommand( !$this->sendCommand(
'User & Password', 'User & Password',
@ -648,7 +656,7 @@ class SMTP
} }
//The following borrowed from //The following borrowed from
//http://php.net/manual/en/function.mhash.php#27225 //https://www.php.net/manual/en/function.mhash.php#27225
//RFC 2104 HMAC implementation for php. //RFC 2104 HMAC implementation for php.
//Creates an md5 HMAC. //Creates an md5 HMAC.
@ -787,7 +795,7 @@ class SMTP
//Send the lines to the server //Send the lines to the server
foreach ($lines_out as $line_out) { foreach ($lines_out as $line_out) {
//Dot-stuffing as per RFC5321 section 4.5.2 //Dot-stuffing as per RFC5321 section 4.5.2
//https://tools.ietf.org/html/rfc5321#section-4.5.2 //https://www.rfc-editor.org/rfc/rfc5321#section-4.5.2
if (!empty($line_out) && $line_out[0] === '.') { if (!empty($line_out) && $line_out[0] === '.') {
$line_out = '.' . $line_out; $line_out = '.' . $line_out;
} }
@ -1162,7 +1170,9 @@ class SMTP
} else { } else {
$this->edebug('CLIENT -> SERVER: ' . $data, self::DEBUG_CLIENT); $this->edebug('CLIENT -> SERVER: ' . $data, self::DEBUG_CLIENT);
} }
set_error_handler([$this, 'errorHandler']); set_error_handler(function () {
call_user_func_array([$this, 'errorHandler'], func_get_args());
});
$result = fwrite($this->smtp_conn, $data); $result = fwrite($this->smtp_conn, $data);
restore_error_handler(); restore_error_handler();
@ -1265,7 +1275,9 @@ class SMTP
while (is_resource($this->smtp_conn) && !feof($this->smtp_conn)) { while (is_resource($this->smtp_conn) && !feof($this->smtp_conn)) {
//Must pass vars in here as params are by reference //Must pass vars in here as params are by reference
//solution for signals inspired by https://github.com/symfony/symfony/pull/6540 //solution for signals inspired by https://github.com/symfony/symfony/pull/6540
set_error_handler([$this, 'errorHandler']); set_error_handler(function () {
call_user_func_array([$this, 'errorHandler'], func_get_args());
});
$n = stream_select($selR, $selW, $selW, $this->Timelimit); $n = stream_select($selR, $selW, $selW, $this->Timelimit);
restore_error_handler(); restore_error_handler();

View file

@ -128,7 +128,7 @@ class Hash
/** /**
* Outer XOR (Internal HMAC) * Outer XOR (Internal HMAC)
* *
* Used only for sha512/* * Used only for sha512
* *
* @see self::hash() * @see self::hash()
* @var string * @var string
@ -138,7 +138,7 @@ class Hash
/** /**
* Inner XOR (Internal HMAC) * Inner XOR (Internal HMAC)
* *
* Used only for sha512/* * Used only for sha512
* *
* @see self::hash() * @see self::hash()
* @var string * @var string
@ -285,12 +285,16 @@ class Hash
*/ */
public function setHash($hash) public function setHash($hash)
{ {
$oldHash = $this->hashParam;
$this->hashParam = $hash = strtolower($hash); $this->hashParam = $hash = strtolower($hash);
switch ($hash) { switch ($hash) {
case 'umac-32': case 'umac-32':
case 'umac-64': case 'umac-64':
case 'umac-96': case 'umac-96':
case 'umac-128': case 'umac-128':
if ($oldHash != $this->hashParam) {
$this->recomputeAESKey = true;
}
$this->blockSize = 128; $this->blockSize = 128;
$this->length = abs(substr($hash, -3)) >> 3; $this->length = abs(substr($hash, -3)) >> 3;
$this->algo = 'umac'; $this->algo = 'umac';
@ -418,13 +422,17 @@ class Hash
'0F6D2B697BD44DA8', '77E36F7304C48942', '3F9D85A86A1D36C8', '1112E6AD91D692A1' '0F6D2B697BD44DA8', '77E36F7304C48942', '3F9D85A86A1D36C8', '1112E6AD91D692A1'
]; ];
for ($i = 0; $i < 8; $i++) { for ($i = 0; $i < 8; $i++) {
if (PHP_INT_SIZE == 8) {
list(, $initial[$i]) = unpack('J', pack('H*', $initial[$i]));
} else {
$initial[$i] = new BigInteger($initial[$i], 16); $initial[$i] = new BigInteger($initial[$i], 16);
$initial[$i]->setPrecision(64); $initial[$i]->setPrecision(64);
} }
}
$this->parameters = compact('initial'); $this->parameters = compact('initial');
$hash = ['phpseclib3\Crypt\Hash', 'sha512']; $hash = ['phpseclib3\Crypt\Hash', PHP_INT_SIZE == 8 ? 'sha512_64' : 'sha512'];
} }
} }
@ -564,11 +572,14 @@ class Hash
// For each chunk, except the last: endian-adjust, NH hash // For each chunk, except the last: endian-adjust, NH hash
// and add bit-length. Use results to build Y. // and add bit-length. Use results to build Y.
// //
$length = new BigInteger(1024 * 8); $length = 1024 * 8;
$y = ''; $y = '';
for ($i = 0; $i < count($m) - 1; $i++) { for ($i = 0; $i < count($m) - 1; $i++) {
$m[$i] = pack('N*', ...unpack('V*', $m[$i])); // ENDIAN-SWAP $m[$i] = pack('N*', ...unpack('V*', $m[$i])); // ENDIAN-SWAP
$y .= static::nh($k, $m[$i], $length); $y .= PHP_INT_SIZE == 8 ?
static::nh64($k, $m[$i], $length) :
static::nh32($k, $m[$i], $length);
} }
// //
@ -581,70 +592,256 @@ class Hash
$m[$i] = str_pad(isset($m[$i]) ? $m[$i] : '', $pad, "\0"); // zeropad $m[$i] = str_pad(isset($m[$i]) ? $m[$i] : '', $pad, "\0"); // zeropad
$m[$i] = pack('N*', ...unpack('V*', $m[$i])); // ENDIAN-SWAP $m[$i] = pack('N*', ...unpack('V*', $m[$i])); // ENDIAN-SWAP
$y .= static::nh($k, $m[$i], new BigInteger($length * 8)); $y .= PHP_INT_SIZE == 8 ?
static::nh64($k, $m[$i], $length * 8) :
static::nh32($k, $m[$i], $length * 8);
return $y; return $y;
} }
/** /**
* NH Algorithm * 32-bit safe 64-bit Multiply with 2x 32-bit ints
*
* @param int $x
* @param int $y
* @return string $x * $y
*/
private static function mul32_64($x, $y)
{
// see mul64() for a more detailed explanation of how this works
$x1 = ($x >> 16) & 0xFFFF;
$x0 = $x & 0xFFFF;
$y1 = ($y >> 16) & 0xFFFF;
$y0 = $y & 0xFFFF;
// the following 3x lines will possibly yield floats
$z2 = $x1 * $y1;
$z0 = $x0 * $y0;
$z1 = $x1 * $y0 + $x0 * $y1;
$a = intval(fmod($z0, 65536));
$b = intval($z0 / 65536) + intval(fmod($z1, 65536));
$c = intval($z1 / 65536) + intval(fmod($z2, 65536)) + intval($b / 65536);
$b = intval(fmod($b, 65536));
$d = intval($z2 / 65536) + intval($c / 65536);
$c = intval(fmod($c, 65536));
$d = intval(fmod($d, 65536));
return pack('n4', $d, $c, $b, $a);
}
/**
* 32-bit safe 64-bit Addition with 2x 64-bit strings
*
* @param int $x
* @param int $y
* @return int $x * $y
*/
private static function add32_64($x, $y)
{
list(, $x1, $x2, $x3, $x4) = unpack('n4', $x);
list(, $y1, $y2, $y3, $y4) = unpack('n4', $y);
$a = $x4 + $y4;
$b = $x3 + $y3 + ($a >> 16);
$c = $x2 + $y2 + ($b >> 16);
$d = $x1 + $y1 + ($c >> 16);
return pack('n4', $d, $c, $b, $a);
}
/**
* 32-bit safe 32-bit Addition with 2x 32-bit strings
*
* @param int $x
* @param int $y
* @return int $x * $y
*/
private static function add32($x, $y)
{
// see add64() for a more detailed explanation of how this works
$x1 = $x & 0xFFFF;
$x2 = ($x >> 16) & 0xFFFF;
$y1 = $y & 0xFFFF;
$y2 = ($y >> 16) & 0xFFFF;
$a = $x1 + $y1;
$b = ($x2 + $y2 + ($a >> 16)) << 16;
$a &= 0xFFFF;
return $a | $b;
}
/**
* NH Algorithm / 32-bit safe
* *
* @param string $k string of length 1024 bytes. * @param string $k string of length 1024 bytes.
* @param string $m string with length divisible by 32 bytes. * @param string $m string with length divisible by 32 bytes.
* @return string string of length 8 bytes. * @return string string of length 8 bytes.
*/ */
private static function nh($k, $m, $length) private static function nh32($k, $m, $length)
{ {
$toUInt32 = function ($x) {
$x = new BigInteger($x, 256);
$x->setPrecision(32);
return $x;
};
// //
// Break M and K into 4-byte chunks // Break M and K into 4-byte chunks
// //
//$t = strlen($m) >> 2; $k = unpack('N*', $k);
$m = str_split($m, 4); $m = unpack('N*', $m);
$t = count($m); $t = count($m);
$k = str_split($k, 4);
$k = array_pad(array_slice($k, 0, $t), $t, 0);
$m = array_map($toUInt32, $m);
$k = array_map($toUInt32, $k);
// //
// Perform NH hash on the chunks, pairing words for multiplication // Perform NH hash on the chunks, pairing words for multiplication
// which are 4 apart to accommodate vector-parallelism. // which are 4 apart to accommodate vector-parallelism.
// //
$y = new BigInteger(); $i = 1;
$y->setPrecision(64); $y = "\0\0\0\0\0\0\0\0";
$i = 0; while ($i <= $t) {
while ($i < $t) { $temp = self::add32($m[$i], $k[$i]);
$temp = $m[$i]->add($k[$i]); $temp2 = self::add32($m[$i + 4], $k[$i + 4]);
$temp->setPrecision(64); $y = self::add32_64($y, self::mul32_64($temp, $temp2));
$temp = $temp->multiply($m[$i + 4]->add($k[$i + 4]));
$y = $y->add($temp);
$temp = $m[$i + 1]->add($k[$i + 1]); $temp = self::add32($m[$i + 1], $k[$i + 1]);
$temp->setPrecision(64); $temp2 = self::add32($m[$i + 5], $k[$i + 5]);
$temp = $temp->multiply($m[$i + 5]->add($k[$i + 5])); $y = self::add32_64($y, self::mul32_64($temp, $temp2));
$y = $y->add($temp);
$temp = $m[$i + 2]->add($k[$i + 2]); $temp = self::add32($m[$i + 2], $k[$i + 2]);
$temp->setPrecision(64); $temp2 = self::add32($m[$i + 6], $k[$i + 6]);
$temp = $temp->multiply($m[$i + 6]->add($k[$i + 6])); $y = self::add32_64($y, self::mul32_64($temp, $temp2));
$y = $y->add($temp);
$temp = $m[$i + 3]->add($k[$i + 3]); $temp = self::add32($m[$i + 3], $k[$i + 3]);
$temp->setPrecision(64); $temp2 = self::add32($m[$i + 7], $k[$i + 7]);
$temp = $temp->multiply($m[$i + 7]->add($k[$i + 7])); $y = self::add32_64($y, self::mul32_64($temp, $temp2));
$y = $y->add($temp);
$i += 8; $i += 8;
} }
return $y->add($length)->toBytes(); return self::add32_64($y, pack('N2', 0, $length));
}
/**
* 64-bit Multiply with 2x 32-bit ints
*
* @param int $x
* @param int $y
* @return int $x * $y
*/
private static function mul64($x, $y)
{
// since PHP doesn't implement unsigned integers we'll implement them with signed integers
// to do this we'll use karatsuba multiplication
$x1 = $x >> 16;
$x0 = $x & 0xFFFF;
$y1 = $y >> 16;
$y0 = $y & 0xFFFF;
$z2 = $x1 * $y1; // up to 32 bits long
$z0 = $x0 * $y0; // up to 32 bits long
$z1 = $x1 * $y0 + $x0 * $y1; // up to 33 bit long
// normally karatsuba multiplication calculates $z1 thusly:
//$z1 = ($x1 + $x0) * ($y0 + $y1) - $z2 - $z0;
// the idea being to eliminate one extra multiplication. for arbitrary precision math that makes sense
// but not for this purpose
// at this point karatsuba would normally return this:
//return ($z2 << 64) + ($z1 << 32) + $z0;
// the problem is that the output could be out of range for signed 64-bit ints,
// which would cause PHP to switch to floats, which would risk losing the lower few bits
// as such we'll OR 4x 16-bit blocks together like so:
/*
........ | ........ | ........ | ........
upper $z2 | lower $z2 | lower $z1 | lower $z0
| +upper $z1 | +upper $z0 |
+ $carry | + $carry | |
*/
// technically upper $z1 is 17 bit - not 16 - but the most significant digit of that will
// just get added to $carry
$a = $z0 & 0xFFFF;
$b = ($z0 >> 16) + ($z1 & 0xFFFF);
$c = ($z1 >> 16) + ($z2 & 0xFFFF) + ($b >> 16);
$b = ($b & 0xFFFF) << 16;
$d = ($z2 >> 16) + ($c >> 16);
$c = ($c & 0xFFFF) << 32;
$d = ($d & 0xFFFF) << 48;
return $a | $b | $c | $d;
}
/**
* 64-bit Addition with 2x 64-bit ints
*
* @param int $x
* @param int $y
* @return int $x + $y
*/
private static function add64($x, $y)
{
// doing $x + $y risks returning a result that's out of range for signed 64-bit ints
// in that event PHP would convert the result to a float and precision would be lost
// so we'll just add 2x 32-bit ints together like so:
/*
........ | ........
upper $x | lower $x
+upper $y |+lower $y
+ $carry |
*/
$x1 = $x & 0xFFFFFFFF;
$x2 = ($x >> 32) & 0xFFFFFFFF;
$y1 = $y & 0xFFFFFFFF;
$y2 = ($y >> 32) & 0xFFFFFFFF;
$a = $x1 + $y1;
$b = ($x2 + $y2 + ($a >> 32)) << 32;
$a &= 0xFFFFFFFF;
return $a | $b;
}
/**
* NH Algorithm / 64-bit safe
*
* @param string $k string of length 1024 bytes.
* @param string $m string with length divisible by 32 bytes.
* @return string string of length 8 bytes.
*/
private static function nh64($k, $m, $length)
{
//
// Break M and K into 4-byte chunks
//
$k = unpack('N*', $k);
$m = unpack('N*', $m);
$t = count($m);
//
// Perform NH hash on the chunks, pairing words for multiplication
// which are 4 apart to accommodate vector-parallelism.
//
$i = 1;
$y = 0;
while ($i <= $t) {
$temp = ($m[$i] + $k[$i]) & 0xFFFFFFFF;
$temp2 = ($m[$i + 4] + $k[$i + 4]) & 0xFFFFFFFF;
$y = self::add64($y, self::mul64($temp, $temp2));
$temp = ($m[$i + 1] + $k[$i + 1]) & 0xFFFFFFFF;
$temp2 = ($m[$i + 5] + $k[$i + 5]) & 0xFFFFFFFF;
$y = self::add64($y, self::mul64($temp, $temp2));
$temp = ($m[$i + 2] + $k[$i + 2]) & 0xFFFFFFFF;
$temp2 = ($m[$i + 6] + $k[$i + 6]) & 0xFFFFFFFF;
$y = self::add64($y, self::mul64($temp, $temp2));
$temp = ($m[$i + 3] + $k[$i + 3]) & 0xFFFFFFFF;
$temp2 = ($m[$i + 7] + $k[$i + 7]) & 0xFFFFFFFF;
$y = self::add64($y, self::mul64($temp, $temp2));
$i += 8;
}
return pack('J', self::add64($y, $length));
} }
/** /**
@ -1125,9 +1322,10 @@ class Hash
list($lo, $hi) = $x; list($lo, $hi) = $x;
} }
$mask = -1 ^ (-1 << $shift);
return [ return [
($hi << $shift) | (($lo >> (32 - $shift)) & (1 << $shift) - 1), ($hi << $shift) | (($lo >> (32 - $shift)) & $mask),
($lo << $shift) | (($hi >> (32 - $shift)) & (1 << $shift) - 1) ($lo << $shift) | (($hi >> (32 - $shift)) & $mask)
]; ];
} }
@ -1277,14 +1475,27 @@ class Hash
} }
/** /**
* Rotate 64-bit int * Left rotate 64-bit int
* *
* @param int $x * @param int $x
* @param int $shift * @param int $shift
*/ */
private static function rotateLeft64($x, $shift) private static function rotateLeft64($x, $shift)
{ {
return ($x << $shift) | (($x >> (64 - $shift)) & ((1 << $shift) - 1)); $mask = -1 ^ (-1 << $shift);
return ($x << $shift) | (($x >> (64 - $shift)) & $mask);
}
/**
* Right rotate 64-bit int
*
* @param int $x
* @param int $shift
*/
private static function rotateRight64($x, $shift)
{
$mask = -1 ^ (-1 << (64 - $shift));
return (($x >> $shift) & $mask) | ($x << (64 - $shift));
} }
/** /**
@ -1445,6 +1656,140 @@ class Hash
return $temp; return $temp;
} }
/**
* Pure-PHP implementation of SHA512
*
* @param string $m
* @param array $hash
* @return string
*/
private static function sha512_64($m, $hash)
{
static $k;
if (!isset($k)) {
// Initialize table of round constants
// (first 64 bits of the fractional parts of the cube roots of the first 80 primes 2..409)
$k = [
'428a2f98d728ae22', '7137449123ef65cd', 'b5c0fbcfec4d3b2f', 'e9b5dba58189dbbc',
'3956c25bf348b538', '59f111f1b605d019', '923f82a4af194f9b', 'ab1c5ed5da6d8118',
'd807aa98a3030242', '12835b0145706fbe', '243185be4ee4b28c', '550c7dc3d5ffb4e2',
'72be5d74f27b896f', '80deb1fe3b1696b1', '9bdc06a725c71235', 'c19bf174cf692694',
'e49b69c19ef14ad2', 'efbe4786384f25e3', '0fc19dc68b8cd5b5', '240ca1cc77ac9c65',
'2de92c6f592b0275', '4a7484aa6ea6e483', '5cb0a9dcbd41fbd4', '76f988da831153b5',
'983e5152ee66dfab', 'a831c66d2db43210', 'b00327c898fb213f', 'bf597fc7beef0ee4',
'c6e00bf33da88fc2', 'd5a79147930aa725', '06ca6351e003826f', '142929670a0e6e70',
'27b70a8546d22ffc', '2e1b21385c26c926', '4d2c6dfc5ac42aed', '53380d139d95b3df',
'650a73548baf63de', '766a0abb3c77b2a8', '81c2c92e47edaee6', '92722c851482353b',
'a2bfe8a14cf10364', 'a81a664bbc423001', 'c24b8b70d0f89791', 'c76c51a30654be30',
'd192e819d6ef5218', 'd69906245565a910', 'f40e35855771202a', '106aa07032bbd1b8',
'19a4c116b8d2d0c8', '1e376c085141ab53', '2748774cdf8eeb99', '34b0bcb5e19b48a8',
'391c0cb3c5c95a63', '4ed8aa4ae3418acb', '5b9cca4f7763e373', '682e6ff3d6b2b8a3',
'748f82ee5defb2fc', '78a5636f43172f60', '84c87814a1f0ab72', '8cc702081a6439ec',
'90befffa23631e28', 'a4506cebde82bde9', 'bef9a3f7b2c67915', 'c67178f2e372532b',
'ca273eceea26619c', 'd186b8c721c0c207', 'eada7dd6cde0eb1e', 'f57d4f7fee6ed178',
'06f067aa72176fba', '0a637dc5a2c898a6', '113f9804bef90dae', '1b710b35131c471b',
'28db77f523047d84', '32caab7b40c72493', '3c9ebe0a15c9bebc', '431d67c49c100d4c',
'4cc5d4becb3e42b6', '597f299cfc657e2a', '5fcb6fab3ad6faec', '6c44198c4a475817'
];
for ($i = 0; $i < 80; $i++) {
list(, $k[$i]) = unpack('J', pack('H*', $k[$i]));
}
}
// Pre-processing
$length = strlen($m);
// to round to nearest 112 mod 128, we'll add 128 - (length + (128 - 112)) % 128
$m .= str_repeat(chr(0), 128 - (($length + 16) & 0x7F));
$m[$length] = chr(0x80);
// we don't support hashing strings 512MB long
$m .= pack('N4', 0, 0, 0, $length << 3);
// Process the message in successive 1024-bit chunks
$chunks = str_split($m, 128);
foreach ($chunks as $chunk) {
$w = [];
for ($i = 0; $i < 16; $i++) {
list(, $w[]) = unpack('J', Strings::shift($chunk, 8));
}
// Extend the sixteen 32-bit words into eighty 32-bit words
for ($i = 16; $i < 80; $i++) {
$temp = [
self::rotateRight64($w[$i - 15], 1),
self::rotateRight64($w[$i - 15], 8),
($w[$i - 15] >> 7) & 0x01FFFFFFFFFFFFFF,
];
$s0 = $temp[0] ^ $temp[1] ^ $temp[2];
$temp = [
self::rotateRight64($w[$i - 2], 19),
self::rotateRight64($w[$i - 2], 61),
($w[$i - 2] >> 6) & 0x03FFFFFFFFFFFFFF,
];
$s1 = $temp[0] ^ $temp[1] ^ $temp[2];
$w[$i] = $w[$i - 16];
$w[$i] = self::add64($w[$i], $s0);
$w[$i] = self::add64($w[$i], $w[$i - 7]);
$w[$i] = self::add64($w[$i], $s1);
}
// Initialize hash value for this chunk
list($a, $b, $c, $d, $e, $f, $g, $h) = $hash;
// Main loop
for ($i = 0; $i < 80; $i++) {
$temp = [
self::rotateRight64($a, 28),
self::rotateRight64($a, 34),
self::rotateRight64($a, 39),
];
$s0 = $temp[0] ^ $temp[1] ^ $temp[2];
$temp = [$a & $b, $a & $c, $b & $c];
$maj = $temp[0] ^ $temp[1] ^ $temp[2];
$t2 = self::add64($s0, $maj);
$temp = [
self::rotateRight64($e, 14),
self::rotateRight64($e, 18),
self::rotateRight64($e, 41),
];
$s1 = $temp[0] ^ $temp[1] ^ $temp[2];
$ch = ($e & $f) ^ ($g & ~$e);
$t1 = self::add64($h, $s1);
$t1 = self::add64($t1, $ch);
$t1 = self::add64($t1, $k[$i]);
$t1 = self::add64($t1, $w[$i]);
$h = $g;
$g = $f;
$f = $e;
$e = self::add64($d, $t1);
$d = $c;
$c = $b;
$b = $a;
$a = self::add64($t1, $t2);
}
// Add this chunk's hash to result so far
$hash = [
self::add64($hash[0], $a),
self::add64($hash[1], $b),
self::add64($hash[2], $c),
self::add64($hash[3], $d),
self::add64($hash[4], $e),
self::add64($hash[5], $f),
self::add64($hash[6], $g),
self::add64($hash[7], $h),
];
}
// Produce the final hash value (big-endian)
// (\phpseclib3\Crypt\Hash::hash() trims the output for hashes but not for HMACs. as such, we trim the output here)
return pack('J*', ...$hash);
}
/** /**
* __toString() magic method * __toString() magic method
*/ */

View file

@ -27,9 +27,9 @@ abstract class TBSCertList
'children' => [ 'children' => [
'version' => [ 'version' => [
'type' => ASN1::TYPE_INTEGER, 'type' => ASN1::TYPE_INTEGER,
'mapping' => ['v1', 'v2', 'v3'], 'mapping' => ['v1', 'v2'],
'optional' => true, 'optional' => true,
'default' => 'v2' 'default' => 'v1'
], ],
'signature' => AlgorithmIdentifier::MAP, 'signature' => AlgorithmIdentifier::MAP,
'issuer' => Name::MAP, 'issuer' => Name::MAP,

View file

@ -2904,11 +2904,11 @@ class X509
$version = isset($tbsCertList['version']) ? $tbsCertList['version'] : 0; $version = isset($tbsCertList['version']) ? $tbsCertList['version'] : 0;
if (!$version) { if (!$version) {
if (!empty($tbsCertList['crlExtensions'])) { if (!empty($tbsCertList['crlExtensions'])) {
$version = 1; // v2. $version = 'v2'; // v2.
} elseif (!empty($tbsCertList['revokedCertificates'])) { } elseif (!empty($tbsCertList['revokedCertificates'])) {
foreach ($tbsCertList['revokedCertificates'] as $cert) { foreach ($tbsCertList['revokedCertificates'] as $cert) {
if (!empty($cert['crlEntryExtensions'])) { if (!empty($cert['crlEntryExtensions'])) {
$version = 1; // v2. $version = 'v2'; // v2.
} }
} }
} }

Some files were not shown because too many files have changed in this diff Show more