Updated to new HTTP router and replaced database statement cache.

This commit is contained in:
flash 2024-03-29 23:45:32 +00:00
parent 57c4677d52
commit ca523b9ef5
8 changed files with 202 additions and 255 deletions

266
composer.lock generated
View file

@ -8,16 +8,16 @@
"packages": [
{
"name": "chillerlan/php-qrcode",
"version": "4.4.0",
"version": "4.4.1",
"source": {
"type": "git",
"url": "https://github.com/chillerlan/php-qrcode.git",
"reference": "52889cd7ab1b78e6a345edafe24aa74bc5becc08"
"reference": "f5e243f3b61a60934780579430a951460f40888d"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/chillerlan/php-qrcode/zipball/52889cd7ab1b78e6a345edafe24aa74bc5becc08",
"reference": "52889cd7ab1b78e6a345edafe24aa74bc5becc08",
"url": "https://api.github.com/repos/chillerlan/php-qrcode/zipball/f5e243f3b61a60934780579430a951460f40888d",
"reference": "f5e243f3b61a60934780579430a951460f40888d",
"shasum": ""
},
"require": {
@ -27,10 +27,10 @@
},
"require-dev": {
"phan/phan": "^5.4",
"phpmd/phpmd": "^2.13",
"phpmd/phpmd": "^2.15",
"phpunit/phpunit": "^9.6",
"setasign/fpdf": "^1.8.2",
"squizlabs/php_codesniffer": "^3.7"
"squizlabs/php_codesniffer": "^3.8"
},
"suggest": {
"chillerlan/php-authenticator": "Yet another Google authenticator! Also creates URIs for mobile apps.",
@ -73,7 +73,7 @@
],
"support": {
"issues": "https://github.com/chillerlan/php-qrcode/issues",
"source": "https://github.com/chillerlan/php-qrcode/tree/4.4.0"
"source": "https://github.com/chillerlan/php-qrcode/tree/4.4.1"
},
"funding": [
{
@ -85,20 +85,20 @@
"type": "ko_fi"
}
],
"time": "2023-11-23T23:53:20+00:00"
"time": "2024-01-06T16:56:58+00:00"
},
{
"name": "chillerlan/php-settings-container",
"version": "3.1.0",
"version": "3.2.0",
"source": {
"type": "git",
"url": "https://github.com/chillerlan/php-settings-container.git",
"reference": "4d02944424fa1f48abca96353257c93cbac856c1"
"reference": "8f93648fac8e6bacac8e00a8d325eba4950295e6"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/chillerlan/php-settings-container/zipball/4d02944424fa1f48abca96353257c93cbac856c1",
"reference": "4d02944424fa1f48abca96353257c93cbac856c1",
"url": "https://api.github.com/repos/chillerlan/php-settings-container/zipball/8f93648fac8e6bacac8e00a8d325eba4950295e6",
"reference": "8f93648fac8e6bacac8e00a8d325eba4950295e6",
"shasum": ""
},
"require": {
@ -107,9 +107,9 @@
},
"require-dev": {
"phan/phan": "^5.4",
"phpmd/phpmd": "^2.13",
"phpunit/phpunit": "^10.2",
"squizlabs/php_codesniffer": "^3.7"
"phpmd/phpmd": "^2.15",
"phpunit/phpunit": "^10.5",
"squizlabs/php_codesniffer": "^3.9"
},
"type": "library",
"autoload": {
@ -150,31 +150,31 @@
"type": "ko_fi"
}
],
"time": "2023-07-17T20:46:37+00:00"
"time": "2024-03-02T20:07:15+00:00"
},
{
"name": "doctrine/lexer",
"version": "3.0.0",
"version": "3.0.1",
"source": {
"type": "git",
"url": "https://github.com/doctrine/lexer.git",
"reference": "84a527db05647743d50373e0ec53a152f2cde568"
"reference": "31ad66abc0fc9e1a1f2d9bc6a42668d2fbbcd6dd"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/doctrine/lexer/zipball/84a527db05647743d50373e0ec53a152f2cde568",
"reference": "84a527db05647743d50373e0ec53a152f2cde568",
"url": "https://api.github.com/repos/doctrine/lexer/zipball/31ad66abc0fc9e1a1f2d9bc6a42668d2fbbcd6dd",
"reference": "31ad66abc0fc9e1a1f2d9bc6a42668d2fbbcd6dd",
"shasum": ""
},
"require": {
"php": "^8.1"
},
"require-dev": {
"doctrine/coding-standard": "^10",
"phpstan/phpstan": "^1.9",
"phpunit/phpunit": "^9.5",
"doctrine/coding-standard": "^12",
"phpstan/phpstan": "^1.10",
"phpunit/phpunit": "^10.5",
"psalm/plugin-phpunit": "^0.18.3",
"vimeo/psalm": "^5.0"
"vimeo/psalm": "^5.21"
},
"type": "library",
"autoload": {
@ -211,7 +211,7 @@
],
"support": {
"issues": "https://github.com/doctrine/lexer/issues",
"source": "https://github.com/doctrine/lexer/tree/3.0.0"
"source": "https://github.com/doctrine/lexer/tree/3.0.1"
},
"funding": [
{
@ -227,7 +227,7 @@
"type": "tidelift"
}
],
"time": "2022-12-15T16:57:16+00:00"
"time": "2024-02-05T11:56:58+00:00"
},
{
"name": "egulias/email-validator",
@ -302,7 +302,7 @@
"source": {
"type": "git",
"url": "https://patchii.net/flash/index.git",
"reference": "e31781c69f0b13fe251771c8e7e529222630a44f"
"reference": "9d5b050b8928435416a7efbebe2a19ae8e626224"
},
"require": {
"ext-mbstring": "*",
@ -340,7 +340,7 @@
],
"description": "Composer package for the common library for my projects.",
"homepage": "https://railgun.sh/index",
"time": "2023-11-20T19:01:19+00:00"
"time": "2024-03-28T23:27:04+00:00"
},
{
"name": "flashwave/sasae",
@ -348,7 +348,7 @@
"source": {
"type": "git",
"url": "https://patchii.net/flash/sasae.git",
"reference": "b56dd222acb8f138729e6258d4a90bbb8401ff52"
"reference": "c8a9f2974e6591215b3f898dd5525de1e8367f66"
},
"require": {
"flashwave/index": "dev-master",
@ -381,7 +381,7 @@
],
"description": "A wrapper for Twig with added common functionality.",
"homepage": "https://railgun.sh/sasae",
"time": "2023-11-20T19:09:35+00:00"
"time": "2024-01-04T02:13:42+00:00"
},
{
"name": "flashwave/syokuhou",
@ -389,7 +389,7 @@
"source": {
"type": "git",
"url": "https://patchii.net/flash/syokuhou.git",
"reference": "fdf3c38cc216bf7024af331cbe1758532355c22f"
"reference": "c1fe9371ada20fcea51c225cc53b9ceae4642bc4"
},
"require": {
"flashwave/index": "dev-master",
@ -420,7 +420,7 @@
],
"description": "Configuration library for PHP.",
"homepage": "https://railgun.sh/syokuhou",
"time": "2023-11-20T19:10:04+00:00"
"time": "2024-01-04T02:12:49+00:00"
},
{
"name": "guzzlehttp/psr7",
@ -540,16 +540,16 @@
},
{
"name": "jean85/pretty-package-versions",
"version": "2.0.5",
"version": "2.0.6",
"source": {
"type": "git",
"url": "https://github.com/Jean85/pretty-package-versions.git",
"reference": "ae547e455a3d8babd07b96966b17d7fd21d9c6af"
"reference": "f9fdd29ad8e6d024f52678b570e5593759b550b4"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/Jean85/pretty-package-versions/zipball/ae547e455a3d8babd07b96966b17d7fd21d9c6af",
"reference": "ae547e455a3d8babd07b96966b17d7fd21d9c6af",
"url": "https://api.github.com/repos/Jean85/pretty-package-versions/zipball/f9fdd29ad8e6d024f52678b570e5593759b550b4",
"reference": "f9fdd29ad8e6d024f52678b570e5593759b550b4",
"shasum": ""
},
"require": {
@ -557,9 +557,9 @@
"php": "^7.1|^8.0"
},
"require-dev": {
"friendsofphp/php-cs-fixer": "^2.17",
"friendsofphp/php-cs-fixer": "^3.2",
"jean85/composer-provided-replaced-stub-package": "^1.0",
"phpstan/phpstan": "^0.12.66",
"phpstan/phpstan": "^1.4",
"phpunit/phpunit": "^7.5|^8.5|^9.4",
"vimeo/psalm": "^4.3"
},
@ -593,22 +593,22 @@
],
"support": {
"issues": "https://github.com/Jean85/pretty-package-versions/issues",
"source": "https://github.com/Jean85/pretty-package-versions/tree/2.0.5"
"source": "https://github.com/Jean85/pretty-package-versions/tree/2.0.6"
},
"time": "2021-10-08T21:21:46+00:00"
"time": "2024-03-08T09:58:59+00:00"
},
{
"name": "matomo/device-detector",
"version": "6.2.0",
"version": "6.3.0",
"source": {
"type": "git",
"url": "https://github.com/matomo-org/device-detector.git",
"reference": "3577abbfea71eaf88d4cd432274428c39601754f"
"reference": "35efad75b31f2596701834d19f097497909572a4"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/matomo-org/device-detector/zipball/3577abbfea71eaf88d4cd432274428c39601754f",
"reference": "3577abbfea71eaf88d4cd432274428c39601754f",
"url": "https://api.github.com/repos/matomo-org/device-detector/zipball/35efad75b31f2596701834d19f097497909572a4",
"reference": "35efad75b31f2596701834d19f097497909572a4",
"shasum": ""
},
"require": {
@ -620,8 +620,8 @@
},
"require-dev": {
"matthiasmullie/scrapbook": "^1.4.7",
"mayflower/mo4-coding-standard": "^v8.0.0",
"phpstan/phpstan": "^0.12.52",
"mayflower/mo4-coding-standard": "^v9.0.0",
"phpstan/phpstan": "^1.10.44",
"phpunit/phpunit": "^8.5.8",
"psr/cache": "^1.0.1",
"psr/simple-cache": "^1.0.1",
@ -664,14 +664,14 @@
"source": "https://github.com/matomo-org/matomo",
"wiki": "https://dev.matomo.org/"
},
"time": "2023-11-15T09:44:42+00:00"
"time": "2024-02-16T16:26:57+00:00"
},
{
"name": "mustangostang/spyc",
"version": "0.6.3",
"source": {
"type": "git",
"url": "git@github.com:mustangostang/spyc.git",
"url": "https://github.com/mustangostang/spyc.git",
"reference": "4627c838b16550b666d15aeae1e5289dd5b77da0"
},
"dist": {
@ -714,6 +714,10 @@
"yaml",
"yml"
],
"support": {
"issues": "https://github.com/mustangostang/spyc/issues",
"source": "https://github.com/mustangostang/spyc/tree/0.6.3"
},
"time": "2019-09-10T13:16:29+00:00"
},
{
@ -1078,16 +1082,16 @@
},
{
"name": "sentry/sentry",
"version": "4.1.0",
"version": "4.6.1",
"source": {
"type": "git",
"url": "https://github.com/getsentry/sentry-php.git",
"reference": "89666f297891ff937fceb2f3d1fb967a6848cf37"
"reference": "5a94184175e5830b589bf923da8c9c3af2c0f409"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/getsentry/sentry-php/zipball/89666f297891ff937fceb2f3d1fb967a6848cf37",
"reference": "89666f297891ff937fceb2f3d1fb967a6848cf37",
"url": "https://api.github.com/repos/getsentry/sentry-php/zipball/5a94184175e5830b589bf923da8c9c3af2c0f409",
"reference": "5a94184175e5830b589bf923da8c9c3af2c0f409",
"shasum": ""
},
"require": {
@ -1111,7 +1115,7 @@
"phpbench/phpbench": "^1.0",
"phpstan/phpstan": "^1.3",
"phpunit/phpunit": "^8.5.14|^9.4",
"symfony/phpunit-bridge": "^5.2|^6.0",
"symfony/phpunit-bridge": "^5.2|^6.0|^7.0",
"vimeo/psalm": "^4.17"
},
"suggest": {
@ -1151,7 +1155,7 @@
],
"support": {
"issues": "https://github.com/getsentry/sentry-php/issues",
"source": "https://github.com/getsentry/sentry-php/tree/4.1.0"
"source": "https://github.com/getsentry/sentry-php/tree/4.6.1"
},
"funding": [
{
@ -1163,7 +1167,7 @@
"type": "custom"
}
],
"time": "2023-12-04T12:41:21+00:00"
"time": "2024-03-08T08:18:09+00:00"
},
{
"name": "symfony/deprecation-contracts",
@ -1234,16 +1238,16 @@
},
{
"name": "symfony/event-dispatcher",
"version": "v7.0.0",
"version": "v7.0.3",
"source": {
"type": "git",
"url": "https://github.com/symfony/event-dispatcher.git",
"reference": "c459b40ffe67c49af6fd392aac374c9edf8a027e"
"reference": "834c28d533dd0636f910909d01b9ff45cc094b5e"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/c459b40ffe67c49af6fd392aac374c9edf8a027e",
"reference": "c459b40ffe67c49af6fd392aac374c9edf8a027e",
"url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/834c28d533dd0636f910909d01b9ff45cc094b5e",
"reference": "834c28d533dd0636f910909d01b9ff45cc094b5e",
"shasum": ""
},
"require": {
@ -1294,7 +1298,7 @@
"description": "Provides tools that allow your application components to communicate with each other by dispatching events and listening to them",
"homepage": "https://symfony.com",
"support": {
"source": "https://github.com/symfony/event-dispatcher/tree/v7.0.0"
"source": "https://github.com/symfony/event-dispatcher/tree/v7.0.3"
},
"funding": [
{
@ -1310,7 +1314,7 @@
"type": "tidelift"
}
],
"time": "2023-07-27T16:29:09+00:00"
"time": "2024-01-23T15:02:46+00:00"
},
{
"name": "symfony/event-dispatcher-contracts",
@ -1390,16 +1394,16 @@
},
{
"name": "symfony/mailer",
"version": "v6.4.0",
"version": "v6.4.4",
"source": {
"type": "git",
"url": "https://github.com/symfony/mailer.git",
"reference": "ca8dcf8892cdc5b4358ecf2528429bb5e706f7ba"
"reference": "791c5d31a8204cf3db0c66faab70282307f4376b"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/mailer/zipball/ca8dcf8892cdc5b4358ecf2528429bb5e706f7ba",
"reference": "ca8dcf8892cdc5b4358ecf2528429bb5e706f7ba",
"url": "https://api.github.com/repos/symfony/mailer/zipball/791c5d31a8204cf3db0c66faab70282307f4376b",
"reference": "791c5d31a8204cf3db0c66faab70282307f4376b",
"shasum": ""
},
"require": {
@ -1450,7 +1454,7 @@
"description": "Helps sending emails",
"homepage": "https://symfony.com",
"support": {
"source": "https://github.com/symfony/mailer/tree/v6.4.0"
"source": "https://github.com/symfony/mailer/tree/v6.4.4"
},
"funding": [
{
@ -1466,20 +1470,20 @@
"type": "tidelift"
}
],
"time": "2023-11-12T18:02:22+00:00"
"time": "2024-02-03T21:33:47+00:00"
},
{
"name": "symfony/mime",
"version": "v7.0.0",
"version": "v7.0.3",
"source": {
"type": "git",
"url": "https://github.com/symfony/mime.git",
"reference": "0a2fff95c1a10df97f571d67e76c7ae0f0d4f535"
"reference": "c1ffe24ba6fdc3e3f0f3fcb93519103b326a3716"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/mime/zipball/0a2fff95c1a10df97f571d67e76c7ae0f0d4f535",
"reference": "0a2fff95c1a10df97f571d67e76c7ae0f0d4f535",
"url": "https://api.github.com/repos/symfony/mime/zipball/c1ffe24ba6fdc3e3f0f3fcb93519103b326a3716",
"reference": "c1ffe24ba6fdc3e3f0f3fcb93519103b326a3716",
"shasum": ""
},
"require": {
@ -1533,7 +1537,7 @@
"mime-type"
],
"support": {
"source": "https://github.com/symfony/mime/tree/v7.0.0"
"source": "https://github.com/symfony/mime/tree/v7.0.3"
},
"funding": [
{
@ -1549,7 +1553,7 @@
"type": "tidelift"
}
],
"time": "2023-10-19T14:20:43+00:00"
"time": "2024-01-30T08:34:29+00:00"
},
{
"name": "symfony/options-resolver",
@ -1620,16 +1624,16 @@
},
{
"name": "symfony/polyfill-ctype",
"version": "v1.28.0",
"version": "v1.29.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/polyfill-ctype.git",
"reference": "ea208ce43cbb04af6867b4fdddb1bdbf84cc28cb"
"reference": "ef4d7e442ca910c4764bce785146269b30cb5fc4"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/ea208ce43cbb04af6867b4fdddb1bdbf84cc28cb",
"reference": "ea208ce43cbb04af6867b4fdddb1bdbf84cc28cb",
"url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/ef4d7e442ca910c4764bce785146269b30cb5fc4",
"reference": "ef4d7e442ca910c4764bce785146269b30cb5fc4",
"shasum": ""
},
"require": {
@ -1643,9 +1647,6 @@
},
"type": "library",
"extra": {
"branch-alias": {
"dev-main": "1.28-dev"
},
"thanks": {
"name": "symfony/polyfill",
"url": "https://github.com/symfony/polyfill"
@ -1682,7 +1683,7 @@
"portable"
],
"support": {
"source": "https://github.com/symfony/polyfill-ctype/tree/v1.28.0"
"source": "https://github.com/symfony/polyfill-ctype/tree/v1.29.0"
},
"funding": [
{
@ -1698,20 +1699,20 @@
"type": "tidelift"
}
],
"time": "2023-01-26T09:26:14+00:00"
"time": "2024-01-29T20:11:03+00:00"
},
{
"name": "symfony/polyfill-intl-idn",
"version": "v1.28.0",
"version": "v1.29.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/polyfill-intl-idn.git",
"reference": "ecaafce9f77234a6a449d29e49267ba10499116d"
"reference": "a287ed7475f85bf6f61890146edbc932c0fff919"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/polyfill-intl-idn/zipball/ecaafce9f77234a6a449d29e49267ba10499116d",
"reference": "ecaafce9f77234a6a449d29e49267ba10499116d",
"url": "https://api.github.com/repos/symfony/polyfill-intl-idn/zipball/a287ed7475f85bf6f61890146edbc932c0fff919",
"reference": "a287ed7475f85bf6f61890146edbc932c0fff919",
"shasum": ""
},
"require": {
@ -1724,9 +1725,6 @@
},
"type": "library",
"extra": {
"branch-alias": {
"dev-main": "1.28-dev"
},
"thanks": {
"name": "symfony/polyfill",
"url": "https://github.com/symfony/polyfill"
@ -1769,7 +1767,7 @@
"shim"
],
"support": {
"source": "https://github.com/symfony/polyfill-intl-idn/tree/v1.28.0"
"source": "https://github.com/symfony/polyfill-intl-idn/tree/v1.29.0"
},
"funding": [
{
@ -1785,20 +1783,20 @@
"type": "tidelift"
}
],
"time": "2023-01-26T09:30:37+00:00"
"time": "2024-01-29T20:11:03+00:00"
},
{
"name": "symfony/polyfill-intl-normalizer",
"version": "v1.28.0",
"version": "v1.29.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/polyfill-intl-normalizer.git",
"reference": "8c4ad05dd0120b6a53c1ca374dca2ad0a1c4ed92"
"reference": "bc45c394692b948b4d383a08d7753968bed9a83d"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/polyfill-intl-normalizer/zipball/8c4ad05dd0120b6a53c1ca374dca2ad0a1c4ed92",
"reference": "8c4ad05dd0120b6a53c1ca374dca2ad0a1c4ed92",
"url": "https://api.github.com/repos/symfony/polyfill-intl-normalizer/zipball/bc45c394692b948b4d383a08d7753968bed9a83d",
"reference": "bc45c394692b948b4d383a08d7753968bed9a83d",
"shasum": ""
},
"require": {
@ -1809,9 +1807,6 @@
},
"type": "library",
"extra": {
"branch-alias": {
"dev-main": "1.28-dev"
},
"thanks": {
"name": "symfony/polyfill",
"url": "https://github.com/symfony/polyfill"
@ -1853,7 +1848,7 @@
"shim"
],
"support": {
"source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.28.0"
"source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.29.0"
},
"funding": [
{
@ -1869,20 +1864,20 @@
"type": "tidelift"
}
],
"time": "2023-01-26T09:26:14+00:00"
"time": "2024-01-29T20:11:03+00:00"
},
{
"name": "symfony/polyfill-mbstring",
"version": "v1.28.0",
"version": "v1.29.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/polyfill-mbstring.git",
"reference": "42292d99c55abe617799667f454222c54c60e229"
"reference": "9773676c8a1bb1f8d4340a62efe641cf76eda7ec"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/42292d99c55abe617799667f454222c54c60e229",
"reference": "42292d99c55abe617799667f454222c54c60e229",
"url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/9773676c8a1bb1f8d4340a62efe641cf76eda7ec",
"reference": "9773676c8a1bb1f8d4340a62efe641cf76eda7ec",
"shasum": ""
},
"require": {
@ -1896,9 +1891,6 @@
},
"type": "library",
"extra": {
"branch-alias": {
"dev-main": "1.28-dev"
},
"thanks": {
"name": "symfony/polyfill",
"url": "https://github.com/symfony/polyfill"
@ -1936,7 +1928,7 @@
"shim"
],
"support": {
"source": "https://github.com/symfony/polyfill-mbstring/tree/v1.28.0"
"source": "https://github.com/symfony/polyfill-mbstring/tree/v1.29.0"
},
"funding": [
{
@ -1952,20 +1944,20 @@
"type": "tidelift"
}
],
"time": "2023-07-28T09:04:16+00:00"
"time": "2024-01-29T20:11:03+00:00"
},
{
"name": "symfony/polyfill-php72",
"version": "v1.28.0",
"version": "v1.29.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/polyfill-php72.git",
"reference": "70f4aebd92afca2f865444d30a4d2151c13c3179"
"reference": "861391a8da9a04cbad2d232ddd9e4893220d6e25"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/polyfill-php72/zipball/70f4aebd92afca2f865444d30a4d2151c13c3179",
"reference": "70f4aebd92afca2f865444d30a4d2151c13c3179",
"url": "https://api.github.com/repos/symfony/polyfill-php72/zipball/861391a8da9a04cbad2d232ddd9e4893220d6e25",
"reference": "861391a8da9a04cbad2d232ddd9e4893220d6e25",
"shasum": ""
},
"require": {
@ -1973,9 +1965,6 @@
},
"type": "library",
"extra": {
"branch-alias": {
"dev-main": "1.28-dev"
},
"thanks": {
"name": "symfony/polyfill",
"url": "https://github.com/symfony/polyfill"
@ -2012,7 +2001,7 @@
"shim"
],
"support": {
"source": "https://github.com/symfony/polyfill-php72/tree/v1.28.0"
"source": "https://github.com/symfony/polyfill-php72/tree/v1.29.0"
},
"funding": [
{
@ -2028,20 +2017,20 @@
"type": "tidelift"
}
],
"time": "2023-01-26T09:26:14+00:00"
"time": "2024-01-29T20:11:03+00:00"
},
{
"name": "symfony/polyfill-php80",
"version": "v1.28.0",
"version": "v1.29.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/polyfill-php80.git",
"reference": "6caa57379c4aec19c0a12a38b59b26487dcfe4b5"
"reference": "87b68208d5c1188808dd7839ee1e6c8ec3b02f1b"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/polyfill-php80/zipball/6caa57379c4aec19c0a12a38b59b26487dcfe4b5",
"reference": "6caa57379c4aec19c0a12a38b59b26487dcfe4b5",
"url": "https://api.github.com/repos/symfony/polyfill-php80/zipball/87b68208d5c1188808dd7839ee1e6c8ec3b02f1b",
"reference": "87b68208d5c1188808dd7839ee1e6c8ec3b02f1b",
"shasum": ""
},
"require": {
@ -2049,9 +2038,6 @@
},
"type": "library",
"extra": {
"branch-alias": {
"dev-main": "1.28-dev"
},
"thanks": {
"name": "symfony/polyfill",
"url": "https://github.com/symfony/polyfill"
@ -2095,7 +2081,7 @@
"shim"
],
"support": {
"source": "https://github.com/symfony/polyfill-php80/tree/v1.28.0"
"source": "https://github.com/symfony/polyfill-php80/tree/v1.29.0"
},
"funding": [
{
@ -2111,25 +2097,25 @@
"type": "tidelift"
}
],
"time": "2023-01-26T09:26:14+00:00"
"time": "2024-01-29T20:11:03+00:00"
},
{
"name": "symfony/service-contracts",
"version": "v3.4.0",
"version": "v3.4.1",
"source": {
"type": "git",
"url": "https://github.com/symfony/service-contracts.git",
"reference": "b3313c2dbffaf71c8de2934e2ea56ed2291a3838"
"reference": "fe07cbc8d837f60caf7018068e350cc5163681a0"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/service-contracts/zipball/b3313c2dbffaf71c8de2934e2ea56ed2291a3838",
"reference": "b3313c2dbffaf71c8de2934e2ea56ed2291a3838",
"url": "https://api.github.com/repos/symfony/service-contracts/zipball/fe07cbc8d837f60caf7018068e350cc5163681a0",
"reference": "fe07cbc8d837f60caf7018068e350cc5163681a0",
"shasum": ""
},
"require": {
"php": ">=8.1",
"psr/container": "^2.0"
"psr/container": "^1.1|^2.0"
},
"conflict": {
"ext-psr": "<1.1|>=2"
@ -2177,7 +2163,7 @@
"standards"
],
"support": {
"source": "https://github.com/symfony/service-contracts/tree/v3.4.0"
"source": "https://github.com/symfony/service-contracts/tree/v3.4.1"
},
"funding": [
{
@ -2193,7 +2179,7 @@
"type": "tidelift"
}
],
"time": "2023-07-30T20:28:31+00:00"
"time": "2023-12-26T14:02:43+00:00"
},
{
"name": "twig/html-extra",
@ -2335,16 +2321,16 @@
"packages-dev": [
{
"name": "phpstan/phpstan",
"version": "1.10.50",
"version": "1.10.66",
"source": {
"type": "git",
"url": "https://github.com/phpstan/phpstan.git",
"reference": "06a98513ac72c03e8366b5a0cb00750b487032e4"
"reference": "94779c987e4ebd620025d9e5fdd23323903950bd"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/phpstan/phpstan/zipball/06a98513ac72c03e8366b5a0cb00750b487032e4",
"reference": "06a98513ac72c03e8366b5a0cb00750b487032e4",
"url": "https://api.github.com/repos/phpstan/phpstan/zipball/94779c987e4ebd620025d9e5fdd23323903950bd",
"reference": "94779c987e4ebd620025d9e5fdd23323903950bd",
"shasum": ""
},
"require": {
@ -2393,7 +2379,7 @@
"type": "tidelift"
}
],
"time": "2023-12-13T10:59:42+00:00"
"time": "2024-03-28T16:17:31+00:00"
}
],
"aliases": [],
@ -2407,5 +2393,5 @@
"prefer-lowest": false,
"platform": [],
"platform-dev": [],
"plugin-api-version": "2.3.0"
"plugin-api-version": "2.6.0"
}

View file

@ -2,9 +2,7 @@
namespace Hanyuu\Auth;
use Index\XString;
use Index\Data\IDbConnection;
use Index\Data\IDbResult;
use Hanyuu\StatementCache;
use Index\Data\{DbStatementCache,IDbConnection,IDbResult};
use Hanyuu\Users\UserInfo;
class Auth {
@ -16,12 +14,12 @@ class Auth {
'UNIX_TIMESTAMP(auth_login_started)', 'UNIX_TIMESTAMP(auth_login_valid)', 'UNIX_TIMESTAMP(auth_login_completed)',
];
private StatementCache $stmts;
private DbStatementCache $cache;
public function __construct(
private IDbConnection $conn
) {
$this->stmts = new StatementCache($conn);
$this->cache = new DbStatementCache($conn);
}
@ -33,11 +31,7 @@ class Auth {
): string {
$loginId = XString::random(48);
$stmt = $this->stmts->getStatement('create login', function() {
return 'INSERT INTO ' . self::LOGINS_TABLE
. ' (auth_login_id, user_id, auth_login_ip, auth_login_country, auth_login_factors_required)'
. ' VALUES (?, ?, INET6_ATON(?), ?, ?)';
});
$stmt = $this->cache->get('INSERT INTO ' . self::LOGINS_TABLE . ' (auth_login_id, user_id, auth_login_ip, auth_login_country, auth_login_factors_required) VALUES (?, ?, INET6_ATON(?), ?, ?)');
$stmt->addParameter(1, $loginId);
$stmt->addParameter(2, $userInfo->getId());
@ -50,7 +44,7 @@ class Auth {
}
public function destroyLoginSession(AuthLoginInfo $loginInfo): void {
$stmt = $this->stmts->getStatement('destroy login', fn() => ('DELETE FROM ' . self::LOGINS_TABLE . ' WHERE auth_login_id = ?'));
$stmt = $this->cache->get('DELETE FROM ' . self::LOGINS_TABLE . ' WHERE auth_login_id = ?');
$stmt->addParameter(1, $loginInfo->getId());
$stmt->execute();
}
@ -63,7 +57,7 @@ class Auth {
}
public function getLoginSessionById(string $loginId): ?AuthLoginInfo {
$stmt = $this->stmts->getStatement('get login by id', fn() => ('SELECT ' . implode(',', self::LOGINS_FIELDS) . ' FROM ' . self::LOGINS_TABLE . ' WHERE auth_login_id = ?'));
$stmt = $this->cache->get('SELECT ' . implode(',', self::LOGINS_FIELDS) . ' FROM ' . self::LOGINS_TABLE . ' WHERE auth_login_id = ?');
$stmt->addParameter(1, $loginId);
$stmt->execute();
$result = $stmt->getResult();
@ -75,7 +69,7 @@ class Auth {
}
public function incrementLoginSessionDone(AuthLoginInfo $login): void {
$stmt = $this->stmts->getStatement('increment login done', fn() => ('UPDATE ' . self::LOGINS_TABLE . ' SET auth_login_factors_done = auth_login_factors_done + 1 WHERE auth_login_id = ?'));
$stmt = $this->cache->get('UPDATE ' . self::LOGINS_TABLE . ' SET auth_login_factors_done = auth_login_factors_done + 1 WHERE auth_login_id = ?');
$stmt->addParameter(1, $login->getId());
$stmt->execute();
}

View file

@ -2,16 +2,15 @@
namespace Hanyuu\Auth;
use RuntimeException;
use Index\Routing\IRouter;
use Index\Http\Routing\{HttpGet,HttpMiddleware,HttpPost,RouteHandler};
use Syokuhou\IConfig;
use Hanyuu\HanyuuContext;
use Hanyuu\Auth\Auth;
use Hanyuu\Auth\AuthLoginInfo;
use Hanyuu\Auth\{Auth,AuthLoginInfo};
use Hanyuu\Users\Users;
// VERY IMPORTANT TODO: CSRF AND RATE LIMITING
class AuthRoutes {
class AuthRoutes extends RouteHandler {
private HanyuuContext $context;
private Users $users;
private IConfig $config;
@ -20,7 +19,6 @@ class AuthRoutes {
private ?AuthLoginInfo $loginSession;
public function __construct(
IRouter $router,
HanyuuContext $ctx,
IConfig $config
) {
@ -30,30 +28,6 @@ class AuthRoutes {
$this->context->setUpAuth();
$this->auth = $ctx->getAuth();
$router->use('/login', [$this, 'filterLogin']);
$router->get('/login', [$this, 'getLogin']);
$router->post('/login', [$this, 'postLogin']);
$router->get('/login/tfa', [$this, 'getLoginTFA']);
$router->get('/login/done', [$this, 'getLoginDone']);
$router->get('/login/tfa/totp', [$this, 'getLoginTOTP']);
$router->post('/login/tfa/totp', [$this, 'postLoginTOTP']);
$router->get('/login/tfa/u2f', [$this, 'getLoginU2F']);
$router->post('/login/tfa/u2f', [$this, 'postLoginU2F']);
$router->get('/login/tfa/backup', [$this, 'getLoginBackup']);
$router->post('/login/tfa/backup', [$this, 'postLoginBackup']);
$router->get('/register', [$this, 'getRegister']);
$router->get('/forgot-username', [$this, 'getForgotUserName']);
$router->get('/forgot-password', [$this, 'getForgotPassword']);
$router->get('/recover-password', [$this, 'getRecoverPassword']);
}
private function getLoginCookieName(): string {
@ -83,6 +57,7 @@ class AuthRoutes {
return true;
}
#[HttpMiddleware('/login')]
public function filterLogin($response, $request) {
$loginId = (string)$request->getCookie($this->getLoginCookieName());
$this->loginSession = empty($loginId) ? null : $this->auth->getLoginSessionById($loginId);
@ -94,6 +69,7 @@ class AuthRoutes {
}
}
#[HttpGet('/login')]
public function getLogin($response, $request) {
$this->destroyLoginSession($response);
@ -113,6 +89,7 @@ class AuthRoutes {
]);
}
#[HttpPost('/login')]
public function postLogin($response, $request) {
if(!$request->isFormContent())
return 400;
@ -161,6 +138,7 @@ class AuthRoutes {
$response->redirect($factorsRequired > 1 ? '/login/tfa' : '/login/done');
}
#[HttpGet('/login/tfa')]
public function getLoginTFA($response, $request) {
if(!$this->ensureLoginIncomplete($response))
return;
@ -189,6 +167,7 @@ class AuthRoutes {
]);
}
#[HttpGet('/login/done')]
public function getLoginDone($response, $request) {
if($this->loginSession === null) {
$response->redirect('/login');
@ -205,6 +184,7 @@ class AuthRoutes {
return "you've successfully authenticated but there's no session system yet lol";
}
#[HttpGet('/login/tfa/totp')]
public function getLoginTOTP($response, $request) {
if(!$this->ensureLoginIncomplete($response))
return;
@ -222,6 +202,7 @@ class AuthRoutes {
]);
}
#[HttpPost('/login/tfa/totp')]
public function postLoginTOTP($response, $request) {
if(!$request->isFormContent())
return 400;
@ -246,34 +227,42 @@ class AuthRoutes {
$response->redirect('/login/done');
}
#[HttpGet('/login/tfa/u2f')]
public function getLoginU2F($response, $request) {
return 503;
}
#[HttpPost('/login/tfa/u2f')]
public function postLoginU2F($response, $request) {
return 503;
}
#[HttpGet('/login/tfa/backup')]
public function getLoginBackup($response, $request) {
return 503;
}
#[HttpPost('/login/tfa/backup')]
public function postLoginBackup($response, $request) {
return 503;
}
#[HttpGet('/register')]
public function getRegister($response, $request) {
return 503;
}
#[HttpGet('/forgot-username')]
public function getForgotUserName($response, $request) {
return 503;
}
#[HttpGet('/forgot-password')]
public function getForgotPassword($response, $request) {
return 503;
}
#[HttpGet('/recover-password')]
public function getRecoverPassword($response, $request) {
return 503;
}

View file

@ -3,16 +3,10 @@ namespace Hanyuu;
use Index\Environment;
use Index\Data\IDbConnection;
use Index\Data\Migration\IDbMigrationRepo;
use Index\Data\Migration\DbMigrationManager;
use Index\Data\Migration\FsDbMigrationRepo;
use Index\Http\HttpFx;
use Index\Http\HttpRequest;
use Index\Routing\IRouter;
use Index\Data\Migration\{IDbMigrationRepo,DbMigrationManager,FsDbMigrationRepo};
use Sasae\SasaeEnvironment;
use Syokuhou\IConfig;
use Hanyuu\Auth\Auth;
use Hanyuu\Auth\AuthRoutes;
use Hanyuu\Auth\{Auth,AuthRoutes};
use Hanyuu\Users\Users;
class HanyuuContext {
@ -85,13 +79,12 @@ class HanyuuContext {
public function createRouting(): RoutingContext {
$routingCtx = new RoutingContext($this->getTemplating());
$routingCtx->registerDefaultErrorPages();
$routingCtx->getRouter()->get('/', function($response, $request) {
return 503;
});
new AuthRoutes($routingCtx->getRouter(), $this, $this->config->scopeTo('auth'));
$routingCtx->register(new AuthRoutes($this, $this->config->scopeTo('auth')));
return $routingCtx;
}

View file

@ -1,19 +1,16 @@
<?php
namespace Hanyuu;
use Index\Http\HttpFx;
use Index\Http\HttpRequest;
use Index\Routing\IRouter;
use Index\Routing\IRouteHandler;
use Index\Http\Routing\{HttpRouter,IRouter,IRouteHandler};
use Sasae\SasaeEnvironment;
class RoutingContext {
private HttpFx $router;
private HttpRouter $router;
private SasaeEnvironment $templating;
public function __construct(SasaeEnvironment $templating) {
$this->templating = $templating;
$this->router = new HttpFx;
$this->router = new HttpRouter(errorHandler: new RoutingErrorHandler($templating));
$this->router->use('/', fn($resp) => $resp->setPoweredBy('Hanyuu'));
}
@ -21,19 +18,11 @@ class RoutingContext {
return $this->router;
}
public function registerDefaultErrorPages(): void {
$this->router->addErrorHandler(401, fn($resp) => $resp->setContent($this->templating->render('errors/401')));
$this->router->addErrorHandler(403, fn($resp) => $resp->setContent($this->templating->render('errors/403')));
$this->router->addErrorHandler(404, fn($resp) => $resp->setContent($this->templating->render('errors/404')));
$this->router->addErrorHandler(500, fn($resp) => $resp->setContent(file_get_contents(HAU_DIR_TEMPLATES . '/errors/500.html')));
$this->router->addErrorHandler(503, fn($resp) => $resp->setContent(file_get_contents(HAU_DIR_TEMPLATES . '/errors/503.html')));
}
public function register(IRouteHandler $handler): void {
$this->router->register($handler);
}
public function dispatch(?HttpRequest $request = null): void {
$this->router->dispatch($request);
public function dispatch(): void {
$this->router->dispatch();
}
}

View file

@ -0,0 +1,29 @@
<?php
namespace Hanyuu;
use Index\Http\{HttpResponseBuilder,HttpRequest};
use Index\Http\ErrorHandling\HtmlErrorHandler;
use Sasae\SasaeEnvironment;
class RoutingErrorHandler extends HtmlErrorHandler {
public function __construct(
private SasaeEnvironment $templating
) {}
#[\Override]
public function handle(HttpResponseBuilder $response, HttpRequest $request, int $code, string $message): void {
if($code === 500 || $code === 503) {
$response->setTypeHTML();
$response->setContent(file_get_contents(sprintf('%s/errors/%s.html', HAU_DIR_TEMPLATES, $code)));
return;
}
if($code == 401 || $code === 403 || $code === 400) {
$response->setTypeHTML();
$response->setContent($this->templating->render(sprintf('errors/%s', $code)));
return;
}
parent::handle($response, $request, $code, $message);
}
}

View file

@ -1,27 +0,0 @@
<?php
namespace Hanyuu;
use Index\Data\IDbConnection;
use Index\Data\IDbStatement;
class StatementCache {
private array $statements = [];
public function __construct(
private IDbConnection $conn
) {}
public function getStatement(string $name, callable $query): IDbStatement {
if(array_key_exists($name, $this->statements)) {
$stmt = $this->statements[$name];
$stmt->reset();
} else
$this->statements[$name] = $stmt = $this->conn->prepare($query());
return $stmt;
}
public function clearStatement(string $name): void {
unset($this->statements[$name]);
}
}

View file

@ -2,15 +2,9 @@
namespace Hanyuu\Users;
use RuntimeException;
use Index\Data\IDbConnection;
use Index\Data\IDbStatement;
use Index\Data\IDbResult;
use Hanyuu\StatementCache;
use Hanyuu\Auth\IAuthMethod;
use Hanyuu\Auth\Auth;
use Hanyuu\Users\UserInfo;
use Hanyuu\Users\UserPasswordInfo;
use Hanyuu\Users\UserTOTPInfo;
use Index\Data\{DbStatementCache,IDbConnection,IDbStatement,IDbResult};
use Hanyuu\Auth\{Auth,IAuthMethod};
use Hanyuu\Users\{UserInfo,UserPasswordInfo,UserTOTPInfo};
class Users {
private const USERS_TABLE = 'hau_users';
@ -40,12 +34,12 @@ class Users {
'user_id', 'user_backup_code', 'UNIX_TIMESTAMP(user_backup_created)', 'UNIX_TIMESTAMP(user_backup_used)',
];
private StatementCache $stmts;
private DbStatementCache $cache;
public function __construct(
private IDbConnection $conn
) {
$this->stmts = new StatementCache($conn);
$this->cache = new DbStatementCache($conn);
}
private function fetchUserInfoSingle(IDbResult $result, string $exceptionText): UserInfo {
@ -56,7 +50,7 @@ class Users {
}
public function getUserInfoById(string $userId): UserInfo {
$stmt = $this->stmts->getStatement('get info by id', fn() => ('SELECT ' . implode(',', self::USERS_FIELDS) . ' FROM ' . self::USERS_TABLE . ' WHERE user_id = ?'));
$stmt = $this->cache->get('SELECT ' . implode(',', self::USERS_FIELDS) . ' FROM ' . self::USERS_TABLE . ' WHERE user_id = ?');
$stmt->addParameter(1, $userId);
$stmt->execute();
@ -64,7 +58,7 @@ class Users {
}
public function getUserInfoByName(string $userName): UserInfo {
$stmt = $this->stmts->getStatement('get info by name', fn() => ('SELECT ' . implode(',', self::USERS_FIELDS) . ' FROM ' . self::USERS_TABLE . ' WHERE user_name = ?'));
$stmt = $this->cache->get('SELECT ' . implode(',', self::USERS_FIELDS) . ' FROM ' . self::USERS_TABLE . ' WHERE user_name = ?');
$stmt->addParameter(1, $userName);
$stmt->execute();
@ -73,7 +67,7 @@ class Users {
public function countUserTFAMethods(UserInfo $userInfo): int {
$stmt = $this->stmts->getStatement('count user tfa methods', fn() => ('SELECT COUNT(*) FROM ' . self::TFA_TABLE . ' WHERE user_id = ?'));
$stmt = $this->cache->get('SELECT COUNT(*) FROM ' . self::TFA_TABLE . ' WHERE user_id = ?');
$stmt->addParameter(1, $userInfo->getId());
$stmt->execute();
$result = $stmt->getResult();
@ -82,7 +76,7 @@ class Users {
}
public function getUserTFAMethods(UserInfo $userInfo): array {
$stmt = $this->stmts->getStatement('get user tfa methods', fn() => ('SELECT ' . implode(',', self::TFA_FIELDS) . ' FROM ' . self::TFA_TABLE . ' WHERE user_id = ?'));
$stmt = $this->cache->get('SELECT ' . implode(',', self::TFA_FIELDS) . ' FROM ' . self::TFA_TABLE . ' WHERE user_id = ?');
$stmt->addParameter(1, $userInfo->getId());
$stmt->execute();
@ -96,7 +90,7 @@ class Users {
}
public function checkUserTFAMethod(UserInfo $userInfo, IAuthMethod $method): bool {
$stmt = $this->stmts->getStatement('check user auth method', fn() => ('SELECT COUNT(*) FROM ' . self::TFA_TABLE . ' WHERE user_id = ? AND user_tfa_type = ?'));
$stmt = $this->cache->get('SELECT COUNT(*) FROM ' . self::TFA_TABLE . ' WHERE user_id = ? AND user_tfa_type = ?');
$stmt->addParameter(1, $userInfo->getId());
$stmt->addParameter(2, $method->getName());
$stmt->execute();
@ -107,7 +101,7 @@ class Users {
public function getUserPasswordInfo(UserInfo $userInfo): UserPasswordInfo {
$stmt = $this->stmts->getStatement('get pwd', fn() => ('SELECT ' . implode(',', self::PASSWORDS_FIELDS) . ' FROM ' . self::PASSWORDS_TABLE . ' WHERE user_id = ?'));
$stmt = $this->cache->get('SELECT ' . implode(',', self::PASSWORDS_FIELDS) . ' FROM ' . self::PASSWORDS_TABLE . ' WHERE user_id = ?');
$stmt->addParameter(1, $userInfo->getId());
$stmt->execute();
$result = $stmt->getResult();
@ -120,7 +114,7 @@ class Users {
public function getUserTOTPInfo(UserInfo $userInfo): UserTOTPInfo {
$stmt = $this->stmts->getStatement('get totp', fn() => ('SELECT ' . implode(',', self::TOTP_FIELDS) . ' FROM ' . self::TOTP_TABLE . ' WHERE user_id = ?'));
$stmt = $this->cache->get('SELECT ' . implode(',', self::TOTP_FIELDS) . ' FROM ' . self::TOTP_TABLE . ' WHERE user_id = ?');
$stmt->addParameter(1, $userInfo->getId());
$stmt->execute();
$result = $stmt->getResult();
@ -133,7 +127,7 @@ class Users {
public function getUserEMailInfos(UserInfo $userInfo): array {
$stmt = $this->stmts->getStatement('get emails', fn() => ('SELECT ' . implode(',', self::EMAILS_FIELDS) . ' FROM ' . self::EMAILS_TABLE . ' WHERE user_id = ?'));
$stmt = $this->cache->get('SELECT ' . implode(',', self::EMAILS_FIELDS) . ' FROM ' . self::EMAILS_TABLE . ' WHERE user_id = ?');
$stmt->addParameter(1, $userInfo->getId());
$stmt->execute();
$result = $stmt->getResult();
@ -148,7 +142,7 @@ class Users {
public function getUserBackupInfos(UserInfo $userInfo): array {
$stmt = $this->stmts->getStatement('get backups', fn() => ('SELECT ' . implode(',', self::BACKUP_FIELDS) . ' FROM ' . self::BACKUP_TABLE . ' WHERE user_id = ?'));
$stmt = $this->cache->get('SELECT ' . implode(',', self::BACKUP_FIELDS) . ' FROM ' . self::BACKUP_TABLE . ' WHERE user_id = ?');
$stmt->addParameter(1, $userInfo->getId());
$stmt->execute();
$result = $stmt->getResult();