From dfcc88407cb40fa05a38e4c5524a3d9054435d34 Mon Sep 17 00:00:00 2001 From: Raditya Harya Date: Mon, 15 Apr 2024 19:33:48 +0700 Subject: [PATCH] Migrate to hono --- bun.lockb | Bin 156112 -> 127843 bytes package-lock.json | 754 +----------------------------- package.json | 6 +- src/index.ts | 41 +- src/lib/helpers.ts | 1 + src/webhooks/index.ts | 253 +++++----- src/webhooks/routes/example.ts | 12 +- src/webhooks/routes/generic.ts | 23 +- src/webhooks/routes/railway.ts | 28 +- src/webhooks/routes/uptimekuma.ts | 27 +- 10 files changed, 192 insertions(+), 953 deletions(-) diff --git a/bun.lockb b/bun.lockb index 905dab8950f7558380e9a76e070bf7f263d40bd8..f12fa61a1136f3974cc87635122090c5f25550fb 100755 GIT binary patch delta 22931 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 KOSQH-^S=OxlX~3% delta 39528 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 diff --git a/package-lock.json b/package-lock.json index 42ad4d3..afef088 100644 --- a/package-lock.json +++ b/package-lock.json @@ -11,17 +11,14 @@ "dependencies": { "@prisma/client": "5.12.1", "@types/body-parser": "^1.19.5", - "@types/express": "^4.17.21", "axios": "^1.6.8", - "body-parser": "^1.20.2", "croner": "^8.0.2", "date-fns": "^3.6.0", "discord.js": "^14.14.1", "dotenv": "^16.4.5", - "express": "^4.19.2", "form-data": "^4.0.0", "gpt3-tokenizer": "^1.1.5", - "helmet": "^7.1.0", + "hono": "^4.2.4", "lodash": "^4.17.21", "openai": "^4.33.1", "pino": "^8.20.0", @@ -32,7 +29,6 @@ "tmp-promise": "^3.0.3" }, "devDependencies": { - "@types/express-serve-static-core": "^4.19.0", "@types/lodash": "^4.17.0", "@types/node": "^20.12.7", "@typescript-eslint/eslint-plugin": "^7.6.0", @@ -553,33 +549,6 @@ "@types/node": "*" } }, - "node_modules/@types/express": { - "version": "4.17.21", - "resolved": "https://registry.npmjs.org/@types/express/-/express-4.17.21.tgz", - "integrity": "sha512-ejlPM315qwLpaQlQDTjPdsUFSc6ZsP4AN6AlWnogPjQ7CVi7PYF3YVz+CY3jE2pwYf7E/7HlDAN0rV2GxTG0HQ==", - "dependencies": { - "@types/body-parser": "*", - "@types/express-serve-static-core": "^4.17.33", - "@types/qs": "*", - "@types/serve-static": "*" - } - }, - "node_modules/@types/express-serve-static-core": { - "version": "4.19.0", - "resolved": "https://registry.npmjs.org/@types/express-serve-static-core/-/express-serve-static-core-4.19.0.tgz", - "integrity": "sha512-bGyep3JqPCRry1wq+O5n7oiBgGWmeIJXPjXXCo8EK0u8duZGSYar7cGqd3ML2JUsLGeB7fmc06KYo9fLGWqPvQ==", - "dependencies": { - "@types/node": "*", - "@types/qs": "*", - "@types/range-parser": "*", - "@types/send": "*" - } - }, - "node_modules/@types/http-errors": { - "version": "2.0.4", - "resolved": "https://registry.npmjs.org/@types/http-errors/-/http-errors-2.0.4.tgz", - "integrity": "sha512-D0CFMMtydbJAegzOyHjtiKPLlvnm3iTZyZRSZoLq2mRhDdmLfIWOCYPfQJ4cu2erKghU++QvjcUjp/5h7hESpA==" - }, "node_modules/@types/json-schema": { "version": "7.0.15", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.15.tgz", @@ -592,11 +561,6 @@ "integrity": "sha512-t7dhREVv6dbNj0q17X12j7yDG4bD/DHYX7o5/DbDxobP0HnGPgpRz2Ej77aL7TZT3DSw13fqUTj8J4mMnqa7WA==", "dev": true }, - "node_modules/@types/mime": { - "version": "1.3.5", - "resolved": "https://registry.npmjs.org/@types/mime/-/mime-1.3.5.tgz", - "integrity": "sha512-/pyBZWSLD2n0dcHE3hq8s8ZvcETHtEuF+3E7XVt0Ig2nvsVQXdghHVcEkIWjy9A0wKfTn97a/PSDYohKIlnP/w==" - }, "node_modules/@types/node": { "version": "20.12.7", "resolved": "https://registry.npmjs.org/@types/node/-/node-20.12.7.tgz", @@ -614,41 +578,12 @@ "form-data": "^4.0.0" } }, - "node_modules/@types/qs": { - "version": "6.9.14", - "resolved": "https://registry.npmjs.org/@types/qs/-/qs-6.9.14.tgz", - "integrity": "sha512-5khscbd3SwWMhFqylJBLQ0zIu7c1K6Vz0uBIt915BI3zV0q1nfjRQD3RqSBcPaO6PHEF4ov/t9y89fSiyThlPA==" - }, - "node_modules/@types/range-parser": { - "version": "1.2.7", - "resolved": "https://registry.npmjs.org/@types/range-parser/-/range-parser-1.2.7.tgz", - "integrity": "sha512-hKormJbkJqzQGhziax5PItDUTMAM9uE2XXQmM37dyd4hVM+5aVl7oVxMVUiVQn2oCQFN/LKCZdvSM0pFRqbSmQ==" - }, "node_modules/@types/semver": { "version": "7.5.8", "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.5.8.tgz", "integrity": "sha512-I8EUhyrgfLrcTkzV3TSsGyl1tSuPrEDzr0yd5m90UgNxQkyDXULk3b6MlQqTCpZpNtWe1K0hzclnZkTcLBe2UQ==", "dev": true }, - "node_modules/@types/send": { - "version": "0.17.4", - "resolved": "https://registry.npmjs.org/@types/send/-/send-0.17.4.tgz", - "integrity": "sha512-x2EM6TJOybec7c52BX0ZspPodMsQUd5L6PRwOunVyVUhXiBSKf3AezDL8Dgvgt5o0UfKNfuA0eMLr2wLT4AiBA==", - "dependencies": { - "@types/mime": "^1", - "@types/node": "*" - } - }, - "node_modules/@types/serve-static": { - "version": "1.15.7", - "resolved": "https://registry.npmjs.org/@types/serve-static/-/serve-static-1.15.7.tgz", - "integrity": "sha512-W8Ym+h8nhuRwaKPaDw34QUkwsGi6Rc4yYqvKFo5rm2FUEhCFbzVWrxXUxuKK8TASjWsysJY0nsmNCGhCOIsrOw==", - "dependencies": { - "@types/http-errors": "*", - "@types/node": "*", - "@types/send": "*" - } - }, "node_modules/@types/ws": { "version": "8.5.9", "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.5.9.tgz", @@ -879,18 +814,6 @@ "node": ">=6.5" } }, - "node_modules/accepts": { - "version": "1.3.8", - "resolved": "https://registry.npmjs.org/accepts/-/accepts-1.3.8.tgz", - "integrity": "sha512-PYAthTa2m2VKxuvSD3DPC/Gy+U+sOA1LAuT8mkmRuvw+NACSaeXEQ+NHcVF7rONl6qcaxV3Uuemwawk+7+SJLw==", - "dependencies": { - "mime-types": "~2.1.34", - "negotiator": "0.6.3" - }, - "engines": { - "node": ">= 0.6" - } - }, "node_modules/acorn": { "version": "8.11.3", "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.11.3.tgz", @@ -997,11 +920,6 @@ "integrity": "sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==", "dev": true }, - "node_modules/array-flatten": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/array-flatten/-/array-flatten-1.1.1.tgz", - "integrity": "sha512-PCVAQswWemu6UdxsDFFX/+gVeYqKAod3D3UVm91jHwynguOwAvYPhx8nNlM++NqRcK6CxxpUafjmhIdKiHibqg==" - }, "node_modules/array-keyed-map": { "version": "2.1.3", "resolved": "https://registry.npmjs.org/array-keyed-map/-/array-keyed-map-2.1.3.tgz", @@ -1076,42 +994,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/body-parser": { - "version": "1.20.2", - "resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.2.tgz", - "integrity": "sha512-ml9pReCu3M61kGlqoTm2umSXTlRTuGTx0bfYj+uIUKKYycG5NtSbeetV3faSU6R7ajOPw0g/J1PvK4qNy7s5bA==", - "dependencies": { - "bytes": "3.1.2", - "content-type": "~1.0.5", - "debug": "2.6.9", - "depd": "2.0.0", - "destroy": "1.2.0", - "http-errors": "2.0.0", - "iconv-lite": "0.4.24", - "on-finished": "2.4.1", - "qs": "6.11.0", - "raw-body": "2.5.2", - "type-is": "~1.6.18", - "unpipe": "1.0.0" - }, - "engines": { - "node": ">= 0.8", - "npm": "1.2.8000 || >= 1.4.16" - } - }, - "node_modules/body-parser/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/body-parser/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" - }, "node_modules/brace-expansion": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-2.0.1.tgz", @@ -1156,32 +1038,6 @@ "ieee754": "^1.2.1" } }, - "node_modules/bytes": { - "version": "3.1.2", - "resolved": "https://registry.npmjs.org/bytes/-/bytes-3.1.2.tgz", - "integrity": "sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/call-bind": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz", - "integrity": "sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==", - "dependencies": { - "es-define-property": "^1.0.0", - "es-errors": "^1.3.0", - "function-bind": "^1.1.2", - "get-intrinsic": "^1.2.4", - "set-function-length": "^1.2.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/callsites": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/callsites/-/callsites-3.1.0.tgz", @@ -1293,38 +1149,6 @@ "integrity": "sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==", "dev": true }, - "node_modules/content-disposition": { - "version": "0.5.4", - "resolved": "https://registry.npmjs.org/content-disposition/-/content-disposition-0.5.4.tgz", - "integrity": "sha512-FveZTNuGw04cxlAiWbzi6zTAL/lhehaWbTtgluJh4/E95DqMwTmha3KZN1aAWA8cFIhHzMZUvLevkw5Rqk+tSQ==", - "dependencies": { - "safe-buffer": "5.2.1" - }, - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/content-type": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/content-type/-/content-type-1.0.5.tgz", - "integrity": "sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/cookie": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/cookie/-/cookie-0.6.0.tgz", - "integrity": "sha512-U71cyTamuh1CRNCfpGY6to28lxvNwPG4Guz/EVjgf3Jmzv0vlDp1atT9eS5dDjMYHucpHbWns6Lwf3BKz6svdw==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/cookie-signature": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/cookie-signature/-/cookie-signature-1.0.6.tgz", - "integrity": "sha512-QADzlaHc8icV8I7vbaJXJwod9HWYp8uCqf1xa4OfNu1T7JVxQIrUgOWtHdNDtPiywmFbiS12VjotIXLrKM3orQ==" - }, "node_modules/create-require": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/create-require/-/create-require-1.1.1.tgz", @@ -1394,22 +1218,6 @@ "integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==", "dev": true }, - "node_modules/define-data-property": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", - "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", - "dependencies": { - "es-define-property": "^1.0.0", - "es-errors": "^1.3.0", - "gopd": "^1.0.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/delayed-stream": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", @@ -1418,23 +1226,6 @@ "node": ">=0.4.0" } }, - "node_modules/depd": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", - "integrity": "sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==", - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/destroy": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/destroy/-/destroy-1.2.0.tgz", - "integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg==", - "engines": { - "node": ">= 0.8", - "npm": "1.2.8000 || >= 1.4.16" - } - }, "node_modules/diff": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/diff/-/diff-4.0.2.tgz", @@ -1514,25 +1305,12 @@ "integrity": "sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==", "dev": true }, - "node_modules/ee-first": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/ee-first/-/ee-first-1.1.1.tgz", - "integrity": "sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==" - }, "node_modules/emoji-regex": { "version": "9.2.2", "resolved": "https://registry.npmjs.org/emoji-regex/-/emoji-regex-9.2.2.tgz", "integrity": "sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==", "dev": true }, - "node_modules/encodeurl": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/encodeurl/-/encodeurl-1.0.2.tgz", - "integrity": "sha512-TPJXq8JqFaVYm2CWmPvnP2Iyo4ZSM7/QKcSmuMLDObfpH5fi7RUGmd/rTDf+rut/saiDiQEeVTNgAmJEdAOx0w==", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/end-of-stream": { "version": "1.4.4", "resolved": "https://registry.npmjs.org/end-of-stream/-/end-of-stream-1.4.4.tgz", @@ -1550,30 +1328,6 @@ "url": "https://github.com/fb55/entities?sponsor=1" } }, - "node_modules/es-define-property": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.0.tgz", - "integrity": "sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==", - "dependencies": { - "get-intrinsic": "^1.2.4" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/es-errors": { - "version": "1.3.0", - "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", - "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/escape-html": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/escape-html/-/escape-html-1.0.3.tgz", - "integrity": "sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==" - }, "node_modules/escape-string-regexp": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-4.0.0.tgz", @@ -1762,14 +1516,6 @@ "node": ">=0.10.0" } }, - "node_modules/etag": { - "version": "1.8.1", - "resolved": "https://registry.npmjs.org/etag/-/etag-1.8.1.tgz", - "integrity": "sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==", - "engines": { - "node": ">= 0.6" - } - }, "node_modules/event-target-shim": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", @@ -1809,60 +1555,6 @@ "url": "https://github.com/sindresorhus/execa?sponsor=1" } }, - "node_modules/express": { - "version": "4.19.2", - "resolved": "https://registry.npmjs.org/express/-/express-4.19.2.tgz", - "integrity": "sha512-5T6nhjsT+EOMzuck8JjBHARTHfMht0POzlA60WV2pMD3gyXw2LZnZ+ueGdNxG+0calOJcWKbpFcuzLZ91YWq9Q==", - "dependencies": { - "accepts": "~1.3.8", - "array-flatten": "1.1.1", - "body-parser": "1.20.2", - "content-disposition": "0.5.4", - "content-type": "~1.0.4", - "cookie": "0.6.0", - "cookie-signature": "1.0.6", - "debug": "2.6.9", - "depd": "2.0.0", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "finalhandler": "1.2.0", - "fresh": "0.5.2", - "http-errors": "2.0.0", - "merge-descriptors": "1.0.1", - "methods": "~1.1.2", - "on-finished": "2.4.1", - "parseurl": "~1.3.3", - "path-to-regexp": "0.1.7", - "proxy-addr": "~2.0.7", - "qs": "6.11.0", - "range-parser": "~1.2.1", - "safe-buffer": "5.2.1", - "send": "0.18.0", - "serve-static": "1.15.0", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "type-is": "~1.6.18", - "utils-merge": "1.0.1", - "vary": "~1.1.2" - }, - "engines": { - "node": ">= 0.10.0" - } - }, - "node_modules/express/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/express/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" - }, "node_modules/fast-copy": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/fast-copy/-/fast-copy-3.0.2.tgz", @@ -1961,36 +1653,6 @@ "node": ">=8" } }, - "node_modules/finalhandler": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/finalhandler/-/finalhandler-1.2.0.tgz", - "integrity": "sha512-5uXcUVftlQMFnWC9qu/svkWv3GTd2PfUhK/3PLkYNAe7FbqJMt3515HaxE6eRL74GdsriiwujiawdaB1BpEISg==", - "dependencies": { - "debug": "2.6.9", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "on-finished": "2.4.1", - "parseurl": "~1.3.3", - "statuses": "2.0.1", - "unpipe": "~1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, - "node_modules/finalhandler/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/finalhandler/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" - }, "node_modules/find-up": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/find-up/-/find-up-5.0.0.tgz", @@ -2169,22 +1831,6 @@ "node": ">= 14" } }, - "node_modules/forwarded": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", - "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/fresh": { - "version": "0.5.2", - "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", - "integrity": "sha512-zJ2mQYM18rEFOudeV4GShTGIQ7RbzA7ozbU9I/XBpm7kqgMywgmylMwXHxZJmkVoYkna9d2pVXVXPdYTP9ej8Q==", - "engines": { - "node": ">= 0.6" - } - }, "node_modules/fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", @@ -2205,32 +1851,6 @@ "node": "^8.16.0 || ^10.6.0 || >=11.0.0" } }, - "node_modules/function-bind": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/function-bind/-/function-bind-1.1.2.tgz", - "integrity": "sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/get-intrinsic": { - "version": "1.2.4", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.4.tgz", - "integrity": "sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==", - "dependencies": { - "es-errors": "^1.3.0", - "function-bind": "^1.1.2", - "has-proto": "^1.0.1", - "has-symbols": "^1.0.3", - "hasown": "^2.0.0" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/get-stream": { "version": "6.0.1", "resolved": "https://registry.npmjs.org/get-stream/-/get-stream-6.0.1.tgz", @@ -2322,17 +1942,6 @@ "resolved": "https://registry.npmjs.org/globrex/-/globrex-0.1.2.tgz", "integrity": "sha512-uHJgbwAMwNFf5mLst7IWLNg14x1CkeqglJb/K3doi4dw6q2IvAAmM/Y81kevy83wP+Sst+nutFTYOGg3d1lsxg==" }, - "node_modules/gopd": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/gopd/-/gopd-1.0.1.tgz", - "integrity": "sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==", - "dependencies": { - "get-intrinsic": "^1.1.3" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/gpt3-tokenizer": { "version": "1.1.5", "resolved": "https://registry.npmjs.org/gpt3-tokenizer/-/gpt3-tokenizer-1.1.5.tgz", @@ -2359,77 +1968,18 @@ "node": ">=8" } }, - "node_modules/has-property-descriptors": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", - "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", - "dependencies": { - "es-define-property": "^1.0.0" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-proto": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/has-proto/-/has-proto-1.0.3.tgz", - "integrity": "sha512-SJ1amZAJUiZS+PhsVLf5tGydlaVB8EdFpaSO4gmiUKUOxk8qzn5AIy4ZeJUmh22znIdk/uMAUT2pl3FxzVUH+Q==", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/has-symbols": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/has-symbols/-/has-symbols-1.0.3.tgz", - "integrity": "sha512-l3LCuF6MgDNwTDKkdYGEihYjt5pRPbEg46rtlmnSPlUbgmB8LOIrKJbYYFBSbnPaJexMKtiPO8hmeRjRz2Td+A==", - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, - "node_modules/hasown": { - "version": "2.0.2", - "resolved": "https://registry.npmjs.org/hasown/-/hasown-2.0.2.tgz", - "integrity": "sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==", - "dependencies": { - "function-bind": "^1.1.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/helmet": { - "version": "7.1.0", - "resolved": "https://registry.npmjs.org/helmet/-/helmet-7.1.0.tgz", - "integrity": "sha512-g+HZqgfbpXdCkme/Cd/mZkV0aV3BZZZSugecH03kl38m/Kmdx8jKjBikpDj2cr+Iynv4KpYEviojNdTJActJAg==", - "engines": { - "node": ">=16.0.0" - } - }, "node_modules/help-me": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/help-me/-/help-me-5.0.0.tgz", "integrity": "sha512-7xgomUX6ADmcYzFik0HzAxh/73YlKR9bmFzf51CZwR+b6YtzU2m0u49hQCqV6SvlqIqsaxovfwdvbnsw3b/zpg==", "dev": true }, - "node_modules/http-errors": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/http-errors/-/http-errors-2.0.0.tgz", - "integrity": "sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==", - "dependencies": { - "depd": "2.0.0", - "inherits": "2.0.4", - "setprototypeof": "1.2.0", - "statuses": "2.0.1", - "toidentifier": "1.0.1" - }, + "node_modules/hono": { + "version": "4.2.4", + "resolved": "https://registry.npmjs.org/hono/-/hono-4.2.4.tgz", + "integrity": "sha512-2T5Ahxh8tT0ISKCrNeA+OIwfD5W4EZ00iIMYBBCuiIivr+sOrZYOphinARSG7wL3nFsY6zkFHMMZbcR9CzEzug==", "engines": { - "node": ">= 0.8" + "node": ">=16.0.0" } }, "node_modules/human-signals": { @@ -2464,17 +2014,6 @@ "url": "https://github.com/sponsors/typicode" } }, - "node_modules/iconv-lite": { - "version": "0.4.24", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.24.tgz", - "integrity": "sha512-v3MXnZAcvnywkTUEZomIActle7RXXeedOR31wwl7VlyoXO4Qi9arvSenNQWne1TcRwhCL1HwLI21bEqdpj8/rA==", - "dependencies": { - "safer-buffer": ">= 2.1.2 < 3" - }, - "engines": { - "node": ">=0.10.0" - } - }, "node_modules/ieee754": { "version": "1.2.1", "resolved": "https://registry.npmjs.org/ieee754/-/ieee754-1.2.1.tgz", @@ -2547,15 +2086,8 @@ "node_modules/inherits": { "version": "2.0.4", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.4.tgz", - "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==" - }, - "node_modules/ipaddr.js": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", - "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==", - "engines": { - "node": ">= 0.10" - } + "integrity": "sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==", + "dev": true }, "node_modules/is-binary-path": { "version": "2.1.0", @@ -2777,19 +2309,6 @@ "integrity": "sha512-s8UhlNe7vPKomQhC1qFelMokr/Sc3AgNbso3n74mVPA5LTZwkB9NlXf4XPamLxJE8h0gh73rM94xvwRT2CVInw==", "dev": true }, - "node_modules/media-typer": { - "version": "0.3.0", - "resolved": "https://registry.npmjs.org/media-typer/-/media-typer-0.3.0.tgz", - "integrity": "sha512-dq+qelQ9akHpcOl/gUVRTxVIOkAJ1wR3QAvb4RsVjS8oVoFjDGTc679wJYmUmknUF5HwMLOgb5O+a3KxfWapPQ==", - "engines": { - "node": ">= 0.6" - } - }, - "node_modules/merge-descriptors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/merge-descriptors/-/merge-descriptors-1.0.1.tgz", - "integrity": "sha512-cCi6g3/Zr1iqQi6ySbseM1Xvooa98N0w31jzUYrXPX2xqObmFGHJ0tQ5u74H3mVh7wLouTseZyYIq39g8cNp1w==" - }, "node_modules/merge-stream": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", @@ -2805,14 +2324,6 @@ "node": ">= 8" } }, - "node_modules/methods": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/methods/-/methods-1.1.2.tgz", - "integrity": "sha512-iclAHeNqNm68zFtnZ0e+1L2yUIdvzNoauKU4WBA3VvH/vPFieF7qfRlwUZU+DA9P9bPXIS90ulxoUoCH23sV2w==", - "engines": { - "node": ">= 0.6" - } - }, "node_modules/micromatch": { "version": "4.0.5", "resolved": "https://registry.npmjs.org/micromatch/-/micromatch-4.0.5.tgz", @@ -2826,17 +2337,6 @@ "node": ">=8.6" } }, - "node_modules/mime": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/mime/-/mime-1.6.0.tgz", - "integrity": "sha512-x0Vn8spI+wuJ1O6S7gnbaQg8Pxh4NNHb7KSINmEWKiPE4RKOplvijn+NkmYmmRgP68mc70j2EbeTFRsrswaQeg==", - "bin": { - "mime": "cli.js" - }, - "engines": { - "node": ">=4" - } - }, "node_modules/mime-db": { "version": "1.52.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", @@ -2931,14 +2431,6 @@ "integrity": "sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==", "dev": true }, - "node_modules/negotiator": { - "version": "0.6.3", - "resolved": "https://registry.npmjs.org/negotiator/-/negotiator-0.6.3.tgz", - "integrity": "sha512-+EUsqGPLsM+j/zdChZjsnX51g4XrHFOIXwfnCVPGlQk/k5giakcKsuxCObBRu6DSm9opw/O6slWbJdghQM4bBg==", - "engines": { - "node": ">= 0.6" - } - }, "node_modules/node-domexception": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/node-domexception/-/node-domexception-1.0.0.tgz", @@ -3083,14 +2575,6 @@ "node": ">=8" } }, - "node_modules/object-inspect": { - "version": "1.13.1", - "resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.13.1.tgz", - "integrity": "sha512-5qoj1RUiKOMsCCNLV1CBiPYE10sziTsnmNxkAI/rZhiD63CF7IqdFGC/XzjWjpSgLf0LxXX3bDFIh0E18f6UhQ==", - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/on-exit-leak-free": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/on-exit-leak-free/-/on-exit-leak-free-2.1.2.tgz", @@ -3099,17 +2583,6 @@ "node": ">=14.0.0" } }, - "node_modules/on-finished": { - "version": "2.4.1", - "resolved": "https://registry.npmjs.org/on-finished/-/on-finished-2.4.1.tgz", - "integrity": "sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==", - "dependencies": { - "ee-first": "1.1.1" - }, - "engines": { - "node": ">= 0.8" - } - }, "node_modules/once": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", @@ -3219,14 +2692,6 @@ "node": ">=6" } }, - "node_modules/parseurl": { - "version": "1.3.3", - "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", - "integrity": "sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/path-exists": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-4.0.0.tgz", @@ -3270,11 +2735,6 @@ "url": "https://github.com/sponsors/isaacs" } }, - "node_modules/path-to-regexp": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-0.1.7.tgz", - "integrity": "sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==" - }, "node_modules/path-type": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/path-type/-/path-type-4.0.0.tgz", @@ -3462,18 +2922,6 @@ "resolved": "https://registry.npmjs.org/process-warning/-/process-warning-3.0.0.tgz", "integrity": "sha512-mqn0kFRl0EoqhnL0GQ0veqFHyIN1yig9RHh/InzORTUiZHFRAur+aMtRkELNwGs9aNwKS6tg/An4NYBPGwvtzQ==" }, - "node_modules/proxy-addr": { - "version": "2.0.7", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", - "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", - "dependencies": { - "forwarded": "0.2.0", - "ipaddr.js": "1.9.1" - }, - "engines": { - "node": ">= 0.10" - } - }, "node_modules/proxy-from-env": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/proxy-from-env/-/proxy-from-env-1.1.0.tgz", @@ -3504,20 +2952,6 @@ "node": ">=6" } }, - "node_modules/qs": { - "version": "6.11.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.11.0.tgz", - "integrity": "sha512-MvjoMCJwEarSbUYk5O+nmoSzSutSsTwF85zcHPQ9OrlFoZOYIjaqBAJIqIXjptyD5vThxGq52Xu/MaJzRkIk4Q==", - "dependencies": { - "side-channel": "^1.0.4" - }, - "engines": { - "node": ">=0.6" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/queue-lit": { "version": "1.5.2", "resolved": "https://registry.npmjs.org/queue-lit/-/queue-lit-1.5.2.tgz", @@ -3552,33 +2986,11 @@ "resolved": "https://registry.npmjs.org/quick-format-unescaped/-/quick-format-unescaped-4.0.4.tgz", "integrity": "sha512-tYC1Q1hgyRuHgloV/YXs2w15unPVh8qfu/qCTfhTYamaw7fyhumKa2yGpdSo87vY32rIclj+4fWYQXUMs9EHvg==" }, - "node_modules/range-parser": { - "version": "1.2.1", - "resolved": "https://registry.npmjs.org/range-parser/-/range-parser-1.2.1.tgz", - "integrity": "sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==", - "engines": { - "node": ">= 0.6" - } - }, "node_modules/rate-limiter-flexible": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/rate-limiter-flexible/-/rate-limiter-flexible-5.0.0.tgz", "integrity": "sha512-ivCyLBwPtR5IRrz+aZnztVwX16ZK3iAjdlW21I/vjHq56at5Zb8eIefDzODg8R7hwPOHpBtb6Pj9Zdmn0nRb8g==" }, - "node_modules/raw-body": { - "version": "2.5.2", - "resolved": "https://registry.npmjs.org/raw-body/-/raw-body-2.5.2.tgz", - "integrity": "sha512-8zGqypfENjCIqGhgXToC8aB2r7YrBX+AQAfIPs/Mlk+BtPTztOvTS01NRW/3Eh60J+a48lt8qsCzirQ6loCVfA==", - "dependencies": { - "bytes": "3.1.2", - "http-errors": "2.0.0", - "iconv-lite": "0.4.24", - "unpipe": "1.0.0" - }, - "engines": { - "node": ">= 0.8" - } - }, "node_modules/readable-stream": { "version": "4.5.2", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-4.5.2.tgz", @@ -3710,11 +3122,6 @@ "node": ">=10" } }, - "node_modules/safer-buffer": { - "version": "2.1.2", - "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", - "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" - }, "node_modules/sax": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/sax/-/sax-1.3.0.tgz", @@ -3753,82 +3160,6 @@ "node": ">=10" } }, - "node_modules/send": { - "version": "0.18.0", - "resolved": "https://registry.npmjs.org/send/-/send-0.18.0.tgz", - "integrity": "sha512-qqWzuOjSFOuqPjFe4NOsMLafToQQwBSOEpS+FwEt3A2V3vKubTquT3vmLTQpFgMXp8AlFWFuP1qKaJZOtPpVXg==", - "dependencies": { - "debug": "2.6.9", - "depd": "2.0.0", - "destroy": "1.2.0", - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "etag": "~1.8.1", - "fresh": "0.5.2", - "http-errors": "2.0.0", - "mime": "1.6.0", - "ms": "2.1.3", - "on-finished": "2.4.1", - "range-parser": "~1.2.1", - "statuses": "2.0.1" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/send/node_modules/debug": { - "version": "2.6.9", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.9.tgz", - "integrity": "sha512-bC7ElrdJaJnPbAP+1EotYvqZsb3ecl5wi6Bfi6BJTUcNowp6cvspg0jXznRTKDjm/E7AdgFBVeAPVMNcKGsHMA==", - "dependencies": { - "ms": "2.0.0" - } - }, - "node_modules/send/node_modules/debug/node_modules/ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==" - }, - "node_modules/send/node_modules/ms": { - "version": "2.1.3", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" - }, - "node_modules/serve-static": { - "version": "1.15.0", - "resolved": "https://registry.npmjs.org/serve-static/-/serve-static-1.15.0.tgz", - "integrity": "sha512-XGuRDNjXUijsUL0vl6nSD7cwURuzEgglbOaFuZM9g3kwDXOWVTck0jLzjPzGD+TazWbboZYu52/9/XPdUgne9g==", - "dependencies": { - "encodeurl": "~1.0.2", - "escape-html": "~1.0.3", - "parseurl": "~1.3.3", - "send": "0.18.0" - }, - "engines": { - "node": ">= 0.8.0" - } - }, - "node_modules/set-function-length": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", - "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", - "dependencies": { - "define-data-property": "^1.1.4", - "es-errors": "^1.3.0", - "function-bind": "^1.1.2", - "get-intrinsic": "^1.2.4", - "gopd": "^1.0.1", - "has-property-descriptors": "^1.0.2" - }, - "engines": { - "node": ">= 0.4" - } - }, - "node_modules/setprototypeof": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/setprototypeof/-/setprototypeof-1.2.0.tgz", - "integrity": "sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==" - }, "node_modules/shebang-command": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", @@ -3850,23 +3181,6 @@ "node": ">=8" } }, - "node_modules/side-channel": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.6.tgz", - "integrity": "sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==", - "dependencies": { - "call-bind": "^1.0.7", - "es-errors": "^1.3.0", - "get-intrinsic": "^1.2.4", - "object-inspect": "^1.13.1" - }, - "engines": { - "node": ">= 0.4" - }, - "funding": { - "url": "https://github.com/sponsors/ljharb" - } - }, "node_modules/signal-exit": { "version": "3.0.7", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.7.tgz", @@ -3910,14 +3224,6 @@ "node": ">= 10.x" } }, - "node_modules/statuses": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/statuses/-/statuses-2.0.1.tgz", - "integrity": "sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/string_decoder": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.3.0.tgz", @@ -4109,14 +3415,6 @@ "node": ">=8.0" } }, - "node_modules/toidentifier": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", - "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==", - "engines": { - "node": ">=0.6" - } - }, "node_modules/touch": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", @@ -4254,18 +3552,6 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/type-is": { - "version": "1.6.18", - "resolved": "https://registry.npmjs.org/type-is/-/type-is-1.6.18.tgz", - "integrity": "sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==", - "dependencies": { - "media-typer": "0.3.0", - "mime-types": "~2.1.24" - }, - "engines": { - "node": ">= 0.6" - } - }, "node_modules/typescript": { "version": "5.4.5", "resolved": "https://registry.npmjs.org/typescript/-/typescript-5.4.5.tgz", @@ -4301,14 +3587,6 @@ "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-5.26.5.tgz", "integrity": "sha512-JlCMO+ehdEIKqlFxk6IfVoAUVmgz7cU7zD/h9XZ0qzeosSHmUJVOzSQvvYSYWXkFXC+IfLKSIffhv0sVZup6pA==" }, - "node_modules/unpipe": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/unpipe/-/unpipe-1.0.0.tgz", - "integrity": "sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/uri-js": { "version": "4.4.1", "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", @@ -4318,28 +3596,12 @@ "punycode": "^2.1.0" } }, - "node_modules/utils-merge": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/utils-merge/-/utils-merge-1.0.1.tgz", - "integrity": "sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==", - "engines": { - "node": ">= 0.4.0" - } - }, "node_modules/v8-compile-cache-lib": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", "integrity": "sha512-wa7YjyUGfNZngI/vtK0UHAN+lgDCxBPCylVXGp0zu59Fz5aiGtNXaq3DhIov063MorB+VfufLh3JlF2KdTK3xg==", "dev": true }, - "node_modules/vary": { - "version": "1.1.2", - "resolved": "https://registry.npmjs.org/vary/-/vary-1.1.2.tgz", - "integrity": "sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==", - "engines": { - "node": ">= 0.8" - } - }, "node_modules/web-streams-polyfill": { "version": "3.3.3", "resolved": "https://registry.npmjs.org/web-streams-polyfill/-/web-streams-polyfill-3.3.3.tgz", diff --git a/package.json b/package.json index 4a5238a..692968c 100644 --- a/package.json +++ b/package.json @@ -25,17 +25,14 @@ "dependencies": { "@prisma/client": "5.12.1", "@types/body-parser": "^1.19.5", - "@types/express": "^4.17.21", "axios": "^1.6.8", - "body-parser": "^1.20.2", "croner": "^8.0.2", "date-fns": "^3.6.0", "discord.js": "^14.14.1", "dotenv": "^16.4.5", - "express": "^4.19.2", "form-data": "^4.0.0", "gpt3-tokenizer": "^1.1.5", - "helmet": "^7.1.0", + "hono": "^4.2.4", "lodash": "^4.17.21", "openai": "^4.33.1", "pino": "^8.20.0", @@ -46,7 +43,6 @@ "tmp-promise": "^3.0.3" }, "devDependencies": { - "@types/express-serve-static-core": "^4.19.0", "@types/lodash": "^4.17.0", "@types/node": "^20.12.7", "@typescript-eslint/eslint-plugin": "^7.6.0", diff --git a/src/index.ts b/src/index.ts index 439301f..03db189 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,26 +1,20 @@ -import express from 'express'; import { resolve } from 'path'; -import bodyParser from 'body-parser'; -import helmet from 'helmet'; import { Client } from '@/lib/module-loader'; import { ActivityType, GatewayIntentBits, Partials } from 'discord.js'; import config from '@/config'; -import { runFromSrc } from '@/utils/runFromSrc'; import { registerRoutes } from '@/webhooks'; -console.log('runFromSrc', runFromSrc); -const app: express.Application = express(); -const port: number = parseInt(process.env.PORT || '3000'); +import { Hono } from 'hono'; +import { logger } from 'hono/logger'; -app.use(helmet()); -app.use(bodyParser.json()); +const app = new Hono(); +app.use(logger()); +const port: number = parseInt(process.env.PORT || '3000'); const client = new Client({ moduleLoader: { - eventsDir: resolve(__dirname, runFromSrc ? './events' : '../dist/events'), - commandsDir: resolve( - __dirname, - runFromSrc ? './commands' : '../dist/commands', - ), + eventsDir: resolve(__dirname, './events'), + commandsDir: resolve(__dirname, './commands'), + validationsDir: resolve(__dirname, './validations'), }, intents: [ GatewayIntentBits.Guilds, @@ -40,13 +34,11 @@ async function initializeClient() { // Register routes async function registerWebhookRoutes() { const router = await registerRoutes(client); - app.use('/webhooks', router); + app.route('/webhooks', router); } // Health check endpoint -app.get('/health', (req, res) => { - res.send('OK'); -}); +app.get('/health', (c) => c.text('OK')); // Start server async function startServer() { @@ -54,16 +46,10 @@ async function startServer() { await initializeClient(); await registerWebhookRoutes(); - const server = app.listen(port, () => { - console.log(`App listening at ${config.bot.base_url}`); - }); - process.on('SIGINT', () => { console.log('\nGracefully shutting down'); - server.close(() => { - console.log('Express server closed'); - }); + client.destroy(); process.exit(); }); @@ -73,3 +59,8 @@ async function startServer() { } startServer(); + +export default { + port, + fetch: app.fetch, +}; diff --git a/src/lib/helpers.ts b/src/lib/helpers.ts index 990f152..7fbb4e6 100644 --- a/src/lib/helpers.ts +++ b/src/lib/helpers.ts @@ -77,6 +77,7 @@ export function buildContext( export function buildThreadContext( messages: Collection, userMessage: string, + // eslint-disable-next-line @typescript-eslint/no-unused-vars botId: string, ): Array { if (messages.size === 0) { diff --git a/src/webhooks/index.ts b/src/webhooks/index.ts index 23c1dd1..73afd5f 100644 --- a/src/webhooks/index.ts +++ b/src/webhooks/index.ts @@ -1,35 +1,46 @@ /* eslint-disable @typescript-eslint/ban-types */ -import { type Request, type Response, Router } from 'express'; +import { Context, Hono } from 'hono'; +import { createFactory } from 'hono/factory'; import type { Client } from '@/lib/module-loader'; import fs from 'fs'; -import path from 'path'; +import { join, resolve } from 'path'; import crypto from 'crypto'; import logger from '@/utils/logger'; -import { runFromSrc } from '@/utils/runFromSrc'; import config from '@/config'; import { PrismaClient } from '@prisma/client'; +import { Env, HandlerResponse } from 'hono/types'; +import { type TextChannel } from 'discord.js'; -const prisma = new PrismaClient(); -const router = Router(); -const VALID_METHODS = ['get', 'post', 'put', 'delete'] as const; - +interface WebhookVars extends Env { + Variables: { + channel: TextChannel; + client: Client; + }; +} +export type WebhookContext = Context; type Route = { method: (typeof VALID_METHODS)[number]; path: string; - handler: (client: Client) => (req: Request, res: Response) => void; + handler: (client: Client) => (c: WebhookContext) => HandlerResponse; isProtected: boolean; secret?: string; }; +const factory = createFactory(); + +const prisma = new PrismaClient(); + +const VALID_METHODS = ['get', 'post', 'put', 'delete'] as const; + /** * Imports a route file and returns an array of Route objects. * @param file - The name of the file to import. * @param routesPath - The path to the directory containing the route files. * @returns A Promise that resolves to an array of Route objects. */ -async function importRoute(file: string, routesPath: string): Promise { +async function loadRoute(file: string, routesPath: string): Promise { try { - const filePath = path.join(routesPath, file); + const filePath = join(routesPath, file); const stats = fs.statSync(filePath); if (stats.isDirectory()) { @@ -59,7 +70,7 @@ async function importRoute(file: string, routesPath: string): Promise { return methodHandlerPairs.map(([method, handler]) => { const typedHandler = handler as ( client: Client, - ) => (req: Request, res: Response) => void; + ) => (c: Context) => HandlerResponse; return { method: method as (typeof VALID_METHODS)[number], @@ -74,45 +85,23 @@ async function importRoute(file: string, routesPath: string): Promise { } } -/** - * Registers a route in the router with the provided configuration. - * @param route - The route configuration object. - * @param client - Discord client object. - * @param router - The router object. - * @returns The registered route information. - */ async function registerRoute( route: Route, client: Client, - router: Router, -): Promise { + router: Hono, +) { const { method, path: routePath, handler, isProtected, secret } = route; - const handlers = [ - (req: Request, res: Response, next: () => void) => { - if (isProtected) { - const requestSecret = - req.query.secret || req.headers['x-webhook-secret']; - - if (requestSecret !== secret) { - res.status(403).send('Forbidden'); - return; - } - } - next(); - }, + + const handlers = factory.createHandlers( + M_ValidateMethod(method), + M_Secret(isProtected, secret), + M_Discord(client), handler(client), - ]; - ( - router[method as keyof Router] as ( - path: string, - ...handlers: Array< - (req: Request, res: Response, next: () => void) => void - > - ) => void - )(routePath, ...handlers); + ); - // Sync route to the database - const webhookRoute = await prisma.webhookRoutes.upsert({ + (router[method as keyof Hono] as Function)(routePath, ...handlers); + + await prisma.webhookRoutes.upsert({ where: { path: routePath }, create: { path: routePath, @@ -125,27 +114,111 @@ async function registerRoute( }, }); - return { - method, - path: routePath, - handler, - isProtected, - secret: webhookRoute.secret || '', - }; + return route; } -// eslint-disable-next-line @typescript-eslint/no-explicit-any -async function deleteRoutes(dbRoutes: any[], currentRoutes: Route[]) { - const deletedRoutes = dbRoutes.filter((dbRoute) => { - return !currentRoutes.some((route) => route.path === dbRoute.path); +/** + * File based route initialization. + * + * @param client - Discord client object. + * @returns Hono instance with registered routes. + */ +export async function registerRoutes(client: Client) { + const routesPath = join(resolve(), 'src', 'webhooks', 'routes'); + const routeFiles = fs.readdirSync(routesPath); + const WebhookRouter = new Hono(); + + const importedRoutes = ( + await Promise.all(routeFiles.map((file) => loadRoute(file, routesPath))) + ).flat(); + const dbRoutes = await prisma.webhookRoutes.findMany(); + + const routeSecrets: { [key: string]: string } = dbRoutes.reduce( + (acc, route) => ({ ...acc, [route.path]: route.secret || '' }), + {}, + ); + + importedRoutes.forEach((route) => { + route.secret = routeSecrets[route.path]; }); - const deletePromises = deletedRoutes.map((route) => { - logger.info(route, 'Deleting route'); - return route.destroy(); + + const registeredRoutes = await Promise.all( + importedRoutes.map((route) => registerRoute(route, client, WebhookRouter)), + ); + + const dbPaths = dbRoutes.map((route) => route.path); + const definedPaths = registeredRoutes.map((route) => route.path); + const pathsToRemove = dbPaths.filter((path) => !definedPaths.includes(path)); + + logger.info(pathsToRemove, 'Removing Webhook routes from database'); + await prisma.webhookRoutes.deleteMany({ + where: { + path: { + in: pathsToRemove, + }, + }, }); - await Promise.all(deletePromises); + + const groupedRoutes = groupRoutes(registeredRoutes); + const baseUrl = config.bot.base_url; + + const logInfo = Object.entries(groupedRoutes).flatMap(([path, methods]) => + Object.entries(methods).map(([method, { isProtected, secret }]) => ({ + method, + endpoint: `${baseUrl}/webhooks${path}?secret=${secret}&channelId=[channel_id]`, + isProtected, + })), + ); + + logger.info(logInfo, 'Registered routes'); + + return WebhookRouter; } +const M_Secret = (isProtected: boolean, secret: string | undefined) => { + return factory.createMiddleware(async (c: Context, next) => { + if (isProtected) { + const requestSecret = + c.req.query('secret') || c.req.header('x-webhook-secret'); + if (requestSecret !== secret) { + return c.json({ message: 'Unauthorized' }, 401); + } + } + await next(); + }); +}; + +const M_ValidateMethod = (method: string) => { + return factory.createMiddleware(async (c: Context, next) => { + if (!VALID_METHODS.includes(method as (typeof VALID_METHODS)[number])) { + return c.json({ message: 'Method not supported' }, 405); + } + if (c.req.method !== method.toUpperCase()) { + return c.json({ message: 'Method not allowed' }, 405); + } + await next(); + }); +}; + +const M_Discord = (client: Client) => { + return factory.createMiddleware(async (c: Context, next) => { + const channelId = c.req.query('channelId'); + if (!channelId) { + return c.json({ error: 'Missing channelId query parameter' }, 400); + } + + const channel = (await client.channels.fetch(channelId)) as TextChannel; + if (!channel) { + return c.json({ error: 'Invalid channel ID' }, 400); + } + + c.set('channel', channel); + c.set('client', client); + + await next(); + }); +}; + function groupRoutes(routes: Route[]) { return routes.reduce( (acc, route) => { @@ -168,65 +241,3 @@ function groupRoutes(routes: Route[]) { >, ); } - -export async function registerRoutes(client: Client) { - const routesPath = path.join( - path.resolve(), - runFromSrc ? 'src' : 'dist', - 'webhooks', - 'routes', - ); - const routeFiles = fs.readdirSync(routesPath); - - const importedRoutes = await Promise.all( - routeFiles.map((file) => importRoute(file, routesPath)), - ); - - const dbRoutes = await prisma.webhookRoutes.findMany(); - const routeSecrets = dbRoutes.reduce( - (acc, route) => { - acc[route.path] = route.secret || ''; - return acc; - }, - {} as Record, - ); - for (const route of importedRoutes.flat()) { - route.secret = routeSecrets[route.path]; - } - const currentRoutes = importedRoutes.flat(); - - await deleteRoutes(dbRoutes, currentRoutes); - - const routePromises = currentRoutes.map((route) => - registerRoute(route, client, router), - ); - const registeredRoutes = await Promise.all(routePromises); - - router.all('*', (req, res) => { - const matchedRoute = router.stack.find( - (route) => route.route.path === req.path, - ); - if (matchedRoute && !matchedRoute.route.methods[req.method.toLowerCase()]) { - res.status(405).send('Method Not Allowed'); - } else { - res.status(404).send('Not Found'); - } - }); - - const groupedRoutes = groupRoutes(registeredRoutes); - - const baseUrl = config.bot.base_url; - const logInfo = Object.entries(groupedRoutes).map(([path, methods]) => { - return Object.entries(methods).map(([method, { isProtected, secret }]) => { - return { - method, - endpoint: `${baseUrl}/webhooks${path}?secret=${secret}&channelId=[channel_id]`, - isProtected, - }; - }); - }); - - logger.info(logInfo, 'Registered routes'); - - return router; -} diff --git a/src/webhooks/routes/example.ts b/src/webhooks/routes/example.ts index 8220031..9caf562 100644 --- a/src/webhooks/routes/example.ts +++ b/src/webhooks/routes/example.ts @@ -1,17 +1,19 @@ /* eslint-disable @typescript-eslint/no-unused-vars */ -import type { Request, Response } from 'express'; +import type { Context, HonoRequest } from 'hono'; import type { Client } from '@/lib/module-loader'; export const path = '/example'; +export const isProtected = true; + export function get(client: Client) { - return function (req: Request, res: Response) { - res.send('Hello World'); + return function (c: Context) { + return c.text('Hello World'); }; } export function post(client: Client) { - return function (req: Request, res: Response) { - res.send('Hello World'); + return function (c: Context) { + return c.text('Hello World'); }; } diff --git a/src/webhooks/routes/generic.ts b/src/webhooks/routes/generic.ts index eb4b373..0810f8e 100644 --- a/src/webhooks/routes/generic.ts +++ b/src/webhooks/routes/generic.ts @@ -1,4 +1,4 @@ -import type { Request, Response } from 'express'; +import type { Context } from 'hono'; import type { Client } from '@/lib/module-loader'; import { Colors, EmbedBuilder, type TextChannel } from 'discord.js'; import { file as tmpFile } from 'tmp-promise'; @@ -11,26 +11,21 @@ export const path = '/generic'; export const isProtected = true; export function post(client: Client) { - return async function (req: Request, res: Response) { + return async function (c: Context) { try { - const channelId = req?.query?.channelId as string; - if (!channelId) { - res.status(400).send('Missing channelId query parameter'); - return; - } + const channelId = c.req.query('channelId'); - const channel = (await client.channels.fetch(channelId)) as TextChannel; + const channel = (await client.channels.fetch(channelId!)) as TextChannel; if (!channel) { - res.status(404).send('Channel not found'); - return; + return c.json({ error: 'Invalid channel ID' }, 400); } const tmp = await tmpFile({ postfix: '.json' }); const data = JSON.stringify( { - body: req.body, - headers: req.headers, + body: c.body, + headers: c.req.header, }, null, 2, @@ -51,10 +46,10 @@ export function post(client: Client) { await tmp.cleanup(); - res.send('OK'); + return c.json({ success: true }); } catch (error) { console.error(error); - res.status(500).send('An error occurred'); + return c.json({ error: 'An error occurred' }, 500); } }; } diff --git a/src/webhooks/routes/railway.ts b/src/webhooks/routes/railway.ts index 230ed83..d608ecd 100644 --- a/src/webhooks/routes/railway.ts +++ b/src/webhooks/routes/railway.ts @@ -1,10 +1,11 @@ -import type { Request, Response } from 'express'; +/* eslint-disable @typescript-eslint/no-unused-vars */ import type { Client } from '@/lib/module-loader'; -import { Colors, EmbedBuilder, type TextChannel, User } from 'discord.js'; +import { Colors, EmbedBuilder, type TextChannel } from 'discord.js'; +import { WebhookContext } from '..'; export const path = '/railway'; export const isProtected = true; export function post(client: Client) { - return async function (req: Request, res: Response) { + return async function (c: WebhookContext) { try { const { type, @@ -15,7 +16,7 @@ export function post(client: Client) { meta, service, status, - } = req.body; + } = await c.req.json(); if ( typeof type !== 'string' || @@ -24,8 +25,7 @@ export function post(client: Client) { typeof environment !== 'object' || typeof deployment !== 'object' ) { - res.status(400).send('Invalid request body'); - return; + return c.json({ error: 'Invalid request body' }, 400); } const embed = new EmbedBuilder() .setTitle('Railway Status') @@ -63,23 +63,13 @@ export function post(client: Client) { value: status, }, ); - const channelId = req.query.channelId as string | undefined; - if (!channelId) { - res.status(400).send('Missing channelId'); - return; - } - - const channel = (await client.channels.fetch(channelId)) as TextChannel; - if (!channel) { - res.status(404).send('Channel not found'); - return; - } + const channel = c.var.channel; channel.send({ embeds: [embed] }); - res.send('OK'); + return c.json({ success: true }); } catch (error) { console.error(error); - res.status(500).send('An error occurred'); + return c.json({ error: 'An error occurred' }, 500); } }; } diff --git a/src/webhooks/routes/uptimekuma.ts b/src/webhooks/routes/uptimekuma.ts index e21b753..8761ab8 100644 --- a/src/webhooks/routes/uptimekuma.ts +++ b/src/webhooks/routes/uptimekuma.ts @@ -1,13 +1,12 @@ -import type { Request, Response } from 'express'; import type { Client } from '@/lib/module-loader'; import { Colors, EmbedBuilder, - type TextChannel, GuildScheduledEventPrivacyLevel, GuildScheduledEventEntityType, } from 'discord.js'; import config from '@/config'; +import { WebhookContext } from '..'; export const path = '/uptimekuma'; export const isProtected = true; @@ -151,30 +150,22 @@ async function createUptimeEvent(client: Client, body: UptimeKumaPayload) { }); } export function post(client: Client) { - return async function (req: Request, res: Response) { + return async function (c: WebhookContext) { try { - const channelId = req?.query?.channelId as string; - if (!channelId) { - res.status(400).send('Missing channelId query parameter'); - return; - } - - const channel = (await client.channels.fetch(channelId)) as TextChannel; - if (!channel) { - res.status(404).send('Channel not found'); - return; - } + const channel = c.var.channel; + + const payload = (await c.req.json()) as UptimeKumaPayload; await channel.send({ - embeds: [createUptimeKumaEmbed(req.body)], + embeds: [createUptimeKumaEmbed(payload)], }); - await createUptimeEvent(client, req.body as UptimeKumaPayload); + await createUptimeEvent(client, payload); - res.send('OK'); + return c.json({ success: true }); } catch (error) { console.error(error); - res.status(500).send('An error occurred'); + return c.json({ error: 'An error occurred' }, 500); } }; }