From fbb486e69712fa6764cd4635a228b9fa8332636f Mon Sep 17 00:00:00 2001 From: "Gu://em_" Date: Mon, 12 May 2025 16:11:11 +0200 Subject: [PATCH] Added changes I forgot to commit --- .gitignore | 145 --- README.md | 4 +- config/config.json | 19 - frontend/.gitignore | 24 + frontend/index.html | 13 + frontend/package.json | 18 + frontend/pnpm-lock.yaml | 1188 ++++++++++++++++++++ frontend/pnpm-workspace.yaml | 2 + frontend/public/vite.svg | 1 + frontend/src/app.jsx | 43 + frontend/src/assets/preact.svg | 1 + frontend/src/main.jsx | 5 + frontend/src/styles/app.css | 25 + frontend/src/styles/index.css | 68 ++ frontend/vite.config.js | 7 + package.json | 35 - pnpm-lock.yaml | 1884 -------------------------------- server.js | 38 - src/controllers/auth.js | 17 - src/controllers/index.js | 14 - src/controllers/modpacks.js | 0 src/controllers/mods.js | 68 -- src/controllers/users.js | 63 -- src/database/index.js | 112 -- src/database/mysql.js | 30 - src/database/sqlite.js | 70 -- src/middleware/auth.js | 85 -- src/middleware/errors.js | 31 - src/models/index.js | 12 - src/models/mod.js | 192 ---- src/models/modpack.js | 0 src/models/user.js | 125 --- src/routes/index.js | 11 - src/routes/list.js | 24 - src/routes/login.js | 11 - src/routes/modpacks.js | 0 src/routes/mods.js | 27 - src/routes/users.js | 27 - src/schemas/auth.js | 21 - src/schemas/mod.js | 21 - src/schemas/modpack.js | 21 - src/schemas/user.js | 23 - src/services/authService.js | 85 -- src/services/indexService.js | 7 - src/services/modService.js | 164 --- src/services/modpackService.js | 0 src/services/userService.js | 46 - src/utils/appError.js | 27 - src/utils/configManager.js | 89 -- src/utils/convert.js | 11 - src/utils/crypto.js | 61 -- src/utils/sanitize.js | 19 - src/utils/validate.js | 51 - src/utils/validate_legacy.js | 98 -- 54 files changed, 1397 insertions(+), 3786 deletions(-) delete mode 100644 .gitignore delete mode 100644 config/config.json create mode 100644 frontend/.gitignore create mode 100644 frontend/index.html create mode 100644 frontend/package.json create mode 100644 frontend/pnpm-lock.yaml create mode 100644 frontend/pnpm-workspace.yaml create mode 100644 frontend/public/vite.svg create mode 100644 frontend/src/app.jsx create mode 100644 frontend/src/assets/preact.svg create mode 100644 frontend/src/main.jsx create mode 100644 frontend/src/styles/app.css create mode 100644 frontend/src/styles/index.css create mode 100644 frontend/vite.config.js delete mode 100644 package.json delete mode 100644 pnpm-lock.yaml delete mode 100644 server.js delete mode 100644 src/controllers/auth.js delete mode 100644 src/controllers/index.js delete mode 100644 src/controllers/modpacks.js delete mode 100644 src/controllers/mods.js delete mode 100644 src/controllers/users.js delete mode 100644 src/database/index.js delete mode 100644 src/database/mysql.js delete mode 100644 src/database/sqlite.js delete mode 100644 src/middleware/auth.js delete mode 100644 src/middleware/errors.js delete mode 100644 src/models/index.js delete mode 100644 src/models/mod.js delete mode 100644 src/models/modpack.js delete mode 100644 src/models/user.js delete mode 100644 src/routes/index.js delete mode 100644 src/routes/list.js delete mode 100644 src/routes/login.js delete mode 100644 src/routes/modpacks.js delete mode 100644 src/routes/mods.js delete mode 100644 src/routes/users.js delete mode 100644 src/schemas/auth.js delete mode 100644 src/schemas/mod.js delete mode 100644 src/schemas/modpack.js delete mode 100644 src/schemas/user.js delete mode 100644 src/services/authService.js delete mode 100644 src/services/indexService.js delete mode 100644 src/services/modService.js delete mode 100644 src/services/modpackService.js delete mode 100644 src/services/userService.js delete mode 100644 src/utils/appError.js delete mode 100644 src/utils/configManager.js delete mode 100644 src/utils/convert.js delete mode 100644 src/utils/crypto.js delete mode 100644 src/utils/sanitize.js delete mode 100644 src/utils/validate.js delete mode 100644 src/utils/validate_legacy.js diff --git a/.gitignore b/.gitignore deleted file mode 100644 index af33bdf..0000000 --- a/.gitignore +++ /dev/null @@ -1,145 +0,0 @@ -# Logs -logs -*.log -npm-debug.log* -yarn-debug.log* -yarn-error.log* -lerna-debug.log* -.pnpm-debug.log* - -# Diagnostic reports (https://nodejs.org/api/report.html) -report.[0-9]*.[0-9]*.[0-9]*.[0-9]*.json - -# Runtime data -pids -*.pid -*.seed -*.pid.lock - -# Directory for instrumented libs generated by jscoverage/JSCover -lib-cov - -# Coverage directory used by tools like istanbul -coverage -*.lcov - -# nyc test coverage -.nyc_output - -# Grunt intermediate storage (https://gruntjs.com/creating-plugins#storing-task-files) -.grunt - -# Bower dependency directory (https://bower.io/) -bower_components - -# node-waf configuration -.lock-wscript - -# Compiled binary addons (https://nodejs.org/api/addons.html) -build/Release - -# Dependency directories -node_modules/ -jspm_packages/ - -# Snowpack dependency directory (https://snowpack.dev/) -web_modules/ - -# TypeScript cache -*.tsbuildinfo - -# Optional npm cache directory -.npm - -# Optional eslint cache -.eslintcache - -# Optional stylelint cache -.stylelintcache - -# Microbundle cache -.rpt2_cache/ -.rts2_cache_cjs/ -.rts2_cache_es/ -.rts2_cache_umd/ - -# Optional REPL history -.node_repl_history - -# Output of 'npm pack' -*.tgz - -# Yarn Integrity file -.yarn-integrity - -# dotenv environment variable files -.env -.env.development.local -.env.test.local -.env.production.local -.env.local - -# parcel-bundler cache (https://parceljs.org/) -.cache -.parcel-cache - -# Next.js build output -.next -out - -# Nuxt.js build / generate output -.nuxt -dist - -# Gatsby files -.cache/ -# Comment in the public line in if your project uses Gatsby and not Next.js -# https://nextjs.org/blog/next-9-1#public-directory-support -# public - -# vuepress build output -.vuepress/dist - -# vuepress v2.x temp and cache directory -.temp -.cache - -# vitepress build output -**/.vitepress/dist - -# vitepress cache directory -**/.vitepress/cache - -# Docusaurus cache and generated files -.docusaurus - -# Serverless directories -.serverless/ - -# FuseBox cache -.fusebox/ - -# DynamoDB Local files -.dynamodb/ - -# TernJS port file -.tern-port - -# Stores VSCode versions used for testing VSCode extensions -.vscode-test - -# yarn v2 -.yarn/cache -.yarn/unplugged -.yarn/build-state.yml -.yarn/install-state.gz -.pnp.* - -# Vscode files -.vscode - -# Data -data/* - -# Temporary -tests/ \ No newline at end of file diff --git a/README.md b/README.md index 39629d9..f37f6ac 100644 --- a/README.md +++ b/README.md @@ -12,7 +12,7 @@ First make sure you have the following dependencies installed: - **Node.js** - **pnpm** -Then download all needed packages using +Then, for each of frontend and backend, download all needed packages using ```sh pnpm install ``` @@ -28,7 +28,7 @@ node server.js ## 🔧 Configuration -All settings are located in [config/config.json](config/config.json). For more explainations and possible values, give a look to the documentation (incomming). +All settings are located in [backend/config/config.json](backend/config/config.json). For more explainations and possible values, give a look to the documentation (incomming). ## 🔗 Documentation diff --git a/config/config.json b/config/config.json deleted file mode 100644 index a060d02..0000000 --- a/config/config.json +++ /dev/null @@ -1,19 +0,0 @@ -{ - "port": 8000, - - "users": { - "admin": { - "username": "admin", - "password": "admin" - } - }, - - "database": { - "type": "sqlite" - }, - - "auth": { - "JWT_secret": "HGF7654EGBNKJNBJH6754356788GJHGY", - "tokenExpiry": "1h" - } -} \ No newline at end of file diff --git a/frontend/.gitignore b/frontend/.gitignore new file mode 100644 index 0000000..a547bf3 --- /dev/null +++ b/frontend/.gitignore @@ -0,0 +1,24 @@ +# Logs +logs +*.log +npm-debug.log* +yarn-debug.log* +yarn-error.log* +pnpm-debug.log* +lerna-debug.log* + +node_modules +dist +dist-ssr +*.local + +# Editor directories and files +.vscode/* +!.vscode/extensions.json +.idea +.DS_Store +*.suo +*.ntvs* +*.njsproj +*.sln +*.sw? diff --git a/frontend/index.html b/frontend/index.html new file mode 100644 index 0000000..ae54c6f --- /dev/null +++ b/frontend/index.html @@ -0,0 +1,13 @@ + + + + + + + Vite + Preact + + +
+ + + diff --git a/frontend/package.json b/frontend/package.json new file mode 100644 index 0000000..18b808f --- /dev/null +++ b/frontend/package.json @@ -0,0 +1,18 @@ +{ + "name": "wf-radio-frontend", + "private": true, + "version": "0.0.0", + "type": "module", + "scripts": { + "dev": "vite", + "build": "vite build", + "preview": "vite preview" + }, + "dependencies": { + "preact": "^10.26.5" + }, + "devDependencies": { + "@preact/preset-vite": "^2.10.1", + "vite": "^6.3.5" + } +} diff --git a/frontend/pnpm-lock.yaml b/frontend/pnpm-lock.yaml new file mode 100644 index 0000000..891187e --- /dev/null +++ b/frontend/pnpm-lock.yaml @@ -0,0 +1,1188 @@ +lockfileVersion: '9.0' + +settings: + autoInstallPeers: true + excludeLinksFromLockfile: false + +importers: + + .: + dependencies: + preact: + specifier: ^10.26.5 + version: 10.26.6 + devDependencies: + '@preact/preset-vite': + specifier: ^2.10.1 + version: 2.10.1(@babel/core@7.27.1)(preact@10.26.6)(vite@6.3.5) + vite: + specifier: ^6.3.5 + version: 6.3.5 + +packages: + + '@ampproject/remapping@2.3.0': + resolution: {integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==} + engines: {node: '>=6.0.0'} + + '@babel/code-frame@7.27.1': + resolution: {integrity: sha512-cjQ7ZlQ0Mv3b47hABuTevyTuYN4i+loJKGeV9flcCgIK37cCXRh+L1bd3iBHlynerhQ7BhCkn2BPbQUL+rGqFg==} + engines: {node: '>=6.9.0'} + + '@babel/compat-data@7.27.2': + resolution: {integrity: sha512-TUtMJYRPyUb/9aU8f3K0mjmjf6M9N5Woshn2CS6nqJSeJtTtQcpLUXjGt9vbF8ZGff0El99sWkLgzwW3VXnxZQ==} + engines: {node: '>=6.9.0'} + + '@babel/core@7.27.1': + resolution: {integrity: sha512-IaaGWsQqfsQWVLqMn9OB92MNN7zukfVA4s7KKAI0KfrrDsZ0yhi5uV4baBuLuN7n3vsZpwP8asPPcVwApxvjBQ==} + engines: {node: '>=6.9.0'} + + '@babel/generator@7.27.1': + resolution: {integrity: sha512-UnJfnIpc/+JO0/+KRVQNGU+y5taA5vCbwN8+azkX6beii/ZF+enZJSOKo11ZSzGJjlNfJHfQtmQT8H+9TXPG2w==} + engines: {node: '>=6.9.0'} + + '@babel/helper-annotate-as-pure@7.27.1': + resolution: {integrity: sha512-WnuuDILl9oOBbKnb4L+DyODx7iC47XfzmNCpTttFsSp6hTG7XZxu60+4IO+2/hPfcGOoKbFiwoI/+zwARbNQow==} + engines: {node: '>=6.9.0'} + + '@babel/helper-compilation-targets@7.27.2': + resolution: {integrity: sha512-2+1thGUUWWjLTYTHZWK1n8Yga0ijBz1XAhUXcKy81rd5g6yh7hGqMp45v7cadSbEHc9G3OTv45SyneRN3ps4DQ==} + engines: {node: '>=6.9.0'} + + '@babel/helper-module-imports@7.27.1': + resolution: {integrity: sha512-0gSFWUPNXNopqtIPQvlD5WgXYI5GY2kP2cCvoT8kczjbfcfuIljTbcWrulD1CIPIX2gt1wghbDy08yE1p+/r3w==} + engines: {node: '>=6.9.0'} + + '@babel/helper-module-transforms@7.27.1': + resolution: {integrity: sha512-9yHn519/8KvTU5BjTVEEeIM3w9/2yXNKoD82JifINImhpKkARMJKPP59kLo+BafpdN5zgNeIcS4jsGDmd3l58g==} + engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0 + + '@babel/helper-plugin-utils@7.27.1': + resolution: {integrity: sha512-1gn1Up5YXka3YYAHGKpbideQ5Yjf1tDa9qYcgysz+cNCXukyLl6DjPXhD3VRwSb8c0J9tA4b2+rHEZtc6R0tlw==} + engines: {node: '>=6.9.0'} + + '@babel/helper-string-parser@7.27.1': + resolution: {integrity: sha512-qMlSxKbpRlAridDExk92nSobyDdpPijUq2DW6oDnUqd0iOGxmQjyqhMIihI9+zv4LPyZdRje2cavWPbCbWm3eA==} + engines: {node: '>=6.9.0'} + + '@babel/helper-validator-identifier@7.27.1': + resolution: {integrity: sha512-D2hP9eA+Sqx1kBZgzxZh0y1trbuU+JoDkiEwqhQ36nodYqJwyEIhPSdMNd7lOm/4io72luTPWH20Yda0xOuUow==} + engines: {node: '>=6.9.0'} + + '@babel/helper-validator-option@7.27.1': + resolution: {integrity: sha512-YvjJow9FxbhFFKDSuFnVCe2WxXk1zWc22fFePVNEaWJEu8IrZVlda6N0uHwzZrUM1il7NC9Mlp4MaJYbYd9JSg==} + engines: {node: '>=6.9.0'} + + '@babel/helpers@7.27.1': + resolution: {integrity: sha512-FCvFTm0sWV8Fxhpp2McP5/W53GPllQ9QeQ7SiqGWjMf/LVG07lFa5+pgK05IRhVwtvafT22KF+ZSnM9I545CvQ==} + engines: {node: '>=6.9.0'} + + '@babel/parser@7.27.2': + resolution: {integrity: sha512-QYLs8299NA7WM/bZAdp+CviYYkVoYXlDW2rzliy3chxd1PQjej7JORuMJDJXJUb9g0TT+B99EwaVLKmX+sPXWw==} + engines: {node: '>=6.0.0'} + hasBin: true + + '@babel/plugin-syntax-jsx@7.27.1': + resolution: {integrity: sha512-y8YTNIeKoyhGd9O0Jiyzyyqk8gdjnumGTQPsz0xOZOQ2RmkVJeZ1vmmfIvFEKqucBG6axJGBZDE/7iI5suUI/w==} + engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0-0 + + '@babel/plugin-transform-react-jsx-development@7.27.1': + resolution: {integrity: sha512-ykDdF5yI4f1WrAolLqeF3hmYU12j9ntLQl/AOG1HAS21jxyg1Q0/J/tpREuYLfatGdGmXp/3yS0ZA76kOlVq9Q==} + engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0-0 + + '@babel/plugin-transform-react-jsx@7.27.1': + resolution: {integrity: sha512-2KH4LWGSrJIkVf5tSiBFYuXDAoWRq2MMwgivCf+93dd0GQi8RXLjKA/0EvRnVV5G0hrHczsquXuD01L8s6dmBw==} + engines: {node: '>=6.9.0'} + peerDependencies: + '@babel/core': ^7.0.0-0 + + '@babel/template@7.27.2': + resolution: {integrity: sha512-LPDZ85aEJyYSd18/DkjNh4/y1ntkE5KwUHWTiqgRxruuZL2F1yuHligVHLvcHY2vMHXttKFpJn6LwfI7cw7ODw==} + engines: {node: '>=6.9.0'} + + '@babel/traverse@7.27.1': + resolution: {integrity: sha512-ZCYtZciz1IWJB4U61UPu4KEaqyfj+r5T1Q5mqPo+IBpcG9kHv30Z0aD8LXPgC1trYa6rK0orRyAhqUgk4MjmEg==} + engines: {node: '>=6.9.0'} + + '@babel/types@7.27.1': + resolution: {integrity: sha512-+EzkxvLNfiUeKMgy/3luqfsCWFRXLb7U6wNQTk60tovuckwB15B191tJWvpp4HjiQWdJkCxO3Wbvc6jlk3Xb2Q==} + engines: {node: '>=6.9.0'} + + '@esbuild/aix-ppc64@0.25.4': + resolution: {integrity: sha512-1VCICWypeQKhVbE9oW/sJaAmjLxhVqacdkvPLEjwlttjfwENRSClS8EjBz0KzRyFSCPDIkuXW34Je/vk7zdB7Q==} + engines: {node: '>=18'} + cpu: [ppc64] + os: [aix] + + '@esbuild/android-arm64@0.25.4': + resolution: {integrity: sha512-bBy69pgfhMGtCnwpC/x5QhfxAz/cBgQ9enbtwjf6V9lnPI/hMyT9iWpR1arm0l3kttTr4L0KSLpKmLp/ilKS9A==} + engines: {node: '>=18'} + cpu: [arm64] + os: [android] + + '@esbuild/android-arm@0.25.4': + resolution: {integrity: sha512-QNdQEps7DfFwE3hXiU4BZeOV68HHzYwGd0Nthhd3uCkkEKK7/R6MTgM0P7H7FAs5pU/DIWsviMmEGxEoxIZ+ZQ==} + engines: {node: '>=18'} + cpu: [arm] + os: [android] + + '@esbuild/android-x64@0.25.4': + resolution: {integrity: sha512-TVhdVtQIFuVpIIR282btcGC2oGQoSfZfmBdTip2anCaVYcqWlZXGcdcKIUklfX2wj0JklNYgz39OBqh2cqXvcQ==} + engines: {node: '>=18'} + cpu: [x64] + os: [android] + + '@esbuild/darwin-arm64@0.25.4': + resolution: {integrity: sha512-Y1giCfM4nlHDWEfSckMzeWNdQS31BQGs9/rouw6Ub91tkK79aIMTH3q9xHvzH8d0wDru5Ci0kWB8b3up/nl16g==} + engines: {node: '>=18'} + cpu: [arm64] + os: [darwin] + + '@esbuild/darwin-x64@0.25.4': + resolution: {integrity: sha512-CJsry8ZGM5VFVeyUYB3cdKpd/H69PYez4eJh1W/t38vzutdjEjtP7hB6eLKBoOdxcAlCtEYHzQ/PJ/oU9I4u0A==} + engines: {node: '>=18'} + cpu: [x64] + os: [darwin] + + '@esbuild/freebsd-arm64@0.25.4': + resolution: {integrity: sha512-yYq+39NlTRzU2XmoPW4l5Ifpl9fqSk0nAJYM/V/WUGPEFfek1epLHJIkTQM6bBs1swApjO5nWgvr843g6TjxuQ==} + engines: {node: '>=18'} + cpu: [arm64] + os: [freebsd] + + '@esbuild/freebsd-x64@0.25.4': + resolution: {integrity: sha512-0FgvOJ6UUMflsHSPLzdfDnnBBVoCDtBTVyn/MrWloUNvq/5SFmh13l3dvgRPkDihRxb77Y17MbqbCAa2strMQQ==} + engines: {node: '>=18'} + cpu: [x64] + os: [freebsd] + + '@esbuild/linux-arm64@0.25.4': + resolution: {integrity: sha512-+89UsQTfXdmjIvZS6nUnOOLoXnkUTB9hR5QAeLrQdzOSWZvNSAXAtcRDHWtqAUtAmv7ZM1WPOOeSxDzzzMogiQ==} + engines: {node: '>=18'} + cpu: [arm64] + os: [linux] + + '@esbuild/linux-arm@0.25.4': + resolution: {integrity: sha512-kro4c0P85GMfFYqW4TWOpvmF8rFShbWGnrLqlzp4X1TNWjRY3JMYUfDCtOxPKOIY8B0WC8HN51hGP4I4hz4AaQ==} + engines: {node: '>=18'} + cpu: [arm] + os: [linux] + + '@esbuild/linux-ia32@0.25.4': + resolution: {integrity: sha512-yTEjoapy8UP3rv8dB0ip3AfMpRbyhSN3+hY8mo/i4QXFeDxmiYbEKp3ZRjBKcOP862Ua4b1PDfwlvbuwY7hIGQ==} + engines: {node: '>=18'} + cpu: [ia32] + os: [linux] + + '@esbuild/linux-loong64@0.25.4': + resolution: {integrity: sha512-NeqqYkrcGzFwi6CGRGNMOjWGGSYOpqwCjS9fvaUlX5s3zwOtn1qwg1s2iE2svBe4Q/YOG1q6875lcAoQK/F4VA==} + engines: {node: '>=18'} + cpu: [loong64] + os: [linux] + + '@esbuild/linux-mips64el@0.25.4': + resolution: {integrity: sha512-IcvTlF9dtLrfL/M8WgNI/qJYBENP3ekgsHbYUIzEzq5XJzzVEV/fXY9WFPfEEXmu3ck2qJP8LG/p3Q8f7Zc2Xg==} + engines: {node: '>=18'} + cpu: [mips64el] + os: [linux] + + '@esbuild/linux-ppc64@0.25.4': + resolution: {integrity: sha512-HOy0aLTJTVtoTeGZh4HSXaO6M95qu4k5lJcH4gxv56iaycfz1S8GO/5Jh6X4Y1YiI0h7cRyLi+HixMR+88swag==} + engines: {node: '>=18'} + cpu: [ppc64] + os: [linux] + + '@esbuild/linux-riscv64@0.25.4': + resolution: {integrity: sha512-i8JUDAufpz9jOzo4yIShCTcXzS07vEgWzyX3NH2G7LEFVgrLEhjwL3ajFE4fZI3I4ZgiM7JH3GQ7ReObROvSUA==} + engines: {node: '>=18'} + cpu: [riscv64] + os: [linux] + + '@esbuild/linux-s390x@0.25.4': + resolution: {integrity: sha512-jFnu+6UbLlzIjPQpWCNh5QtrcNfMLjgIavnwPQAfoGx4q17ocOU9MsQ2QVvFxwQoWpZT8DvTLooTvmOQXkO51g==} + engines: {node: '>=18'} + cpu: [s390x] + os: [linux] + + '@esbuild/linux-x64@0.25.4': + resolution: {integrity: sha512-6e0cvXwzOnVWJHq+mskP8DNSrKBr1bULBvnFLpc1KY+d+irZSgZ02TGse5FsafKS5jg2e4pbvK6TPXaF/A6+CA==} + engines: {node: '>=18'} + cpu: [x64] + os: [linux] + + '@esbuild/netbsd-arm64@0.25.4': + resolution: {integrity: sha512-vUnkBYxZW4hL/ie91hSqaSNjulOnYXE1VSLusnvHg2u3jewJBz3YzB9+oCw8DABeVqZGg94t9tyZFoHma8gWZQ==} + engines: {node: '>=18'} + cpu: [arm64] + os: [netbsd] + + '@esbuild/netbsd-x64@0.25.4': + resolution: {integrity: sha512-XAg8pIQn5CzhOB8odIcAm42QsOfa98SBeKUdo4xa8OvX8LbMZqEtgeWE9P/Wxt7MlG2QqvjGths+nq48TrUiKw==} + engines: {node: '>=18'} + cpu: [x64] + os: [netbsd] + + '@esbuild/openbsd-arm64@0.25.4': + resolution: {integrity: sha512-Ct2WcFEANlFDtp1nVAXSNBPDxyU+j7+tId//iHXU2f/lN5AmO4zLyhDcpR5Cz1r08mVxzt3Jpyt4PmXQ1O6+7A==} + engines: {node: '>=18'} + cpu: [arm64] + os: [openbsd] + + '@esbuild/openbsd-x64@0.25.4': + resolution: {integrity: sha512-xAGGhyOQ9Otm1Xu8NT1ifGLnA6M3sJxZ6ixylb+vIUVzvvd6GOALpwQrYrtlPouMqd/vSbgehz6HaVk4+7Afhw==} + engines: {node: '>=18'} + cpu: [x64] + os: [openbsd] + + '@esbuild/sunos-x64@0.25.4': + resolution: {integrity: sha512-Mw+tzy4pp6wZEK0+Lwr76pWLjrtjmJyUB23tHKqEDP74R3q95luY/bXqXZeYl4NYlvwOqoRKlInQialgCKy67Q==} + engines: {node: '>=18'} + cpu: [x64] + os: [sunos] + + '@esbuild/win32-arm64@0.25.4': + resolution: {integrity: sha512-AVUP428VQTSddguz9dO9ngb+E5aScyg7nOeJDrF1HPYu555gmza3bDGMPhmVXL8svDSoqPCsCPjb265yG/kLKQ==} + engines: {node: '>=18'} + cpu: [arm64] + os: [win32] + + '@esbuild/win32-ia32@0.25.4': + resolution: {integrity: sha512-i1sW+1i+oWvQzSgfRcxxG2k4I9n3O9NRqy8U+uugaT2Dy7kLO9Y7wI72haOahxceMX8hZAzgGou1FhndRldxRg==} + engines: {node: '>=18'} + cpu: [ia32] + os: [win32] + + '@esbuild/win32-x64@0.25.4': + resolution: {integrity: sha512-nOT2vZNw6hJ+z43oP1SPea/G/6AbN6X+bGNhNuq8NtRHy4wsMhw765IKLNmnjek7GvjWBYQ8Q5VBoYTFg9y1UQ==} + engines: {node: '>=18'} + cpu: [x64] + os: [win32] + + '@jridgewell/gen-mapping@0.3.8': + resolution: {integrity: sha512-imAbBGkb+ebQyxKgzv5Hu2nmROxoDOXHh80evxdoXNOrvAnVx7zimzc1Oo5h9RlfV4vPXaE2iM5pOFbvOCClWA==} + engines: {node: '>=6.0.0'} + + '@jridgewell/resolve-uri@3.1.2': + resolution: {integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==} + engines: {node: '>=6.0.0'} + + '@jridgewell/set-array@1.2.1': + resolution: {integrity: sha512-R8gLRTZeyp03ymzP/6Lil/28tGeGEzhx1q2k703KGWRAI1VdvPIXdG70VJc2pAMw3NA6JKL5hhFu1sJX0Mnn/A==} + engines: {node: '>=6.0.0'} + + '@jridgewell/sourcemap-codec@1.5.0': + resolution: {integrity: sha512-gv3ZRaISU3fjPAgNsriBRqGWQL6quFx04YMPW/zD8XMLsU32mhCCbfbO6KZFLjvYpCZ8zyDEgqsgf+PwPaM7GQ==} + + '@jridgewell/trace-mapping@0.3.25': + resolution: {integrity: sha512-vNk6aEwybGtawWmy/PzwnGDOjCkLWSD2wqvjGGAgOAwCGWySYXfYoxt00IJkTF+8Lb57DwOb3Aa0o9CApepiYQ==} + + '@preact/preset-vite@2.10.1': + resolution: {integrity: sha512-59lyGBXNfZIr5OOuBUB4/IB8AqF/ULbvYnyItgK/2BJnsGJqaeaJobRVtMp1129obHQuj8oZ/dVxB9inmH8Xig==} + peerDependencies: + '@babel/core': 7.x + vite: 2.x || 3.x || 4.x || 5.x || 6.x + + '@prefresh/babel-plugin@0.5.1': + resolution: {integrity: sha512-uG3jGEAysxWoyG3XkYfjYHgaySFrSsaEb4GagLzYaxlydbuREtaX+FTxuIidp241RaLl85XoHg9Ej6E4+V1pcg==} + + '@prefresh/core@1.5.3': + resolution: {integrity: sha512-nDzxj0tA1/M6APNAWqaxkZ+3sTdPHESa+gol4+Bw7rMc2btWdkLoNH7j9rGhUb8SThC0Vz0VoXtq+U+9azGLHg==} + peerDependencies: + preact: ^10.0.0 + + '@prefresh/utils@1.2.0': + resolution: {integrity: sha512-KtC/fZw+oqtwOLUFM9UtiitB0JsVX0zLKNyRTA332sqREqSALIIQQxdUCS1P3xR/jT1e2e8/5rwH6gdcMLEmsQ==} + + '@prefresh/vite@2.4.7': + resolution: {integrity: sha512-zmCEDWSFHl5A7PciXa/fe+OUjoGi4iiCQclpWfpIg7LjxwWrtlUT4DfxDBcQwHfTyipS/XDm8x7WYrkiTW0q+w==} + peerDependencies: + preact: ^10.4.0 + vite: '>=2.0.0' + + '@rollup/pluginutils@4.2.1': + resolution: {integrity: sha512-iKnFXr7NkdZAIHiIWE+BX5ULi/ucVFYWD6TbAV+rZctiRTY2PL6tsIKhoIOaoskiWAkgu+VsbXgUVDNLHf+InQ==} + engines: {node: '>= 8.0.0'} + + '@rollup/rollup-android-arm-eabi@4.40.2': + resolution: {integrity: sha512-JkdNEq+DFxZfUwxvB58tHMHBHVgX23ew41g1OQinthJ+ryhdRk67O31S7sYw8u2lTjHUPFxwar07BBt1KHp/hg==} + cpu: [arm] + os: [android] + + '@rollup/rollup-android-arm64@4.40.2': + resolution: {integrity: sha512-13unNoZ8NzUmnndhPTkWPWbX3vtHodYmy+I9kuLxN+F+l+x3LdVF7UCu8TWVMt1POHLh6oDHhnOA04n8oJZhBw==} + cpu: [arm64] + os: [android] + + '@rollup/rollup-darwin-arm64@4.40.2': + resolution: {integrity: sha512-Gzf1Hn2Aoe8VZzevHostPX23U7N5+4D36WJNHK88NZHCJr7aVMG4fadqkIf72eqVPGjGc0HJHNuUaUcxiR+N/w==} + cpu: [arm64] + os: [darwin] + + '@rollup/rollup-darwin-x64@4.40.2': + resolution: {integrity: sha512-47N4hxa01a4x6XnJoskMKTS8XZ0CZMd8YTbINbi+w03A2w4j1RTlnGHOz/P0+Bg1LaVL6ufZyNprSg+fW5nYQQ==} + cpu: [x64] + os: [darwin] + + '@rollup/rollup-freebsd-arm64@4.40.2': + resolution: {integrity: sha512-8t6aL4MD+rXSHHZUR1z19+9OFJ2rl1wGKvckN47XFRVO+QL/dUSpKA2SLRo4vMg7ELA8pzGpC+W9OEd1Z/ZqoQ==} + cpu: [arm64] + os: [freebsd] + + '@rollup/rollup-freebsd-x64@4.40.2': + resolution: {integrity: sha512-C+AyHBzfpsOEYRFjztcYUFsH4S7UsE9cDtHCtma5BK8+ydOZYgMmWg1d/4KBytQspJCld8ZIujFMAdKG1xyr4Q==} + cpu: [x64] + os: [freebsd] + + '@rollup/rollup-linux-arm-gnueabihf@4.40.2': + resolution: {integrity: sha512-de6TFZYIvJwRNjmW3+gaXiZ2DaWL5D5yGmSYzkdzjBDS3W+B9JQ48oZEsmMvemqjtAFzE16DIBLqd6IQQRuG9Q==} + cpu: [arm] + os: [linux] + + '@rollup/rollup-linux-arm-musleabihf@4.40.2': + resolution: {integrity: sha512-urjaEZubdIkacKc930hUDOfQPysezKla/O9qV+O89enqsqUmQm8Xj8O/vh0gHg4LYfv7Y7UsE3QjzLQzDYN1qg==} + cpu: [arm] + os: [linux] + + '@rollup/rollup-linux-arm64-gnu@4.40.2': + resolution: {integrity: sha512-KlE8IC0HFOC33taNt1zR8qNlBYHj31qGT1UqWqtvR/+NuCVhfufAq9fxO8BMFC22Wu0rxOwGVWxtCMvZVLmhQg==} + cpu: [arm64] + os: [linux] + + '@rollup/rollup-linux-arm64-musl@4.40.2': + resolution: {integrity: sha512-j8CgxvfM0kbnhu4XgjnCWJQyyBOeBI1Zq91Z850aUddUmPeQvuAy6OiMdPS46gNFgy8gN1xkYyLgwLYZG3rBOg==} + cpu: [arm64] + os: [linux] + + '@rollup/rollup-linux-loongarch64-gnu@4.40.2': + resolution: {integrity: sha512-Ybc/1qUampKuRF4tQXc7G7QY9YRyeVSykfK36Y5Qc5dmrIxwFhrOzqaVTNoZygqZ1ZieSWTibfFhQ5qK8jpWxw==} + cpu: [loong64] + os: [linux] + + '@rollup/rollup-linux-powerpc64le-gnu@4.40.2': + resolution: {integrity: sha512-3FCIrnrt03CCsZqSYAOW/k9n625pjpuMzVfeI+ZBUSDT3MVIFDSPfSUgIl9FqUftxcUXInvFah79hE1c9abD+Q==} + cpu: [ppc64] + os: [linux] + + '@rollup/rollup-linux-riscv64-gnu@4.40.2': + resolution: {integrity: sha512-QNU7BFHEvHMp2ESSY3SozIkBPaPBDTsfVNGx3Xhv+TdvWXFGOSH2NJvhD1zKAT6AyuuErJgbdvaJhYVhVqrWTg==} + cpu: [riscv64] + os: [linux] + + '@rollup/rollup-linux-riscv64-musl@4.40.2': + resolution: {integrity: sha512-5W6vNYkhgfh7URiXTO1E9a0cy4fSgfE4+Hl5agb/U1sa0kjOLMLC1wObxwKxecE17j0URxuTrYZZME4/VH57Hg==} + cpu: [riscv64] + os: [linux] + + '@rollup/rollup-linux-s390x-gnu@4.40.2': + resolution: {integrity: sha512-B7LKIz+0+p348JoAL4X/YxGx9zOx3sR+o6Hj15Y3aaApNfAshK8+mWZEf759DXfRLeL2vg5LYJBB7DdcleYCoQ==} + cpu: [s390x] + os: [linux] + + '@rollup/rollup-linux-x64-gnu@4.40.2': + resolution: {integrity: sha512-lG7Xa+BmBNwpjmVUbmyKxdQJ3Q6whHjMjzQplOs5Z+Gj7mxPtWakGHqzMqNER68G67kmCX9qX57aRsW5V0VOng==} + cpu: [x64] + os: [linux] + + '@rollup/rollup-linux-x64-musl@4.40.2': + resolution: {integrity: sha512-tD46wKHd+KJvsmije4bUskNuvWKFcTOIM9tZ/RrmIvcXnbi0YK/cKS9FzFtAm7Oxi2EhV5N2OpfFB348vSQRXA==} + cpu: [x64] + os: [linux] + + '@rollup/rollup-win32-arm64-msvc@4.40.2': + resolution: {integrity: sha512-Bjv/HG8RRWLNkXwQQemdsWw4Mg+IJ29LK+bJPW2SCzPKOUaMmPEppQlu/Fqk1d7+DX3V7JbFdbkh/NMmurT6Pg==} + cpu: [arm64] + os: [win32] + + '@rollup/rollup-win32-ia32-msvc@4.40.2': + resolution: {integrity: sha512-dt1llVSGEsGKvzeIO76HToiYPNPYPkmjhMHhP00T9S4rDern8P2ZWvWAQUEJ+R1UdMWJ/42i/QqJ2WV765GZcA==} + cpu: [ia32] + os: [win32] + + '@rollup/rollup-win32-x64-msvc@4.40.2': + resolution: {integrity: sha512-bwspbWB04XJpeElvsp+DCylKfF4trJDa2Y9Go8O6A7YLX2LIKGcNK/CYImJN6ZP4DcuOHB4Utl3iCbnR62DudA==} + cpu: [x64] + os: [win32] + + '@types/estree@1.0.7': + resolution: {integrity: sha512-w28IoSUCJpidD/TGviZwwMJckNESJZXFu7NBZ5YJ4mEUnNraUn9Pm8HSZm/jDF1pDWYKspWE7oVphigUPRakIQ==} + + babel-plugin-transform-hook-names@1.0.2: + resolution: {integrity: sha512-5gafyjyyBTTdX/tQQ0hRgu4AhNHG/hqWi0ZZmg2xvs2FgRkJXzDNKBZCyoYqgFkovfDrgM8OoKg8karoUvWeCw==} + peerDependencies: + '@babel/core': ^7.12.10 + + boolbase@1.0.0: + resolution: {integrity: sha512-JZOSA7Mo9sNGB8+UjSgzdLtokWAky1zbztM3WRLCbZ70/3cTANmQmOdR7y2g+J0e2WXywy1yS468tY+IruqEww==} + + browserslist@4.24.5: + resolution: {integrity: sha512-FDToo4Wo82hIdgc1CQ+NQD0hEhmpPjrZ3hiUgwgOG6IuTdlpr8jdjyG24P6cNP1yJpTLzS5OcGgSw0xmDU1/Tw==} + engines: {node: ^6 || ^7 || ^8 || ^9 || ^10 || ^11 || ^12 || >=13.7} + hasBin: true + + caniuse-lite@1.0.30001717: + resolution: {integrity: sha512-auPpttCq6BDEG8ZAuHJIplGw6GODhjw+/11e7IjpnYCxZcW/ONgPs0KVBJ0d1bY3e2+7PRe5RCLyP+PfwVgkYw==} + + convert-source-map@2.0.0: + resolution: {integrity: sha512-Kvp459HrV2FEJ1CAsi1Ku+MY3kasH19TFykTz2xWmMeq6bk2NU3XXvfJ+Q61m0xktWwt+1HSYf3JZsTms3aRJg==} + + css-select@5.1.0: + resolution: {integrity: sha512-nwoRF1rvRRnnCqqY7updORDsuqKzqYJ28+oSMaJMMgOauh3fvwHqMS7EZpIPqK8GL+g9mKxF1vP/ZjSeNjEVHg==} + + css-what@6.1.0: + resolution: {integrity: sha512-HTUrgRJ7r4dsZKU6GjmpfRK1O76h97Z8MfS1G0FozR+oF2kG6Vfe8JE6zwrkbxigziPHinCJ+gCPjA9EaBDtRw==} + engines: {node: '>= 6'} + + debug@4.4.0: + resolution: {integrity: sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==} + engines: {node: '>=6.0'} + peerDependencies: + supports-color: '*' + peerDependenciesMeta: + supports-color: + optional: true + + dom-serializer@2.0.0: + resolution: {integrity: sha512-wIkAryiqt/nV5EQKqQpo3SToSOV9J0DnbJqwK7Wv/Trc92zIAYZ4FlMu+JPFW1DfGFt81ZTCGgDEabffXeLyJg==} + + domelementtype@2.3.0: + resolution: {integrity: sha512-OLETBj6w0OsagBwdXnPdN0cnMfF9opN69co+7ZrbfPGrdpPVNBUj02spi6B1N7wChLQiPn4CSH/zJvXw56gmHw==} + + domhandler@5.0.3: + resolution: {integrity: sha512-cgwlv/1iFQiFnU96XXgROh8xTeetsnJiDsTc7TYCLFd9+/WNkIqPTxiM/8pSd8VIrhXGTf1Ny1q1hquVqDJB5w==} + engines: {node: '>= 4'} + + domutils@3.2.2: + resolution: {integrity: sha512-6kZKyUajlDuqlHKVX1w7gyslj9MPIXzIFiz/rGu35uC1wMi+kMhQwGhl4lt9unC9Vb9INnY9Z3/ZA3+FhASLaw==} + + electron-to-chromium@1.5.151: + resolution: {integrity: sha512-Rl6uugut2l9sLojjS4H4SAr3A4IgACMLgpuEMPYCVcKydzfyPrn5absNRju38IhQOf/NwjJY8OGWjlteqYeBCA==} + + entities@4.5.0: + resolution: {integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==} + engines: {node: '>=0.12'} + + esbuild@0.25.4: + resolution: {integrity: sha512-8pgjLUcUjcgDg+2Q4NYXnPbo/vncAY4UmyaCm0jZevERqCHZIaWwdJHkf8XQtu4AxSKCdvrUbT0XUr1IdZzI8Q==} + engines: {node: '>=18'} + hasBin: true + + escalade@3.2.0: + resolution: {integrity: sha512-WUj2qlxaQtO4g6Pq5c29GTcWGDyd8itL8zTlipgECz3JesAiiOKotd8JU6otB3PACgG6xkJUyVhboMS+bje/jA==} + engines: {node: '>=6'} + + estree-walker@2.0.2: + resolution: {integrity: sha512-Rfkk/Mp/DL7JVje3u18FxFujQlTNR2q6QfMSMB7AvCBx91NGj/ba3kCfza0f6dVDbw7YlRf/nDrn7pQrCCyQ/w==} + + fdir@6.4.4: + resolution: {integrity: sha512-1NZP+GK4GfuAv3PqKvxQRDMjdSRZjnkq7KfhlNrCNNlZ0ygQFpebfrnfnq/W7fpUnAv9aGWmY1zKx7FYL3gwhg==} + peerDependencies: + picomatch: ^3 || ^4 + peerDependenciesMeta: + picomatch: + optional: true + + fsevents@2.3.3: + resolution: {integrity: sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==} + engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} + os: [darwin] + + gensync@1.0.0-beta.2: + resolution: {integrity: sha512-3hN7NaskYvMDLQY55gnW3NQ+mesEAepTqlg+VEbj7zzqEMBVNhzcGYYeqFo/TlYz6eQiFcp1HcsCZO+nGgS8zg==} + engines: {node: '>=6.9.0'} + + globals@11.12.0: + resolution: {integrity: sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==} + engines: {node: '>=4'} + + he@1.2.0: + resolution: {integrity: sha512-F/1DnUGPopORZi0ni+CvrCgHQ5FyEAHRLSApuYWMmrbSwoN2Mn/7k+Gl38gJnR7yyDZk6WLXwiGod1JOWNDKGw==} + hasBin: true + + js-tokens@4.0.0: + resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==} + + jsesc@3.1.0: + resolution: {integrity: sha512-/sM3dO2FOzXjKQhJuo0Q173wf2KOo8t4I8vHy6lF9poUp7bKT0/NHE8fPX23PwfhnykfqnC2xRxOnVw5XuGIaA==} + engines: {node: '>=6'} + hasBin: true + + json5@2.2.3: + resolution: {integrity: sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==} + engines: {node: '>=6'} + hasBin: true + + kolorist@1.8.0: + resolution: {integrity: sha512-Y+60/zizpJ3HRH8DCss+q95yr6145JXZo46OTpFvDZWLfRCE4qChOyk1b26nMaNpfHHgxagk9dXT5OP0Tfe+dQ==} + + lru-cache@5.1.1: + resolution: {integrity: sha512-KpNARQA3Iwv+jTA0utUVVbrh+Jlrr1Fv0e56GGzAFOXN7dk/FviaDW8LHmK52DlcH4WP2n6gI8vN1aesBFgo9w==} + + magic-string@0.30.17: + resolution: {integrity: sha512-sNPKHvyjVf7gyjwS4xGTaW/mCnF8wnjtifKBEhxfZ7E/S8tQ0rssrwGNn6q8JH/ohItJfSQp9mBtQYuTlH5QnA==} + + ms@2.1.3: + resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} + + nanoid@3.3.11: + resolution: {integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==} + engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1} + hasBin: true + + node-html-parser@6.1.13: + resolution: {integrity: sha512-qIsTMOY4C/dAa5Q5vsobRpOOvPfC4pB61UVW2uSwZNUp0QU/jCekTal1vMmbO0DgdHeLUJpv/ARmDqErVxA3Sg==} + + node-releases@2.0.19: + resolution: {integrity: sha512-xxOWJsBKtzAq7DY0J+DTzuz58K8e7sJbdgwkbMWQe8UYB6ekmsQ45q0M/tJDsGaZmbC+l7n57UV8Hl5tHxO9uw==} + + nth-check@2.1.1: + resolution: {integrity: sha512-lqjrjmaOoAnWfMmBPL+XNnynZh2+swxiX3WUE0s4yEHI6m+AwrK2UZOimIRl3X/4QctVqS8AiZjFqyOGrMXb/w==} + + picocolors@1.1.1: + resolution: {integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==} + + picomatch@2.3.1: + resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} + engines: {node: '>=8.6'} + + picomatch@4.0.2: + resolution: {integrity: sha512-M7BAV6Rlcy5u+m6oPhAPFgJTzAioX/6B0DxyvDlo9l8+T3nLKbrczg2WLUyzd45L8RqfUMyGPzekbMvX2Ldkwg==} + engines: {node: '>=12'} + + postcss@8.5.3: + resolution: {integrity: sha512-dle9A3yYxlBSrt8Fu+IpjGT8SY8hN0mlaA6GY8t0P5PjIOZemULz/E2Bnm/2dcUOena75OTNkHI76uZBNUUq3A==} + engines: {node: ^10 || ^12 || >=14} + + preact@10.26.6: + resolution: {integrity: sha512-5SRRBinwpwkaD+OqlBDeITlRgvd8I8QlxHJw9AxSdMNV6O+LodN9nUyYGpSF7sadHjs6RzeFShMexC6DbtWr9g==} + + rollup@4.40.2: + resolution: {integrity: sha512-tfUOg6DTP4rhQ3VjOO6B4wyrJnGOX85requAXvqYTHsOgb2TFJdZ3aWpT8W2kPoypSGP7dZUyzxJ9ee4buM5Fg==} + engines: {node: '>=18.0.0', npm: '>=8.0.0'} + hasBin: true + + semver@6.3.1: + resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} + hasBin: true + + simple-code-frame@1.3.0: + resolution: {integrity: sha512-MB4pQmETUBlNs62BBeRjIFGeuy/x6gGKh7+eRUemn1rCFhqo7K+4slPqsyizCbcbYLnaYqaoZ2FWsZ/jN06D8w==} + + source-map-js@1.2.1: + resolution: {integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==} + engines: {node: '>=0.10.0'} + + source-map@0.7.4: + resolution: {integrity: sha512-l3BikUxvPOcn5E74dZiq5BGsTb5yEwhaTSzccU6t4sDOH8NWJCstKO5QT2CvtFoK6F0saL7p9xHAqHOlCPJygA==} + engines: {node: '>= 8'} + + stack-trace@1.0.0-pre2: + resolution: {integrity: sha512-2ztBJRek8IVofG9DBJqdy2N5kulaacX30Nz7xmkYF6ale9WBVmIy6mFBchvGX7Vx/MyjBhx+Rcxqrj+dbOnQ6A==} + engines: {node: '>=16'} + + tinyglobby@0.2.13: + resolution: {integrity: sha512-mEwzpUgrLySlveBwEVDMKk5B57bhLPYovRfPAXD5gA/98Opn0rCDj3GtLwFvCvH5RK9uPCExUROW5NjDwvqkxw==} + engines: {node: '>=12.0.0'} + + update-browserslist-db@1.1.3: + resolution: {integrity: sha512-UxhIZQ+QInVdunkDAaiazvvT/+fXL5Osr0JZlJulepYu6Jd7qJtDZjlur0emRlT71EN3ScPoE7gvsuIKKNavKw==} + hasBin: true + peerDependencies: + browserslist: '>= 4.21.0' + + vite-prerender-plugin@0.5.10: + resolution: {integrity: sha512-m4i0G5oc3LPLA02uW2XsFZmYNxZdyryz5Ksi78O9puj/ao5c8dBUW06caGwoM1TmYknTBBUyKhtqajUpoP+z8Q==} + peerDependencies: + vite: 5.x || 6.x + + vite@6.3.5: + resolution: {integrity: sha512-cZn6NDFE7wdTpINgs++ZJ4N49W2vRp8LCKrn3Ob1kYNtOo21vfDoaV5GzBfLU4MovSAB8uNRm4jgzVQZ+mBzPQ==} + engines: {node: ^18.0.0 || ^20.0.0 || >=22.0.0} + hasBin: true + peerDependencies: + '@types/node': ^18.0.0 || ^20.0.0 || >=22.0.0 + jiti: '>=1.21.0' + less: '*' + lightningcss: ^1.21.0 + sass: '*' + sass-embedded: '*' + stylus: '*' + sugarss: '*' + terser: ^5.16.0 + tsx: ^4.8.1 + yaml: ^2.4.2 + peerDependenciesMeta: + '@types/node': + optional: true + jiti: + optional: true + less: + optional: true + lightningcss: + optional: true + sass: + optional: true + sass-embedded: + optional: true + stylus: + optional: true + sugarss: + optional: true + terser: + optional: true + tsx: + optional: true + yaml: + optional: true + + yallist@3.1.1: + resolution: {integrity: sha512-a4UGQaWPH59mOXUYnAG2ewncQS4i4F43Tv3JoAM+s2VDAmS9NsK8GpDMLrCHPksFT7h3K6TOoUNn2pb7RoXx4g==} + +snapshots: + + '@ampproject/remapping@2.3.0': + dependencies: + '@jridgewell/gen-mapping': 0.3.8 + '@jridgewell/trace-mapping': 0.3.25 + + '@babel/code-frame@7.27.1': + dependencies: + '@babel/helper-validator-identifier': 7.27.1 + js-tokens: 4.0.0 + picocolors: 1.1.1 + + '@babel/compat-data@7.27.2': {} + + '@babel/core@7.27.1': + dependencies: + '@ampproject/remapping': 2.3.0 + '@babel/code-frame': 7.27.1 + '@babel/generator': 7.27.1 + '@babel/helper-compilation-targets': 7.27.2 + '@babel/helper-module-transforms': 7.27.1(@babel/core@7.27.1) + '@babel/helpers': 7.27.1 + '@babel/parser': 7.27.2 + '@babel/template': 7.27.2 + '@babel/traverse': 7.27.1 + '@babel/types': 7.27.1 + convert-source-map: 2.0.0 + debug: 4.4.0 + gensync: 1.0.0-beta.2 + json5: 2.2.3 + semver: 6.3.1 + transitivePeerDependencies: + - supports-color + + '@babel/generator@7.27.1': + dependencies: + '@babel/parser': 7.27.2 + '@babel/types': 7.27.1 + '@jridgewell/gen-mapping': 0.3.8 + '@jridgewell/trace-mapping': 0.3.25 + jsesc: 3.1.0 + + '@babel/helper-annotate-as-pure@7.27.1': + dependencies: + '@babel/types': 7.27.1 + + '@babel/helper-compilation-targets@7.27.2': + dependencies: + '@babel/compat-data': 7.27.2 + '@babel/helper-validator-option': 7.27.1 + browserslist: 4.24.5 + lru-cache: 5.1.1 + semver: 6.3.1 + + '@babel/helper-module-imports@7.27.1': + dependencies: + '@babel/traverse': 7.27.1 + '@babel/types': 7.27.1 + transitivePeerDependencies: + - supports-color + + '@babel/helper-module-transforms@7.27.1(@babel/core@7.27.1)': + dependencies: + '@babel/core': 7.27.1 + '@babel/helper-module-imports': 7.27.1 + '@babel/helper-validator-identifier': 7.27.1 + '@babel/traverse': 7.27.1 + transitivePeerDependencies: + - supports-color + + '@babel/helper-plugin-utils@7.27.1': {} + + '@babel/helper-string-parser@7.27.1': {} + + '@babel/helper-validator-identifier@7.27.1': {} + + '@babel/helper-validator-option@7.27.1': {} + + '@babel/helpers@7.27.1': + dependencies: + '@babel/template': 7.27.2 + '@babel/types': 7.27.1 + + '@babel/parser@7.27.2': + dependencies: + '@babel/types': 7.27.1 + + '@babel/plugin-syntax-jsx@7.27.1(@babel/core@7.27.1)': + dependencies: + '@babel/core': 7.27.1 + '@babel/helper-plugin-utils': 7.27.1 + + '@babel/plugin-transform-react-jsx-development@7.27.1(@babel/core@7.27.1)': + dependencies: + '@babel/core': 7.27.1 + '@babel/plugin-transform-react-jsx': 7.27.1(@babel/core@7.27.1) + transitivePeerDependencies: + - supports-color + + '@babel/plugin-transform-react-jsx@7.27.1(@babel/core@7.27.1)': + dependencies: + '@babel/core': 7.27.1 + '@babel/helper-annotate-as-pure': 7.27.1 + '@babel/helper-module-imports': 7.27.1 + '@babel/helper-plugin-utils': 7.27.1 + '@babel/plugin-syntax-jsx': 7.27.1(@babel/core@7.27.1) + '@babel/types': 7.27.1 + transitivePeerDependencies: + - supports-color + + '@babel/template@7.27.2': + dependencies: + '@babel/code-frame': 7.27.1 + '@babel/parser': 7.27.2 + '@babel/types': 7.27.1 + + '@babel/traverse@7.27.1': + dependencies: + '@babel/code-frame': 7.27.1 + '@babel/generator': 7.27.1 + '@babel/parser': 7.27.2 + '@babel/template': 7.27.2 + '@babel/types': 7.27.1 + debug: 4.4.0 + globals: 11.12.0 + transitivePeerDependencies: + - supports-color + + '@babel/types@7.27.1': + dependencies: + '@babel/helper-string-parser': 7.27.1 + '@babel/helper-validator-identifier': 7.27.1 + + '@esbuild/aix-ppc64@0.25.4': + optional: true + + '@esbuild/android-arm64@0.25.4': + optional: true + + '@esbuild/android-arm@0.25.4': + optional: true + + '@esbuild/android-x64@0.25.4': + optional: true + + '@esbuild/darwin-arm64@0.25.4': + optional: true + + '@esbuild/darwin-x64@0.25.4': + optional: true + + '@esbuild/freebsd-arm64@0.25.4': + optional: true + + '@esbuild/freebsd-x64@0.25.4': + optional: true + + '@esbuild/linux-arm64@0.25.4': + optional: true + + '@esbuild/linux-arm@0.25.4': + optional: true + + '@esbuild/linux-ia32@0.25.4': + optional: true + + '@esbuild/linux-loong64@0.25.4': + optional: true + + '@esbuild/linux-mips64el@0.25.4': + optional: true + + '@esbuild/linux-ppc64@0.25.4': + optional: true + + '@esbuild/linux-riscv64@0.25.4': + optional: true + + '@esbuild/linux-s390x@0.25.4': + optional: true + + '@esbuild/linux-x64@0.25.4': + optional: true + + '@esbuild/netbsd-arm64@0.25.4': + optional: true + + '@esbuild/netbsd-x64@0.25.4': + optional: true + + '@esbuild/openbsd-arm64@0.25.4': + optional: true + + '@esbuild/openbsd-x64@0.25.4': + optional: true + + '@esbuild/sunos-x64@0.25.4': + optional: true + + '@esbuild/win32-arm64@0.25.4': + optional: true + + '@esbuild/win32-ia32@0.25.4': + optional: true + + '@esbuild/win32-x64@0.25.4': + optional: true + + '@jridgewell/gen-mapping@0.3.8': + dependencies: + '@jridgewell/set-array': 1.2.1 + '@jridgewell/sourcemap-codec': 1.5.0 + '@jridgewell/trace-mapping': 0.3.25 + + '@jridgewell/resolve-uri@3.1.2': {} + + '@jridgewell/set-array@1.2.1': {} + + '@jridgewell/sourcemap-codec@1.5.0': {} + + '@jridgewell/trace-mapping@0.3.25': + dependencies: + '@jridgewell/resolve-uri': 3.1.2 + '@jridgewell/sourcemap-codec': 1.5.0 + + '@preact/preset-vite@2.10.1(@babel/core@7.27.1)(preact@10.26.6)(vite@6.3.5)': + dependencies: + '@babel/core': 7.27.1 + '@babel/plugin-transform-react-jsx': 7.27.1(@babel/core@7.27.1) + '@babel/plugin-transform-react-jsx-development': 7.27.1(@babel/core@7.27.1) + '@prefresh/vite': 2.4.7(preact@10.26.6)(vite@6.3.5) + '@rollup/pluginutils': 4.2.1 + babel-plugin-transform-hook-names: 1.0.2(@babel/core@7.27.1) + debug: 4.4.0 + kolorist: 1.8.0 + vite: 6.3.5 + vite-prerender-plugin: 0.5.10(vite@6.3.5) + transitivePeerDependencies: + - preact + - supports-color + + '@prefresh/babel-plugin@0.5.1': {} + + '@prefresh/core@1.5.3(preact@10.26.6)': + dependencies: + preact: 10.26.6 + + '@prefresh/utils@1.2.0': {} + + '@prefresh/vite@2.4.7(preact@10.26.6)(vite@6.3.5)': + dependencies: + '@babel/core': 7.27.1 + '@prefresh/babel-plugin': 0.5.1 + '@prefresh/core': 1.5.3(preact@10.26.6) + '@prefresh/utils': 1.2.0 + '@rollup/pluginutils': 4.2.1 + preact: 10.26.6 + vite: 6.3.5 + transitivePeerDependencies: + - supports-color + + '@rollup/pluginutils@4.2.1': + dependencies: + estree-walker: 2.0.2 + picomatch: 2.3.1 + + '@rollup/rollup-android-arm-eabi@4.40.2': + optional: true + + '@rollup/rollup-android-arm64@4.40.2': + optional: true + + '@rollup/rollup-darwin-arm64@4.40.2': + optional: true + + '@rollup/rollup-darwin-x64@4.40.2': + optional: true + + '@rollup/rollup-freebsd-arm64@4.40.2': + optional: true + + '@rollup/rollup-freebsd-x64@4.40.2': + optional: true + + '@rollup/rollup-linux-arm-gnueabihf@4.40.2': + optional: true + + '@rollup/rollup-linux-arm-musleabihf@4.40.2': + optional: true + + '@rollup/rollup-linux-arm64-gnu@4.40.2': + optional: true + + '@rollup/rollup-linux-arm64-musl@4.40.2': + optional: true + + '@rollup/rollup-linux-loongarch64-gnu@4.40.2': + optional: true + + '@rollup/rollup-linux-powerpc64le-gnu@4.40.2': + optional: true + + '@rollup/rollup-linux-riscv64-gnu@4.40.2': + optional: true + + '@rollup/rollup-linux-riscv64-musl@4.40.2': + optional: true + + '@rollup/rollup-linux-s390x-gnu@4.40.2': + optional: true + + '@rollup/rollup-linux-x64-gnu@4.40.2': + optional: true + + '@rollup/rollup-linux-x64-musl@4.40.2': + optional: true + + '@rollup/rollup-win32-arm64-msvc@4.40.2': + optional: true + + '@rollup/rollup-win32-ia32-msvc@4.40.2': + optional: true + + '@rollup/rollup-win32-x64-msvc@4.40.2': + optional: true + + '@types/estree@1.0.7': {} + + babel-plugin-transform-hook-names@1.0.2(@babel/core@7.27.1): + dependencies: + '@babel/core': 7.27.1 + + boolbase@1.0.0: {} + + browserslist@4.24.5: + dependencies: + caniuse-lite: 1.0.30001717 + electron-to-chromium: 1.5.151 + node-releases: 2.0.19 + update-browserslist-db: 1.1.3(browserslist@4.24.5) + + caniuse-lite@1.0.30001717: {} + + convert-source-map@2.0.0: {} + + css-select@5.1.0: + dependencies: + boolbase: 1.0.0 + css-what: 6.1.0 + domhandler: 5.0.3 + domutils: 3.2.2 + nth-check: 2.1.1 + + css-what@6.1.0: {} + + debug@4.4.0: + dependencies: + ms: 2.1.3 + + dom-serializer@2.0.0: + dependencies: + domelementtype: 2.3.0 + domhandler: 5.0.3 + entities: 4.5.0 + + domelementtype@2.3.0: {} + + domhandler@5.0.3: + dependencies: + domelementtype: 2.3.0 + + domutils@3.2.2: + dependencies: + dom-serializer: 2.0.0 + domelementtype: 2.3.0 + domhandler: 5.0.3 + + electron-to-chromium@1.5.151: {} + + entities@4.5.0: {} + + esbuild@0.25.4: + optionalDependencies: + '@esbuild/aix-ppc64': 0.25.4 + '@esbuild/android-arm': 0.25.4 + '@esbuild/android-arm64': 0.25.4 + '@esbuild/android-x64': 0.25.4 + '@esbuild/darwin-arm64': 0.25.4 + '@esbuild/darwin-x64': 0.25.4 + '@esbuild/freebsd-arm64': 0.25.4 + '@esbuild/freebsd-x64': 0.25.4 + '@esbuild/linux-arm': 0.25.4 + '@esbuild/linux-arm64': 0.25.4 + '@esbuild/linux-ia32': 0.25.4 + '@esbuild/linux-loong64': 0.25.4 + '@esbuild/linux-mips64el': 0.25.4 + '@esbuild/linux-ppc64': 0.25.4 + '@esbuild/linux-riscv64': 0.25.4 + '@esbuild/linux-s390x': 0.25.4 + '@esbuild/linux-x64': 0.25.4 + '@esbuild/netbsd-arm64': 0.25.4 + '@esbuild/netbsd-x64': 0.25.4 + '@esbuild/openbsd-arm64': 0.25.4 + '@esbuild/openbsd-x64': 0.25.4 + '@esbuild/sunos-x64': 0.25.4 + '@esbuild/win32-arm64': 0.25.4 + '@esbuild/win32-ia32': 0.25.4 + '@esbuild/win32-x64': 0.25.4 + + escalade@3.2.0: {} + + estree-walker@2.0.2: {} + + fdir@6.4.4(picomatch@4.0.2): + optionalDependencies: + picomatch: 4.0.2 + + fsevents@2.3.3: + optional: true + + gensync@1.0.0-beta.2: {} + + globals@11.12.0: {} + + he@1.2.0: {} + + js-tokens@4.0.0: {} + + jsesc@3.1.0: {} + + json5@2.2.3: {} + + kolorist@1.8.0: {} + + lru-cache@5.1.1: + dependencies: + yallist: 3.1.1 + + magic-string@0.30.17: + dependencies: + '@jridgewell/sourcemap-codec': 1.5.0 + + ms@2.1.3: {} + + nanoid@3.3.11: {} + + node-html-parser@6.1.13: + dependencies: + css-select: 5.1.0 + he: 1.2.0 + + node-releases@2.0.19: {} + + nth-check@2.1.1: + dependencies: + boolbase: 1.0.0 + + picocolors@1.1.1: {} + + picomatch@2.3.1: {} + + picomatch@4.0.2: {} + + postcss@8.5.3: + dependencies: + nanoid: 3.3.11 + picocolors: 1.1.1 + source-map-js: 1.2.1 + + preact@10.26.6: {} + + rollup@4.40.2: + dependencies: + '@types/estree': 1.0.7 + optionalDependencies: + '@rollup/rollup-android-arm-eabi': 4.40.2 + '@rollup/rollup-android-arm64': 4.40.2 + '@rollup/rollup-darwin-arm64': 4.40.2 + '@rollup/rollup-darwin-x64': 4.40.2 + '@rollup/rollup-freebsd-arm64': 4.40.2 + '@rollup/rollup-freebsd-x64': 4.40.2 + '@rollup/rollup-linux-arm-gnueabihf': 4.40.2 + '@rollup/rollup-linux-arm-musleabihf': 4.40.2 + '@rollup/rollup-linux-arm64-gnu': 4.40.2 + '@rollup/rollup-linux-arm64-musl': 4.40.2 + '@rollup/rollup-linux-loongarch64-gnu': 4.40.2 + '@rollup/rollup-linux-powerpc64le-gnu': 4.40.2 + '@rollup/rollup-linux-riscv64-gnu': 4.40.2 + '@rollup/rollup-linux-riscv64-musl': 4.40.2 + '@rollup/rollup-linux-s390x-gnu': 4.40.2 + '@rollup/rollup-linux-x64-gnu': 4.40.2 + '@rollup/rollup-linux-x64-musl': 4.40.2 + '@rollup/rollup-win32-arm64-msvc': 4.40.2 + '@rollup/rollup-win32-ia32-msvc': 4.40.2 + '@rollup/rollup-win32-x64-msvc': 4.40.2 + fsevents: 2.3.3 + + semver@6.3.1: {} + + simple-code-frame@1.3.0: + dependencies: + kolorist: 1.8.0 + + source-map-js@1.2.1: {} + + source-map@0.7.4: {} + + stack-trace@1.0.0-pre2: {} + + tinyglobby@0.2.13: + dependencies: + fdir: 6.4.4(picomatch@4.0.2) + picomatch: 4.0.2 + + update-browserslist-db@1.1.3(browserslist@4.24.5): + dependencies: + browserslist: 4.24.5 + escalade: 3.2.0 + picocolors: 1.1.1 + + vite-prerender-plugin@0.5.10(vite@6.3.5): + dependencies: + kolorist: 1.8.0 + magic-string: 0.30.17 + node-html-parser: 6.1.13 + simple-code-frame: 1.3.0 + source-map: 0.7.4 + stack-trace: 1.0.0-pre2 + vite: 6.3.5 + + vite@6.3.5: + dependencies: + esbuild: 0.25.4 + fdir: 6.4.4(picomatch@4.0.2) + picomatch: 4.0.2 + postcss: 8.5.3 + rollup: 4.40.2 + tinyglobby: 0.2.13 + optionalDependencies: + fsevents: 2.3.3 + + yallist@3.1.1: {} diff --git a/frontend/pnpm-workspace.yaml b/frontend/pnpm-workspace.yaml new file mode 100644 index 0000000..efc037a --- /dev/null +++ b/frontend/pnpm-workspace.yaml @@ -0,0 +1,2 @@ +onlyBuiltDependencies: + - esbuild diff --git a/frontend/public/vite.svg b/frontend/public/vite.svg new file mode 100644 index 0000000..e7b8dfb --- /dev/null +++ b/frontend/public/vite.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/frontend/src/app.jsx b/frontend/src/app.jsx new file mode 100644 index 0000000..9efff17 --- /dev/null +++ b/frontend/src/app.jsx @@ -0,0 +1,43 @@ +import { useState } from 'preact/hooks' +import preactLogo from './assets/preact.svg' +import viteLogo from '/vite.svg' +import './styles/app.css' + +export function App() { + const [count, setCount] = useState(0) + + return ( + <> +
+ + + + + + +
+

Vite + Preact

+
+ +

+ Edit src/app.jsx and save to test HMR +

+
+

+ Check out{' '} + + create-preact + + , the official Preact + Vite starter +

+

+ Click on the Vite and Preact logos to learn more +

+ + ) +} diff --git a/frontend/src/assets/preact.svg b/frontend/src/assets/preact.svg new file mode 100644 index 0000000..908f17d --- /dev/null +++ b/frontend/src/assets/preact.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/frontend/src/main.jsx b/frontend/src/main.jsx new file mode 100644 index 0000000..008c962 --- /dev/null +++ b/frontend/src/main.jsx @@ -0,0 +1,5 @@ +import { render } from 'preact' +import './styles/index.css' +import { App } from './app.jsx' + +render(, document.getElementById('app')) diff --git a/frontend/src/styles/app.css b/frontend/src/styles/app.css new file mode 100644 index 0000000..088ed3a --- /dev/null +++ b/frontend/src/styles/app.css @@ -0,0 +1,25 @@ +#app { + max-width: 1280px; + margin: 0 auto; + padding: 2rem; + text-align: center; +} + +.logo { + height: 6em; + padding: 1.5em; +} +.logo:hover { + filter: drop-shadow(0 0 2em #646cffaa); +} +.logo.preact:hover { + filter: drop-shadow(0 0 2em #673ab8aa); +} + +.card { + padding: 2em; +} + +.read-the-docs { + color: #888; +} diff --git a/frontend/src/styles/index.css b/frontend/src/styles/index.css new file mode 100644 index 0000000..08a3ac9 --- /dev/null +++ b/frontend/src/styles/index.css @@ -0,0 +1,68 @@ +:root { + font-family: system-ui, Avenir, Helvetica, Arial, sans-serif; + line-height: 1.5; + font-weight: 400; + + color-scheme: light dark; + color: rgba(255, 255, 255, 0.87); + background-color: #242424; + + font-synthesis: none; + text-rendering: optimizeLegibility; + -webkit-font-smoothing: antialiased; + -moz-osx-font-smoothing: grayscale; +} + +a { + font-weight: 500; + color: #646cff; + text-decoration: inherit; +} +a:hover { + color: #535bf2; +} + +body { + margin: 0; + display: flex; + place-items: center; + min-width: 320px; + min-height: 100vh; +} + +h1 { + font-size: 3.2em; + line-height: 1.1; +} + +button { + border-radius: 8px; + border: 1px solid transparent; + padding: 0.6em 1.2em; + font-size: 1em; + font-weight: 500; + font-family: inherit; + background-color: #1a1a1a; + cursor: pointer; + transition: border-color 0.25s; +} +button:hover { + border-color: #646cff; +} +button:focus, +button:focus-visible { + outline: 4px auto -webkit-focus-ring-color; +} + +@media (prefers-color-scheme: light) { + :root { + color: #213547; + background-color: #ffffff; + } + a:hover { + color: #747bff; + } + button { + background-color: #f9f9f9; + } +} diff --git a/frontend/vite.config.js b/frontend/vite.config.js new file mode 100644 index 0000000..b995c32 --- /dev/null +++ b/frontend/vite.config.js @@ -0,0 +1,7 @@ +import { defineConfig } from 'vite' +import preact from '@preact/preset-vite' + +// https://vite.dev/config/ +export default defineConfig({ + plugins: [preact()], +}) diff --git a/package.json b/package.json deleted file mode 100644 index 1facd76..0000000 --- a/package.json +++ /dev/null @@ -1,35 +0,0 @@ -{ - "name": "wf-radio", - "version": "1.0.0", - "description": "", - "main": "server.js", - "scripts": { - "start": "node server.js", - "start-auto": "pnpx nodemon server.js", - "test": "echo \"Error: no test specified\" && exit 1" - }, - "keywords": [], - "author": "", - "license": "ISC", - "packageManager": "pnpm@10.5.2", - "dependencies": { - "ajv": "^8.17.1", - "bcrypt": "^5.1.1", - "better-sqlite3": "^11.9.1", - "dompurify": "^3.2.4", - "express": "^5.1.0", - "jsdom": "^26.0.0", - "jsonwebtoken": "^9.0.2", - "marked": "^15.0.7", - "mysql": "^2.18.1" - }, - "pnpm": { - "onlyBuiltDependencies": [ - "bcrypt", - "better-sqlite3" - ] - }, - "devDependencies": { - "nodemon": "^3.1.9" - } -} diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml deleted file mode 100644 index d1d6f0f..0000000 --- a/pnpm-lock.yaml +++ /dev/null @@ -1,1884 +0,0 @@ -lockfileVersion: '9.0' - -settings: - autoInstallPeers: true - excludeLinksFromLockfile: false - -importers: - - .: - dependencies: - ajv: - specifier: ^8.17.1 - version: 8.17.1 - bcrypt: - specifier: ^5.1.1 - version: 5.1.1 - better-sqlite3: - specifier: ^11.9.1 - version: 11.9.1 - dompurify: - specifier: ^3.2.4 - version: 3.2.5 - express: - specifier: ^5.1.0 - version: 5.1.0 - jsdom: - specifier: ^26.0.0 - version: 26.1.0 - jsonwebtoken: - specifier: ^9.0.2 - version: 9.0.2 - marked: - specifier: ^15.0.7 - version: 15.0.10 - mysql: - specifier: ^2.18.1 - version: 2.18.1 - devDependencies: - nodemon: - specifier: ^3.1.9 - version: 3.1.10 - -packages: - - '@asamuzakjp/css-color@3.1.4': - resolution: {integrity: sha512-SeuBV4rnjpFNjI8HSgKUwteuFdkHwkboq31HWzznuqgySQir+jSTczoWVVL4jvOjKjuH80fMDG0Fvg1Sb+OJsA==} - - '@csstools/color-helpers@5.0.2': - resolution: {integrity: sha512-JqWH1vsgdGcw2RR6VliXXdA0/59LttzlU8UlRT/iUUsEeWfYq8I+K0yhihEUTTHLRm1EXvpsCx3083EU15ecsA==} - engines: {node: '>=18'} - - '@csstools/css-calc@2.1.3': - resolution: {integrity: sha512-XBG3talrhid44BY1x3MHzUx/aTG8+x/Zi57M4aTKK9RFB4aLlF3TTSzfzn8nWVHWL3FgAXAxmupmDd6VWww+pw==} - engines: {node: '>=18'} - peerDependencies: - '@csstools/css-parser-algorithms': ^3.0.4 - '@csstools/css-tokenizer': ^3.0.3 - - '@csstools/css-color-parser@3.0.9': - resolution: {integrity: sha512-wILs5Zk7BU86UArYBJTPy/FMPPKVKHMj1ycCEyf3VUptol0JNRLFU/BZsJ4aiIHJEbSLiizzRrw8Pc1uAEDrXw==} - engines: {node: '>=18'} - peerDependencies: - '@csstools/css-parser-algorithms': ^3.0.4 - '@csstools/css-tokenizer': ^3.0.3 - - '@csstools/css-parser-algorithms@3.0.4': - resolution: {integrity: sha512-Up7rBoV77rv29d3uKHUIVubz1BTcgyUK72IvCQAbfbMv584xHcGKCKbWh7i8hPrRJ7qU4Y8IO3IY9m+iTB7P3A==} - engines: {node: '>=18'} - peerDependencies: - '@csstools/css-tokenizer': ^3.0.3 - - '@csstools/css-tokenizer@3.0.3': - resolution: {integrity: sha512-UJnjoFsmxfKUdNYdWgOB0mWUypuLvAfQPH1+pyvRJs6euowbFkFC6P13w1l8mJyi3vxYMxc9kld5jZEGRQs6bw==} - engines: {node: '>=18'} - - '@mapbox/node-pre-gyp@1.0.11': - resolution: {integrity: sha512-Yhlar6v9WQgUp/He7BdgzOz8lqMQ8sU+jkCq7Wx8Myc5YFJLbEe7lgui/V7G1qB1DJykHSGwreceSaD60Y0PUQ==} - hasBin: true - - '@types/trusted-types@2.0.7': - resolution: {integrity: sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==} - - abbrev@1.1.1: - resolution: {integrity: sha512-nne9/IiQ/hzIhY6pdDnbBtz7DjPTKrY00P/zvPSm5pOFkl6xuGrGnXn/VtTNNfNtAfZ9/1RtehkszU9qcTii0Q==} - - accepts@2.0.0: - resolution: {integrity: sha512-5cvg6CtKwfgdmVqY1WIiXKc3Q1bkRqGLi+2W/6ao+6Y7gu/RCwRuAhGEzh5B4KlszSuTLgZYuqFqo5bImjNKng==} - engines: {node: '>= 0.6'} - - agent-base@6.0.2: - resolution: {integrity: sha512-RZNwNclF7+MS/8bDg70amg32dyeZGZxiDuQmZxKLAlQjr3jGyLx+4Kkk58UO7D2QdgFIQCovuSuZESne6RG6XQ==} - engines: {node: '>= 6.0.0'} - - agent-base@7.1.3: - resolution: {integrity: sha512-jRR5wdylq8CkOe6hei19GGZnxM6rBGwFl3Bg0YItGDimvjGtAvdZk4Pu6Cl4u4Igsws4a1fd1Vq3ezrhn4KmFw==} - engines: {node: '>= 14'} - - ajv@8.17.1: - resolution: {integrity: sha512-B/gBuNg5SiMTrPkC+A2+cW0RszwxYmn6VYxB/inlBStS5nx6xHIt/ehKRhIMhqusl7a8LjQoZnjCs5vhwxOQ1g==} - - ansi-regex@5.0.1: - resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==} - engines: {node: '>=8'} - - anymatch@3.1.3: - resolution: {integrity: sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==} - engines: {node: '>= 8'} - - aproba@2.0.0: - resolution: {integrity: sha512-lYe4Gx7QT+MKGbDsA+Z+he/Wtef0BiwDOlK/XkBrdfsh9J/jPPXbX0tE9x9cl27Tmu5gg3QUbUrQYa/y+KOHPQ==} - - are-we-there-yet@2.0.0: - resolution: {integrity: sha512-Ci/qENmwHnsYo9xKIcUJN5LeDKdJ6R1Z1j9V/J5wyq8nh/mYPEpIKJbBZXtZjG04HiK7zV/p6Vs9952MrMeUIw==} - engines: {node: '>=10'} - deprecated: This package is no longer supported. - - balanced-match@1.0.2: - resolution: {integrity: sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==} - - base64-js@1.5.1: - resolution: {integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==} - - bcrypt@5.1.1: - resolution: {integrity: sha512-AGBHOG5hPYZ5Xl9KXzU5iKq9516yEmvCKDg3ecP5kX2aB6UqTeXZxk2ELnDgDm6BQSMlLt9rDB4LoSMx0rYwww==} - engines: {node: '>= 10.0.0'} - - better-sqlite3@11.9.1: - resolution: {integrity: sha512-Ba0KR+Fzxh2jDRhdg6TSH0SJGzb8C0aBY4hR8w8madIdIzzC6Y1+kx5qR6eS1Z+Gy20h6ZU28aeyg0z1VIrShQ==} - - bignumber.js@9.0.0: - resolution: {integrity: sha512-t/OYhhJ2SD+YGBQcjY8GzzDHEk9f3nerxjtfa6tlMXfe7frs/WozhvCNoGvpM0P3bNf3Gq5ZRMlGr5f3r4/N8A==} - - binary-extensions@2.3.0: - resolution: {integrity: sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==} - engines: {node: '>=8'} - - bindings@1.5.0: - resolution: {integrity: sha512-p2q/t/mhvuOj/UeLlV6566GD/guowlr0hHxClI0W9m7MWYkL1F0hLo+0Aexs9HSPCtR1SXQ0TD3MMKrXZajbiQ==} - - bl@4.1.0: - resolution: {integrity: sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==} - - body-parser@2.2.0: - resolution: {integrity: sha512-02qvAaxv8tp7fBa/mw1ga98OGm+eCbqzJOKoRt70sLmfEEi+jyBYVTDGfCL/k06/4EMk/z01gCe7HoCH/f2LTg==} - engines: {node: '>=18'} - - brace-expansion@1.1.11: - resolution: {integrity: sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==} - - braces@3.0.3: - resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} - engines: {node: '>=8'} - - buffer-equal-constant-time@1.0.1: - resolution: {integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==} - - buffer@5.7.1: - resolution: {integrity: sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==} - - bytes@3.1.2: - resolution: {integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==} - engines: {node: '>= 0.8'} - - call-bind-apply-helpers@1.0.2: - resolution: {integrity: sha512-Sp1ablJ0ivDkSzjcaJdxEunN5/XvksFJ2sMBFfq6x0ryhQV/2b/KwFe21cMpmHtPOSij8K99/wSfoEuTObmuMQ==} - engines: {node: '>= 0.4'} - - call-bound@1.0.4: - resolution: {integrity: sha512-+ys997U96po4Kx/ABpBCqhA9EuxJaQWDQg7295H4hBphv3IZg0boBKuwYpt4YXp6MZ5AmZQnU/tyMTlRpaSejg==} - engines: {node: '>= 0.4'} - - chokidar@3.6.0: - resolution: {integrity: sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==} - engines: {node: '>= 8.10.0'} - - chownr@1.1.4: - resolution: {integrity: sha512-jJ0bqzaylmJtVnNgzTeSOs8DPavpbYgEr/b0YL8/2GO3xJEhInFmhKMUnEJQjZumK7KXGFhUy89PrsJWlakBVg==} - - chownr@2.0.0: - resolution: {integrity: sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ==} - engines: {node: '>=10'} - - color-support@1.1.3: - resolution: {integrity: sha512-qiBjkpbMLO/HL68y+lh4q0/O1MZFj2RX6X/KmMa3+gJD3z+WwI1ZzDHysvqHGS3mP6mznPckpXmw1nI9cJjyRg==} - hasBin: true - - concat-map@0.0.1: - resolution: {integrity: sha512-/Srv4dswyQNBfohGpz9o6Yb3Gz3SrUDqBH5rTuhGR7ahtlbYKnVxw2bCFMRljaA7EXHaXZ8wsHdodFvbkhKmqg==} - - console-control-strings@1.1.0: - resolution: {integrity: sha512-ty/fTekppD2fIwRvnZAVdeOiGd1c7YXEixbgJTNzqcxJWKQnjJ/V1bNEEE6hygpM3WjwHFUVK6HTjWSzV4a8sQ==} - - content-disposition@1.0.0: - resolution: {integrity: sha512-Au9nRL8VNUut/XSzbQA38+M78dzP4D+eqg3gfJHMIHHYa3bg067xj1KxMUWj+VULbiZMowKngFFbKczUrNJ1mg==} - engines: {node: '>= 0.6'} - - content-type@1.0.5: - resolution: {integrity: sha512-nTjqfcBFEipKdXCv4YDQWCfmcLZKm81ldF0pAopTvyrFGVbcR6P/VAAd5G7N+0tTr8QqiU0tFadD6FK4NtJwOA==} - engines: {node: '>= 0.6'} - - cookie-signature@1.2.2: - resolution: {integrity: sha512-D76uU73ulSXrD1UXF4KE2TMxVVwhsnCgfAyTg9k8P6KGZjlXKrOLe4dJQKI3Bxi5wjesZoFXJWElNWBjPZMbhg==} - engines: {node: '>=6.6.0'} - - cookie@0.7.2: - resolution: {integrity: sha512-yki5XnKuf750l50uGTllt6kKILY4nQ1eNIQatoXEByZ5dWgnKqbnqmTrBE5B4N7lrMJKQ2ytWMiTO2o0v6Ew/w==} - engines: {node: '>= 0.6'} - - core-util-is@1.0.3: - resolution: {integrity: sha512-ZQBvi1DcpJ4GDqanjucZ2Hj3wEO5pZDS89BWbkcrvdxksJorwUDDZamX9ldFkp9aw2lmBDLgkObEA4DWNJ9FYQ==} - - cssstyle@4.3.1: - resolution: {integrity: sha512-ZgW+Jgdd7i52AaLYCriF8Mxqft0gD/R9i9wi6RWBhs1pqdPEzPjym7rvRKi397WmQFf3SlyUsszhw+VVCbx79Q==} - engines: {node: '>=18'} - - data-urls@5.0.0: - resolution: {integrity: sha512-ZYP5VBHshaDAiVZxjbRVcFJpc+4xGgT0bK3vzy1HLN8jTO975HEbuYzZJcHoQEY5K1a0z8YayJkyVETa08eNTg==} - engines: {node: '>=18'} - - debug@4.4.0: - resolution: {integrity: sha512-6WTZ/IxCY/T6BALoZHaE4ctp9xm+Z5kY/pzYaCHRFeyVhojxlrm+46y68HA6hr0TcwEssoxNiDEUJQjfPZ/RYA==} - engines: {node: '>=6.0'} - peerDependencies: - supports-color: '*' - peerDependenciesMeta: - supports-color: - optional: true - - decimal.js@10.5.0: - resolution: {integrity: sha512-8vDa8Qxvr/+d94hSh5P3IJwI5t8/c0KsMp+g8bNw9cY2icONa5aPfvKeieW1WlG0WQYwwhJ7mjui2xtiePQSXw==} - - decompress-response@6.0.0: - resolution: {integrity: sha512-aW35yZM6Bb/4oJlZncMH2LCoZtJXTRxES17vE3hoRiowU2kWHaJKFkSBDnDR+cm9J+9QhXmREyIfv0pji9ejCQ==} - engines: {node: '>=10'} - - deep-extend@0.6.0: - resolution: {integrity: sha512-LOHxIOaPYdHlJRtCQfDIVZtfw/ufM8+rVj649RIHzcm/vGwQRXFt6OPqIFWsm2XEMrNIEtWR64sY1LEKD2vAOA==} - engines: {node: '>=4.0.0'} - - delegates@1.0.0: - resolution: {integrity: sha512-bd2L678uiWATM6m5Z1VzNCErI3jiGzt6HGY8OVICs40JQq/HALfbyNJmp0UDakEY4pMMaN0Ly5om/B1VI/+xfQ==} - - depd@2.0.0: - resolution: {integrity: sha512-g7nH6P6dyDioJogAAGprGpCtVImJhpPk/roCzdb3fIh61/s/nPsfR6onyMwkCAR/OlC3yBC0lESvUoQEAssIrw==} - engines: {node: '>= 0.8'} - - detect-libc@2.0.4: - resolution: {integrity: sha512-3UDv+G9CsCKO1WKMGw9fwq/SWJYbI0c5Y7LU1AXYoDdbhE2AHQ6N6Nb34sG8Fj7T5APy8qXDCKuuIHd1BR0tVA==} - engines: {node: '>=8'} - - dompurify@3.2.5: - resolution: {integrity: sha512-mLPd29uoRe9HpvwP2TxClGQBzGXeEC/we/q+bFlmPPmj2p2Ugl3r6ATu/UU1v77DXNcehiBg9zsr1dREyA/dJQ==} - - dunder-proto@1.0.1: - resolution: {integrity: sha512-KIN/nDJBQRcXw0MLVhZE9iQHmG68qAVIBg9CqmUYjmQIhgij9U5MFvrqkUL5FbtyyzZuOeOt0zdeRe4UY7ct+A==} - engines: {node: '>= 0.4'} - - ecdsa-sig-formatter@1.0.11: - resolution: {integrity: sha512-nagl3RYrbNv6kQkeJIpt6NJZy8twLB/2vtz6yN9Z4vRKHN4/QZJIEbqohALSgwKdnksuY3k5Addp5lg8sVoVcQ==} - - ee-first@1.1.1: - resolution: {integrity: sha512-WMwm9LhRUo+WUaRN+vRuETqG89IgZphVSNkdFgeb6sS/E4OrDIN7t48CAewSHXc6C8lefD8KKfr5vY61brQlow==} - - emoji-regex@8.0.0: - resolution: {integrity: sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==} - - encodeurl@2.0.0: - resolution: {integrity: sha512-Q0n9HRi4m6JuGIV1eFlmvJB7ZEVxu93IrMyiMsGC0lrMJMWzRgx6WGquyfQgZVb31vhGgXnfmPNNXmxnOkRBrg==} - engines: {node: '>= 0.8'} - - end-of-stream@1.4.4: - resolution: {integrity: sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==} - - entities@6.0.0: - resolution: {integrity: sha512-aKstq2TDOndCn4diEyp9Uq/Flu2i1GlLkc6XIDQSDMuaFE3OPW5OphLCyQ5SpSJZTb4reN+kTcYru5yIfXoRPw==} - engines: {node: '>=0.12'} - - es-define-property@1.0.1: - resolution: {integrity: sha512-e3nRfgfUZ4rNGL232gUgX06QNyyez04KdjFrF+LTRoOXmrOgFKDg4BCdsjW8EnT69eqdYGmRpJwiPVYNrCaW3g==} - engines: {node: '>= 0.4'} - - es-errors@1.3.0: - resolution: {integrity: sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==} - engines: {node: '>= 0.4'} - - es-object-atoms@1.1.1: - resolution: {integrity: sha512-FGgH2h8zKNim9ljj7dankFPcICIK9Cp5bm+c2gQSYePhpaG5+esrLODihIorn+Pe6FGJzWhXQotPv73jTaldXA==} - engines: {node: '>= 0.4'} - - escape-html@1.0.3: - resolution: {integrity: sha512-NiSupZ4OeuGwr68lGIeym/ksIZMJodUGOSCZ/FSnTxcrekbvqrgdUxlJOMpijaKZVjAJrWrGs/6Jy8OMuyj9ow==} - - etag@1.8.1: - resolution: {integrity: sha512-aIL5Fx7mawVa300al2BnEE4iNvo1qETxLrPI/o05L7z6go7fCw1J6EQmbK4FmJ2AS7kgVF/KEZWufBfdClMcPg==} - engines: {node: '>= 0.6'} - - expand-template@2.0.3: - resolution: {integrity: sha512-XYfuKMvj4O35f/pOXLObndIRvyQ+/+6AhODh+OKWj9S9498pHHn/IMszH+gt0fBCRWMNfk1ZSp5x3AifmnI2vg==} - engines: {node: '>=6'} - - express@5.1.0: - resolution: {integrity: sha512-DT9ck5YIRU+8GYzzU5kT3eHGA5iL+1Zd0EutOmTE9Dtk+Tvuzd23VBU+ec7HPNSTxXYO55gPV/hq4pSBJDjFpA==} - engines: {node: '>= 18'} - - fast-deep-equal@3.1.3: - resolution: {integrity: sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==} - - fast-uri@3.0.6: - resolution: {integrity: sha512-Atfo14OibSv5wAp4VWNsFYE1AchQRTv9cBGWET4pZWHzYshFSS9NQI6I57rdKn9croWVMbYFbLhJ+yJvmZIIHw==} - - file-uri-to-path@1.0.0: - resolution: {integrity: sha512-0Zt+s3L7Vf1biwWZ29aARiVYLx7iMGnEUl9x33fbB/j3jR81u/O2LbqK+Bm1CDSNDKVtJ/YjwY7TUd5SkeLQLw==} - - fill-range@7.1.1: - resolution: {integrity: sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==} - engines: {node: '>=8'} - - finalhandler@2.1.0: - resolution: {integrity: sha512-/t88Ty3d5JWQbWYgaOGCCYfXRwV1+be02WqYYlL6h0lEiUAMPM8o8qKGO01YIkOHzka2up08wvgYD0mDiI+q3Q==} - engines: {node: '>= 0.8'} - - forwarded@0.2.0: - resolution: {integrity: sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==} - engines: {node: '>= 0.6'} - - fresh@2.0.0: - resolution: {integrity: sha512-Rx/WycZ60HOaqLKAi6cHRKKI7zxWbJ31MhntmtwMoaTeF7XFH9hhBp8vITaMidfljRQ6eYWCKkaTK+ykVJHP2A==} - engines: {node: '>= 0.8'} - - fs-constants@1.0.0: - resolution: {integrity: sha512-y6OAwoSIf7FyjMIv94u+b5rdheZEjzR63GTyZJm5qh4Bi+2YgwLCcI/fPFZkL5PSixOt6ZNKm+w+Hfp/Bciwow==} - - fs-minipass@2.1.0: - resolution: {integrity: sha512-V/JgOLFCS+R6Vcq0slCuaeWEdNC3ouDlJMNIsacH2VtALiu9mV4LPrHc5cDl8k5aw6J8jwgWWpiTo5RYhmIzvg==} - engines: {node: '>= 8'} - - fs.realpath@1.0.0: - resolution: {integrity: sha512-OO0pH2lK6a0hZnAdau5ItzHPI6pUlvI7jMVnxUQRtw4owF2wk8lOSabtGDCTP4Ggrg2MbGnWO9X8K1t4+fGMDw==} - - fsevents@2.3.3: - resolution: {integrity: sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==} - engines: {node: ^8.16.0 || ^10.6.0 || >=11.0.0} - os: [darwin] - - function-bind@1.1.2: - resolution: {integrity: sha512-7XHNxH7qX9xG5mIwxkhumTox/MIRNcOgDrxWsMt2pAr23WHp6MrRlN7FBSFpCpr+oVO0F744iUgR82nJMfG2SA==} - - gauge@3.0.2: - resolution: {integrity: sha512-+5J6MS/5XksCuXq++uFRsnUd7Ovu1XenbeuIuNRJxYWjgQbPuFhT14lAvsWfqfAmnwluf1OwMjz39HjfLPci0Q==} - engines: {node: '>=10'} - deprecated: This package is no longer supported. - - get-intrinsic@1.3.0: - resolution: {integrity: sha512-9fSjSaos/fRIVIp+xSJlE6lfwhES7LNtKaCBIamHsjr2na1BiABJPo0mOjjz8GJDURarmCPGqaiVg5mfjb98CQ==} - engines: {node: '>= 0.4'} - - get-proto@1.0.1: - resolution: {integrity: sha512-sTSfBjoXBp89JvIKIefqw7U2CCebsc74kiY6awiGogKtoSGbgjYE/G/+l9sF3MWFPNc9IcoOC4ODfKHfxFmp0g==} - engines: {node: '>= 0.4'} - - github-from-package@0.0.0: - resolution: {integrity: sha512-SyHy3T1v2NUXn29OsWdxmK6RwHD+vkj3v8en8AOBZ1wBQ/hCAQ5bAQTD02kW4W9tUp/3Qh6J8r9EvntiyCmOOw==} - - glob-parent@5.1.2: - resolution: {integrity: sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==} - engines: {node: '>= 6'} - - glob@7.2.3: - resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==} - deprecated: Glob versions prior to v9 are no longer supported - - gopd@1.2.0: - resolution: {integrity: sha512-ZUKRh6/kUFoAiTAtTYPZJ3hw9wNxx+BIBOijnlG9PnrJsCcSjs1wyyD6vJpaYtgnzDrKYRSqf3OO6Rfa93xsRg==} - engines: {node: '>= 0.4'} - - has-flag@3.0.0: - resolution: {integrity: sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==} - engines: {node: '>=4'} - - has-symbols@1.1.0: - resolution: {integrity: sha512-1cDNdwJ2Jaohmb3sg4OmKaMBwuC48sYni5HUw2DvsC8LjGTLK9h+eb1X6RyuOHe4hT0ULCW68iomhjUoKUqlPQ==} - engines: {node: '>= 0.4'} - - has-unicode@2.0.1: - resolution: {integrity: sha512-8Rf9Y83NBReMnx0gFzA8JImQACstCYWUplepDa9xprwwtmgEZUF0h/i5xSA625zB/I37EtrswSST6OXxwaaIJQ==} - - hasown@2.0.2: - resolution: {integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==} - engines: {node: '>= 0.4'} - - html-encoding-sniffer@4.0.0: - resolution: {integrity: sha512-Y22oTqIU4uuPgEemfz7NDJz6OeKf12Lsu+QC+s3BVpda64lTiMYCyGwg5ki4vFxkMwQdeZDl2adZoqUgdFuTgQ==} - engines: {node: '>=18'} - - http-errors@2.0.0: - resolution: {integrity: sha512-FtwrG/euBzaEjYeRqOgly7G0qviiXoJWnvEH2Z1plBdXgbyjv34pHTSb9zoeHMyDy33+DWy5Wt9Wo+TURtOYSQ==} - engines: {node: '>= 0.8'} - - http-proxy-agent@7.0.2: - resolution: {integrity: sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==} - engines: {node: '>= 14'} - - https-proxy-agent@5.0.1: - resolution: {integrity: sha512-dFcAjpTQFgoLMzC2VwU+C/CbS7uRL0lWmxDITmqm7C+7F0Odmj6s9l6alZc6AELXhrnggM2CeWSXHGOdX2YtwA==} - engines: {node: '>= 6'} - - https-proxy-agent@7.0.6: - resolution: {integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==} - engines: {node: '>= 14'} - - iconv-lite@0.6.3: - resolution: {integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==} - engines: {node: '>=0.10.0'} - - ieee754@1.2.1: - resolution: {integrity: sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==} - - ignore-by-default@1.0.1: - resolution: {integrity: sha512-Ius2VYcGNk7T90CppJqcIkS5ooHUZyIQK+ClZfMfMNFEF9VSE73Fq+906u/CWu92x4gzZMWOwfFYckPObzdEbA==} - - inflight@1.0.6: - resolution: {integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==} - deprecated: This module is not supported, and leaks memory. Do not use it. Check out lru-cache if you want a good and tested way to coalesce async requests by a key value, which is much more comprehensive and powerful. - - inherits@2.0.4: - resolution: {integrity: sha512-k/vGaX4/Yla3WzyMCvTQOXYeIHvqOKtnqBduzTHpzpQZzAskKMhZ2K+EnBiSM9zGSoIFeMpXKxa4dYeZIQqewQ==} - - ini@1.3.8: - resolution: {integrity: sha512-JV/yugV2uzW5iMRSiZAyDtQd+nxtUnjeLt0acNdw98kKLrvuRVyB80tsREOE7yvGVgalhZ6RNXCmEHkUKBKxew==} - - ipaddr.js@1.9.1: - resolution: {integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==} - engines: {node: '>= 0.10'} - - is-binary-path@2.1.0: - resolution: {integrity: sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==} - engines: {node: '>=8'} - - is-extglob@2.1.1: - resolution: {integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==} - engines: {node: '>=0.10.0'} - - is-fullwidth-code-point@3.0.0: - resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==} - engines: {node: '>=8'} - - is-glob@4.0.3: - resolution: {integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==} - engines: {node: '>=0.10.0'} - - is-number@7.0.0: - resolution: {integrity: sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==} - engines: {node: '>=0.12.0'} - - is-potential-custom-element-name@1.0.1: - resolution: {integrity: sha512-bCYeRA2rVibKZd+s2625gGnGF/t7DSqDs4dP7CrLA1m7jKWz6pps0LpYLJN8Q64HtmPKJ1hrN3nzPNKFEKOUiQ==} - - is-promise@4.0.0: - resolution: {integrity: sha512-hvpoI6korhJMnej285dSg6nu1+e6uxs7zG3BYAm5byqDsgJNWwxzM6z6iZiAgQR4TJ30JmBTOwqZUw3WlyH3AQ==} - - isarray@1.0.0: - resolution: {integrity: sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==} - - jsdom@26.1.0: - resolution: {integrity: sha512-Cvc9WUhxSMEo4McES3P7oK3QaXldCfNWp7pl2NNeiIFlCoLr3kfq9kb1fxftiwk1FLV7CvpvDfonxtzUDeSOPg==} - engines: {node: '>=18'} - peerDependencies: - canvas: ^3.0.0 - peerDependenciesMeta: - canvas: - optional: true - - json-schema-traverse@1.0.0: - resolution: {integrity: sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==} - - jsonwebtoken@9.0.2: - resolution: {integrity: sha512-PRp66vJ865SSqOlgqS8hujT5U4AOgMfhrwYIuIhfKaoSCZcirrmASQr8CX7cUg+RMih+hgznrjp99o+W4pJLHQ==} - engines: {node: '>=12', npm: '>=6'} - - jwa@1.4.1: - resolution: {integrity: sha512-qiLX/xhEEFKUAJ6FiBMbes3w9ATzyk5W7Hvzpa/SLYdxNtng+gcurvrI7TbACjIXlsJyr05/S1oUhZrc63evQA==} - - jws@3.2.2: - resolution: {integrity: sha512-YHlZCB6lMTllWDtSPHz/ZXTsi8S00usEV6v1tjq8tOUZzw7DpSDWVXjXDre6ed1w/pd495ODpHZYSdkRTsa0HA==} - - lodash.includes@4.3.0: - resolution: {integrity: sha512-W3Bx6mdkRTGtlJISOvVD/lbqjTlPPUDTMnlXZFnVwi9NKJ6tiAk6LVdlhZMm17VZisqhKcgzpO5Wz91PCt5b0w==} - - lodash.isboolean@3.0.3: - resolution: {integrity: sha512-Bz5mupy2SVbPHURB98VAcw+aHh4vRV5IPNhILUCsOzRmsTmSQ17jIuqopAentWoehktxGd9e/hbIXq980/1QJg==} - - lodash.isinteger@4.0.4: - resolution: {integrity: sha512-DBwtEWN2caHQ9/imiNeEA5ys1JoRtRfY3d7V9wkqtbycnAmTvRRmbHKDV4a0EYc678/dia0jrte4tjYwVBaZUA==} - - lodash.isnumber@3.0.3: - resolution: {integrity: sha512-QYqzpfwO3/CWf3XP+Z+tkQsfaLL/EnUlXWVkIk5FUPc4sBdTehEqZONuyRt2P67PXAk+NXmTBcc97zw9t1FQrw==} - - lodash.isplainobject@4.0.6: - resolution: {integrity: sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==} - - lodash.isstring@4.0.1: - resolution: {integrity: sha512-0wJxfxH1wgO3GrbuP+dTTk7op+6L41QCXbGINEmD+ny/G/eCqGzxyCsh7159S+mgDDcoarnBw6PC1PS5+wUGgw==} - - lodash.once@4.1.1: - resolution: {integrity: sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg==} - - lru-cache@10.4.3: - resolution: {integrity: sha512-JNAzZcXrCt42VGLuYz0zfAzDfAvJWW6AfYlDBQyDV5DClI2m5sAmK+OIO7s59XfsRsWHp02jAJrRadPRGTt6SQ==} - - make-dir@3.1.0: - resolution: {integrity: sha512-g3FeP20LNwhALb/6Cz6Dd4F2ngze0jz7tbzrD2wAV+o9FeNHe4rL+yK2md0J/fiSf1sa1ADhXqi5+oVwOM/eGw==} - engines: {node: '>=8'} - - marked@15.0.10: - resolution: {integrity: sha512-BXzsfFiR2UqXFKRwpugWuCYi9mWd1aX/Yns/X52xWfvfen9lnGEDbJw9ZEjjvLZVqntqT2gX45eYvqb2dIokDw==} - engines: {node: '>= 18'} - hasBin: true - - math-intrinsics@1.1.0: - resolution: {integrity: sha512-/IXtbwEk5HTPyEwyKX6hGkYXxM9nbj64B+ilVJnC/R6B0pH5G4V3b0pVbL7DBj4tkhBAppbQUlf6F6Xl9LHu1g==} - engines: {node: '>= 0.4'} - - media-typer@1.1.0: - resolution: {integrity: sha512-aisnrDP4GNe06UcKFnV5bfMNPBUw4jsLGaWwWfnH3v02GnBuXX2MCVn5RbrWo0j3pczUilYblq7fQ7Nw2t5XKw==} - engines: {node: '>= 0.8'} - - merge-descriptors@2.0.0: - resolution: {integrity: sha512-Snk314V5ayFLhp3fkUREub6WtjBfPdCPY1Ln8/8munuLuiYhsABgBVWsozAG+MWMbVEvcdcpbi9R7ww22l9Q3g==} - engines: {node: '>=18'} - - mime-db@1.54.0: - resolution: {integrity: sha512-aU5EJuIN2WDemCcAp2vFBfp/m4EAhWJnUNSSw0ixs7/kXbd6Pg64EmwJkNdFhB8aWt1sH2CTXrLxo/iAGV3oPQ==} - engines: {node: '>= 0.6'} - - mime-types@3.0.1: - resolution: {integrity: sha512-xRc4oEhT6eaBpU1XF7AjpOFD+xQmXNB5OVKwp4tqCuBpHLS/ZbBDrc07mYTDqVMg6PfxUjjNp85O6Cd2Z/5HWA==} - engines: {node: '>= 0.6'} - - mimic-response@3.1.0: - resolution: {integrity: sha512-z0yWI+4FDrrweS8Zmt4Ej5HdJmky15+L2e6Wgn3+iK5fWzb6T3fhNFq2+MeTRb064c6Wr4N/wv0DzQTjNzHNGQ==} - engines: {node: '>=10'} - - minimatch@3.1.2: - resolution: {integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==} - - minimist@1.2.8: - resolution: {integrity: sha512-2yyAR8qBkN3YuheJanUpWC5U3bb5osDywNB8RzDVlDwDHbocAJveqqj1u8+SVD7jkWT4yvsHCpWqqWqAxb0zCA==} - - minipass@3.3.6: - resolution: {integrity: sha512-DxiNidxSEK+tHG6zOIklvNOwm3hvCrbUrdtzY74U6HKTJxvIDfOUL5W5P2Ghd3DTkhhKPYGqeNUIh5qcM4YBfw==} - engines: {node: '>=8'} - - minipass@5.0.0: - resolution: {integrity: sha512-3FnjYuehv9k6ovOEbyOswadCDPX1piCfhV8ncmYtHOjuPwylVWsghTLo7rabjC3Rx5xD4HDx8Wm1xnMF7S5qFQ==} - engines: {node: '>=8'} - - minizlib@2.1.2: - resolution: {integrity: sha512-bAxsR8BVfj60DWXHE3u30oHzfl4G7khkSuPW+qvpd7jFRHm7dLxOjUk1EHACJ/hxLY8phGJ0YhYHZo7jil7Qdg==} - engines: {node: '>= 8'} - - mkdirp-classic@0.5.3: - resolution: {integrity: sha512-gKLcREMhtuZRwRAfqP3RFW+TK4JqApVBtOIftVgjuABpAtpxhPGaDcfvbhNvD0B8iD1oUr/txX35NjcaY6Ns/A==} - - mkdirp@1.0.4: - resolution: {integrity: sha512-vVqVZQyf3WLx2Shd0qJ9xuvqgAyKPLAiqITEtqW0oIUjzo3PePDd6fW9iFz30ef7Ysp/oiWqbhszeGWW2T6Gzw==} - engines: {node: '>=10'} - hasBin: true - - ms@2.1.3: - resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} - - mysql@2.18.1: - resolution: {integrity: sha512-Bca+gk2YWmqp2Uf6k5NFEurwY/0td0cpebAucFpY/3jhrwrVGuxU2uQFCHjU19SJfje0yQvi+rVWdq78hR5lig==} - engines: {node: '>= 0.6'} - - napi-build-utils@2.0.0: - resolution: {integrity: sha512-GEbrYkbfF7MoNaoh2iGG84Mnf/WZfB0GdGEsM8wz7Expx/LlWf5U8t9nvJKXSp3qr5IsEbK04cBGhol/KwOsWA==} - - negotiator@1.0.0: - resolution: {integrity: sha512-8Ofs/AUQh8MaEcrlq5xOX0CQ9ypTF5dl78mjlMNfOK08fzpgTHQRQPBxcPlEtIw0yRpws+Zo/3r+5WRby7u3Gg==} - engines: {node: '>= 0.6'} - - node-abi@3.74.0: - resolution: {integrity: sha512-c5XK0MjkGBrQPGYG24GBADZud0NCbznxNx0ZkS+ebUTrmV1qTDxPxSL8zEAPURXSbLRWVexxmP4986BziahL5w==} - engines: {node: '>=10'} - - node-addon-api@5.1.0: - resolution: {integrity: sha512-eh0GgfEkpnoWDq+VY8OyvYhFEzBk6jIYbRKdIlyTiAXIVJ8PyBaKb0rp7oDtoddbdoHWhq8wwr+XZ81F1rpNdA==} - - node-fetch@2.7.0: - resolution: {integrity: sha512-c4FRfUm/dbcWZ7U+1Wq0AwCyFL+3nt2bEw05wfxSz+DWpWsitgmSgYmy2dQdWyKC1694ELPqMs/YzUSNozLt8A==} - engines: {node: 4.x || >=6.0.0} - peerDependencies: - encoding: ^0.1.0 - peerDependenciesMeta: - encoding: - optional: true - - nodemon@3.1.10: - resolution: {integrity: sha512-WDjw3pJ0/0jMFmyNDp3gvY2YizjLmmOUQo6DEBY+JgdvW/yQ9mEeSw6H5ythl5Ny2ytb7f9C2nIbjSxMNzbJXw==} - engines: {node: '>=10'} - hasBin: true - - nopt@5.0.0: - resolution: {integrity: sha512-Tbj67rffqceeLpcRXrT7vKAN8CwfPeIBgM7E6iBkmKLV7bEMwpGgYLGv0jACUsECaa/vuxP0IjEont6umdMgtQ==} - engines: {node: '>=6'} - hasBin: true - - normalize-path@3.0.0: - resolution: {integrity: sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==} - engines: {node: '>=0.10.0'} - - npmlog@5.0.1: - resolution: {integrity: sha512-AqZtDUWOMKs1G/8lwylVjrdYgqA4d9nu8hc+0gzRxlDb1I10+FHBGMXs6aiQHFdCUUlqH99MUMuLfzWDNDtfxw==} - deprecated: This package is no longer supported. - - nwsapi@2.2.20: - resolution: {integrity: sha512-/ieB+mDe4MrrKMT8z+mQL8klXydZWGR5Dowt4RAGKbJ3kIGEx3X4ljUo+6V73IXtUPWgfOlU5B9MlGxFO5T+cA==} - - object-assign@4.1.1: - resolution: {integrity: sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==} - engines: {node: '>=0.10.0'} - - object-inspect@1.13.4: - resolution: {integrity: sha512-W67iLl4J2EXEGTbfeHCffrjDfitvLANg0UlX3wFUUSTx92KXRFegMHUVgSqE+wvhAbi4WqjGg9czysTV2Epbew==} - engines: {node: '>= 0.4'} - - on-finished@2.4.1: - resolution: {integrity: sha512-oVlzkg3ENAhCk2zdv7IJwd/QUD4z2RxRwpkcGY8psCVcCYZNq4wYnVWALHM+brtuJjePWiYF/ClmuDr8Ch5+kg==} - engines: {node: '>= 0.8'} - - once@1.4.0: - resolution: {integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==} - - parse5@7.3.0: - resolution: {integrity: sha512-IInvU7fabl34qmi9gY8XOVxhYyMyuH2xUNpb2q8/Y+7552KlejkRvqvD19nMoUW/uQGGbqNpA6Tufu5FL5BZgw==} - - parseurl@1.3.3: - resolution: {integrity: sha512-CiyeOxFT/JZyN5m0z9PfXw4SCBJ6Sygz1Dpl0wqjlhDEGGBP1GnsUVEL0p63hoG1fcj3fHynXi9NYO4nWOL+qQ==} - engines: {node: '>= 0.8'} - - path-is-absolute@1.0.1: - resolution: {integrity: sha512-AVbw3UJ2e9bq64vSaS9Am0fje1Pa8pbGqTTsmXfaIiMpnr5DlDhfJOuLj9Sf95ZPVDAUerDfEk88MPmPe7UCQg==} - engines: {node: '>=0.10.0'} - - path-to-regexp@8.2.0: - resolution: {integrity: sha512-TdrF7fW9Rphjq4RjrW0Kp2AW0Ahwu9sRGTkS6bvDi0SCwZlEZYmcfDbEsTz8RVk0EHIS/Vd1bv3JhG+1xZuAyQ==} - engines: {node: '>=16'} - - picomatch@2.3.1: - resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} - engines: {node: '>=8.6'} - - prebuild-install@7.1.3: - resolution: {integrity: sha512-8Mf2cbV7x1cXPUILADGI3wuhfqWvtiLA1iclTDbFRZkgRQS0NqsPZphna9V+HyTEadheuPmjaJMsbzKQFOzLug==} - engines: {node: '>=10'} - hasBin: true - - process-nextick-args@2.0.1: - resolution: {integrity: sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==} - - proxy-addr@2.0.7: - resolution: {integrity: sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==} - engines: {node: '>= 0.10'} - - pstree.remy@1.1.8: - resolution: {integrity: sha512-77DZwxQmxKnu3aR542U+X8FypNzbfJ+C5XQDk3uWjWxn6151aIMGthWYRXTqT1E5oJvg+ljaa2OJi+VfvCOQ8w==} - - pump@3.0.2: - resolution: {integrity: sha512-tUPXtzlGM8FE3P0ZL6DVs/3P58k9nk8/jZeQCurTJylQA8qFYzHFfhBJkuqyE0FifOsQ0uKWekiZ5g8wtr28cw==} - - punycode@2.3.1: - resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} - engines: {node: '>=6'} - - qs@6.14.0: - resolution: {integrity: sha512-YWWTjgABSKcvs/nWBi9PycY/JiPJqOD4JA6o9Sej2AtvSGarXxKC3OQSk4pAarbdQlKAh5D4FCQkJNkW+GAn3w==} - engines: {node: '>=0.6'} - - range-parser@1.2.1: - resolution: {integrity: sha512-Hrgsx+orqoygnmhFbKaHE6c296J+HTAQXoxEF6gNupROmmGJRoyzfG3ccAveqCBrwr/2yxQ5BVd/GTl5agOwSg==} - engines: {node: '>= 0.6'} - - raw-body@3.0.0: - resolution: {integrity: sha512-RmkhL8CAyCRPXCE28MMH0z2PNWQBNk2Q09ZdxM9IOOXwxwZbN+qbWaatPkdkWIKL2ZVDImrN/pK5HTRz2PcS4g==} - engines: {node: '>= 0.8'} - - rc@1.2.8: - resolution: {integrity: sha512-y3bGgqKj3QBdxLbLkomlohkvsA8gdAiUQlSBJnBhfn+BPxg4bc62d8TcBW15wavDfgexCgccckhcZvywyQYPOw==} - hasBin: true - - readable-stream@2.3.7: - resolution: {integrity: sha512-Ebho8K4jIbHAxnuxi7o42OrZgF/ZTNcsZj6nRKyUmkhLFq8CHItp/fy6hQZuZmP/n3yZ9VBUbp4zz/mX8hmYPw==} - - readable-stream@3.6.2: - resolution: {integrity: sha512-9u/sniCrY3D5WdsERHzHE4G2YCXqoG5FTHUiCC4SIbr6XcLZBY05ya9EKjYek9O5xOAwjGq+1JdGBAS7Q9ScoA==} - engines: {node: '>= 6'} - - readdirp@3.6.0: - resolution: {integrity: sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==} - engines: {node: '>=8.10.0'} - - require-from-string@2.0.2: - resolution: {integrity: sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==} - engines: {node: '>=0.10.0'} - - rimraf@3.0.2: - resolution: {integrity: sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==} - deprecated: Rimraf versions prior to v4 are no longer supported - hasBin: true - - router@2.2.0: - resolution: {integrity: sha512-nLTrUKm2UyiL7rlhapu/Zl45FwNgkZGaCpZbIHajDYgwlJCOzLSk+cIPAnsEqV955GjILJnKbdQC1nVPz+gAYQ==} - engines: {node: '>= 18'} - - rrweb-cssom@0.8.0: - resolution: {integrity: sha512-guoltQEx+9aMf2gDZ0s62EcV8lsXR+0w8915TC3ITdn2YueuNjdAYh/levpU9nFaoChh9RUS5ZdQMrKfVEN9tw==} - - safe-buffer@5.1.2: - resolution: {integrity: sha512-Gd2UZBJDkXlY7GbJxfsE8/nvKkUEU1G38c1siN6QP6a9PT9MmHB8GnpscSmMJSoF8LOIrt8ud/wPtojys4G6+g==} - - safe-buffer@5.2.1: - resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} - - safer-buffer@2.1.2: - resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} - - saxes@6.0.0: - resolution: {integrity: sha512-xAg7SOnEhrm5zI3puOOKyy1OMcMlIJZYNJY7xLBwSze0UjhPLnWfj2GF2EpT0jmzaJKIWKHLsaSSajf35bcYnA==} - engines: {node: '>=v12.22.7'} - - semver@6.3.1: - resolution: {integrity: sha512-BR7VvDCVHO+q2xBEWskxS6DJE1qRnb7DxzUrogb71CWoSficBxYsiAGd+Kl0mmq/MprG9yArRkyrQxTO6XjMzA==} - hasBin: true - - semver@7.7.1: - resolution: {integrity: sha512-hlq8tAfn0m/61p4BVRcPzIGr6LKiMwo4VM6dGi6pt4qcRkmNzTcWq6eCEjEh+qXjkMDvPlOFFSGwQjoEa6gyMA==} - engines: {node: '>=10'} - hasBin: true - - send@1.2.0: - resolution: {integrity: sha512-uaW0WwXKpL9blXE2o0bRhoL2EGXIrZxQ2ZQ4mgcfoBxdFmQold+qWsD2jLrfZ0trjKL6vOw0j//eAwcALFjKSw==} - engines: {node: '>= 18'} - - serve-static@2.2.0: - resolution: {integrity: sha512-61g9pCh0Vnh7IutZjtLGGpTA355+OPn2TyDv/6ivP2h/AdAVX9azsoxmg2/M6nZeQZNYBEwIcsne1mJd9oQItQ==} - engines: {node: '>= 18'} - - set-blocking@2.0.0: - resolution: {integrity: sha512-KiKBS8AnWGEyLzofFfmvKwpdPzqiy16LvQfK3yv/fVH7Bj13/wl3JSR1J+rfgRE9q7xUJK4qvgS8raSOeLUehw==} - - setprototypeof@1.2.0: - resolution: {integrity: sha512-E5LDX7Wrp85Kil5bhZv46j8jOeboKq5JMmYM3gVGdGH8xFpPWXUMsNrlODCrkoxMEeNi/XZIwuRvY4XNwYMJpw==} - - side-channel-list@1.0.0: - resolution: {integrity: sha512-FCLHtRD/gnpCiCHEiJLOwdmFP+wzCmDEkc9y7NsYxeF4u7Btsn1ZuwgwJGxImImHicJArLP4R0yX4c2KCrMrTA==} - engines: {node: '>= 0.4'} - - side-channel-map@1.0.1: - resolution: {integrity: sha512-VCjCNfgMsby3tTdo02nbjtM/ewra6jPHmpThenkTYh8pG9ucZ/1P8So4u4FGBek/BjpOVsDCMoLA/iuBKIFXRA==} - engines: {node: '>= 0.4'} - - side-channel-weakmap@1.0.2: - resolution: {integrity: sha512-WPS/HvHQTYnHisLo9McqBHOJk2FkHO/tlpvldyrnem4aeQp4hai3gythswg6p01oSoTl58rcpiFAjF2br2Ak2A==} - engines: {node: '>= 0.4'} - - side-channel@1.1.0: - resolution: {integrity: sha512-ZX99e6tRweoUXqR+VBrslhda51Nh5MTQwou5tnUDgbtyM0dBgmhEDtWGP/xbKn6hqfPRHujUNwz5fy/wbbhnpw==} - engines: {node: '>= 0.4'} - - signal-exit@3.0.7: - resolution: {integrity: sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==} - - simple-concat@1.0.1: - resolution: {integrity: sha512-cSFtAPtRhljv69IK0hTVZQ+OfE9nePi/rtJmw5UjHeVyVroEqJXP1sFztKUy1qU+xvz3u/sfYJLa947b7nAN2Q==} - - simple-get@4.0.1: - resolution: {integrity: sha512-brv7p5WgH0jmQJr1ZDDfKDOSeWWg+OVypG99A/5vYGPqJ6pxiaHLy8nxtFjBA7oMa01ebA9gfh1uMCFqOuXxvA==} - - simple-update-notifier@2.0.0: - resolution: {integrity: sha512-a2B9Y0KlNXl9u/vsW6sTIu9vGEpfKu2wRV6l1H3XEas/0gUIzGzBoP/IouTcUQbm9JWZLH3COxyn03TYlFax6w==} - engines: {node: '>=10'} - - sqlstring@2.3.1: - resolution: {integrity: sha512-ooAzh/7dxIG5+uDik1z/Rd1vli0+38izZhGzSa34FwR7IbelPWCCKSNIl8jlL/F7ERvy8CB2jNeM1E9i9mXMAQ==} - engines: {node: '>= 0.6'} - - statuses@2.0.1: - resolution: {integrity: sha512-RwNA9Z/7PrK06rYLIzFMlaF+l73iwpzsqRIFgbMLbTcLD6cOao82TaWefPXQvB2fOC4AjuYSEndS7N/mTCbkdQ==} - engines: {node: '>= 0.8'} - - string-width@4.2.3: - resolution: {integrity: sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==} - engines: {node: '>=8'} - - string_decoder@1.1.1: - resolution: {integrity: sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==} - - string_decoder@1.3.0: - resolution: {integrity: sha512-hkRX8U1WjJFd8LsDJ2yQ/wWWxaopEsABU1XfkM8A+j0+85JAGppt16cr1Whg6KIbb4okU6Mql6BOj+uup/wKeA==} - - strip-ansi@6.0.1: - resolution: {integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==} - engines: {node: '>=8'} - - strip-json-comments@2.0.1: - resolution: {integrity: sha512-4gB8na07fecVVkOI6Rs4e7T6NOTki5EmL7TUduTs6bu3EdnSycntVJ4re8kgZA+wx9IueI2Y11bfbgwtzuE0KQ==} - engines: {node: '>=0.10.0'} - - supports-color@5.5.0: - resolution: {integrity: sha512-QjVjwdXIt408MIiAqCX4oUKsgU2EqAGzs2Ppkm4aQYbjm+ZEWEcW4SfFNTr4uMNZma0ey4f5lgLrkB0aX0QMow==} - engines: {node: '>=4'} - - symbol-tree@3.2.4: - resolution: {integrity: sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw==} - - tar-fs@2.1.2: - resolution: {integrity: sha512-EsaAXwxmx8UB7FRKqeozqEPop69DXcmYwTQwXvyAPF352HJsPdkVhvTaDPYqfNgruveJIJy3TA2l+2zj8LJIJA==} - - tar-stream@2.2.0: - resolution: {integrity: sha512-ujeqbceABgwMZxEJnk2HDY2DlnUZ+9oEcb1KzTVfYHio0UE6dG71n60d8D2I4qNvleWrrXpmjpt7vZeF1LnMZQ==} - engines: {node: '>=6'} - - tar@6.2.1: - resolution: {integrity: sha512-DZ4yORTwrbTj/7MZYq2w+/ZFdI6OZ/f9SFHR+71gIVUZhOQPHzVCLpvRnPgyaMpfWxxk/4ONva3GQSyNIKRv6A==} - engines: {node: '>=10'} - - tldts-core@6.1.86: - resolution: {integrity: sha512-Je6p7pkk+KMzMv2XXKmAE3McmolOQFdxkKw0R8EYNr7sELW46JqnNeTX8ybPiQgvg1ymCoF8LXs5fzFaZvJPTA==} - - tldts@6.1.86: - resolution: {integrity: sha512-WMi/OQ2axVTf/ykqCQgXiIct+mSQDFdH2fkwhPwgEwvJ1kSzZRiinb0zF2Xb8u4+OqPChmyI6MEu4EezNJz+FQ==} - hasBin: true - - to-regex-range@5.0.1: - resolution: {integrity: sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==} - engines: {node: '>=8.0'} - - toidentifier@1.0.1: - resolution: {integrity: sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==} - engines: {node: '>=0.6'} - - touch@3.1.1: - resolution: {integrity: sha512-r0eojU4bI8MnHr8c5bNo7lJDdI2qXlWWJk6a9EAFG7vbhTjElYhBVS3/miuE0uOuoLdb8Mc/rVfsmm6eo5o9GA==} - hasBin: true - - tough-cookie@5.1.2: - resolution: {integrity: sha512-FVDYdxtnj0G6Qm/DhNPSb8Ju59ULcup3tuJxkFb5K8Bv2pUXILbf0xZWU8PX8Ov19OXljbUyveOFwRMwkXzO+A==} - engines: {node: '>=16'} - - tr46@0.0.3: - resolution: {integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==} - - tr46@5.1.1: - resolution: {integrity: sha512-hdF5ZgjTqgAntKkklYw0R03MG2x/bSzTtkxmIRw/sTNV8YXsCJ1tfLAX23lhxhHJlEf3CRCOCGGWw3vI3GaSPw==} - engines: {node: '>=18'} - - tunnel-agent@0.6.0: - resolution: {integrity: sha512-McnNiV1l8RYeY8tBgEpuodCC1mLUdbSN+CYBL7kJsJNInOP8UjDDEwdk6Mw60vdLLrr5NHKZhMAOSrR2NZuQ+w==} - - type-is@2.0.1: - resolution: {integrity: sha512-OZs6gsjF4vMp32qrCbiVSkrFmXtG/AZhY3t0iAMrMBiAZyV9oALtXO8hsrHbMXF9x6L3grlFuwW2oAz7cav+Gw==} - engines: {node: '>= 0.6'} - - undefsafe@2.0.5: - resolution: {integrity: sha512-WxONCrssBM8TSPRqN5EmsjVrsv4A8X12J4ArBiiayv3DyyG3ZlIg6yysuuSYdZsVz3TKcTg2fd//Ujd4CHV1iA==} - - unpipe@1.0.0: - resolution: {integrity: sha512-pjy2bYhSsufwWlKwPc+l3cN7+wuJlK6uz0YdJEOlQDbl6jo/YlPi4mb8agUkVC8BF7V8NuzeyPNqRksA3hztKQ==} - engines: {node: '>= 0.8'} - - util-deprecate@1.0.2: - resolution: {integrity: sha512-EPD5q1uXyFxJpCrLnCc1nHnq3gOa6DZBocAIiI2TaSCA7VCJ1UJDMagCzIkXNsUYfD1daK//LTEQ8xiIbrHtcw==} - - vary@1.1.2: - resolution: {integrity: sha512-BNGbWLfd0eUPabhkXUVm0j8uuvREyTh5ovRa/dyow/BqAbZJyC+5fU+IzQOzmAKzYqYRAISoRhdQr3eIZ/PXqg==} - engines: {node: '>= 0.8'} - - w3c-xmlserializer@5.0.0: - resolution: {integrity: sha512-o8qghlI8NZHU1lLPrpi2+Uq7abh4GGPpYANlalzWxyWteJOCsr/P+oPBA49TOLu5FTZO4d3F9MnWJfiMo4BkmA==} - engines: {node: '>=18'} - - webidl-conversions@3.0.1: - resolution: {integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==} - - webidl-conversions@7.0.0: - resolution: {integrity: sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==} - engines: {node: '>=12'} - - whatwg-encoding@3.1.1: - resolution: {integrity: sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==} - engines: {node: '>=18'} - - whatwg-mimetype@4.0.0: - resolution: {integrity: sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==} - engines: {node: '>=18'} - - whatwg-url@14.2.0: - resolution: {integrity: sha512-De72GdQZzNTUBBChsXueQUnPKDkg/5A5zp7pFDuQAj5UFoENpiACU0wlCvzpAGnTkj++ihpKwKyYewn/XNUbKw==} - engines: {node: '>=18'} - - whatwg-url@5.0.0: - resolution: {integrity: sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==} - - wide-align@1.1.5: - resolution: {integrity: sha512-eDMORYaPNZ4sQIuuYPDHdQvf4gyCF9rEEV/yPxGfwPkRodwEgiMUUXTx/dex+Me0wxx53S+NgUHaP7y3MGlDmg==} - - wrappy@1.0.2: - resolution: {integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==} - - ws@8.18.1: - resolution: {integrity: sha512-RKW2aJZMXeMxVpnZ6bck+RswznaxmzdULiBr6KY7XkTnW8uvt0iT9H5DkHUChXrc+uurzwa0rVI16n/Xzjdz1w==} - engines: {node: '>=10.0.0'} - peerDependencies: - bufferutil: ^4.0.1 - utf-8-validate: '>=5.0.2' - peerDependenciesMeta: - bufferutil: - optional: true - utf-8-validate: - optional: true - - xml-name-validator@5.0.0: - resolution: {integrity: sha512-EvGK8EJ3DhaHfbRlETOWAS5pO9MZITeauHKJyb8wyajUfQUenkIg2MvLDTZ4T/TgIcm3HU0TFBgWWboAZ30UHg==} - engines: {node: '>=18'} - - xmlchars@2.2.0: - resolution: {integrity: sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw==} - - yallist@4.0.0: - resolution: {integrity: sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==} - -snapshots: - - '@asamuzakjp/css-color@3.1.4': - dependencies: - '@csstools/css-calc': 2.1.3(@csstools/css-parser-algorithms@3.0.4(@csstools/css-tokenizer@3.0.3))(@csstools/css-tokenizer@3.0.3) - '@csstools/css-color-parser': 3.0.9(@csstools/css-parser-algorithms@3.0.4(@csstools/css-tokenizer@3.0.3))(@csstools/css-tokenizer@3.0.3) - '@csstools/css-parser-algorithms': 3.0.4(@csstools/css-tokenizer@3.0.3) - '@csstools/css-tokenizer': 3.0.3 - lru-cache: 10.4.3 - - '@csstools/color-helpers@5.0.2': {} - - '@csstools/css-calc@2.1.3(@csstools/css-parser-algorithms@3.0.4(@csstools/css-tokenizer@3.0.3))(@csstools/css-tokenizer@3.0.3)': - dependencies: - '@csstools/css-parser-algorithms': 3.0.4(@csstools/css-tokenizer@3.0.3) - '@csstools/css-tokenizer': 3.0.3 - - '@csstools/css-color-parser@3.0.9(@csstools/css-parser-algorithms@3.0.4(@csstools/css-tokenizer@3.0.3))(@csstools/css-tokenizer@3.0.3)': - dependencies: - '@csstools/color-helpers': 5.0.2 - '@csstools/css-calc': 2.1.3(@csstools/css-parser-algorithms@3.0.4(@csstools/css-tokenizer@3.0.3))(@csstools/css-tokenizer@3.0.3) - '@csstools/css-parser-algorithms': 3.0.4(@csstools/css-tokenizer@3.0.3) - '@csstools/css-tokenizer': 3.0.3 - - '@csstools/css-parser-algorithms@3.0.4(@csstools/css-tokenizer@3.0.3)': - dependencies: - '@csstools/css-tokenizer': 3.0.3 - - '@csstools/css-tokenizer@3.0.3': {} - - '@mapbox/node-pre-gyp@1.0.11': - dependencies: - detect-libc: 2.0.4 - https-proxy-agent: 5.0.1 - make-dir: 3.1.0 - node-fetch: 2.7.0 - nopt: 5.0.0 - npmlog: 5.0.1 - rimraf: 3.0.2 - semver: 7.7.1 - tar: 6.2.1 - transitivePeerDependencies: - - encoding - - supports-color - - '@types/trusted-types@2.0.7': - optional: true - - abbrev@1.1.1: {} - - accepts@2.0.0: - dependencies: - mime-types: 3.0.1 - negotiator: 1.0.0 - - agent-base@6.0.2: - dependencies: - debug: 4.4.0(supports-color@5.5.0) - transitivePeerDependencies: - - supports-color - - agent-base@7.1.3: {} - - ajv@8.17.1: - dependencies: - fast-deep-equal: 3.1.3 - fast-uri: 3.0.6 - json-schema-traverse: 1.0.0 - require-from-string: 2.0.2 - - ansi-regex@5.0.1: {} - - anymatch@3.1.3: - dependencies: - normalize-path: 3.0.0 - picomatch: 2.3.1 - - aproba@2.0.0: {} - - are-we-there-yet@2.0.0: - dependencies: - delegates: 1.0.0 - readable-stream: 3.6.2 - - balanced-match@1.0.2: {} - - base64-js@1.5.1: {} - - bcrypt@5.1.1: - dependencies: - '@mapbox/node-pre-gyp': 1.0.11 - node-addon-api: 5.1.0 - transitivePeerDependencies: - - encoding - - supports-color - - better-sqlite3@11.9.1: - dependencies: - bindings: 1.5.0 - prebuild-install: 7.1.3 - - bignumber.js@9.0.0: {} - - binary-extensions@2.3.0: {} - - bindings@1.5.0: - dependencies: - file-uri-to-path: 1.0.0 - - bl@4.1.0: - dependencies: - buffer: 5.7.1 - inherits: 2.0.4 - readable-stream: 3.6.2 - - body-parser@2.2.0: - dependencies: - bytes: 3.1.2 - content-type: 1.0.5 - debug: 4.4.0(supports-color@5.5.0) - http-errors: 2.0.0 - iconv-lite: 0.6.3 - on-finished: 2.4.1 - qs: 6.14.0 - raw-body: 3.0.0 - type-is: 2.0.1 - transitivePeerDependencies: - - supports-color - - brace-expansion@1.1.11: - dependencies: - balanced-match: 1.0.2 - concat-map: 0.0.1 - - braces@3.0.3: - dependencies: - fill-range: 7.1.1 - - buffer-equal-constant-time@1.0.1: {} - - buffer@5.7.1: - dependencies: - base64-js: 1.5.1 - ieee754: 1.2.1 - - bytes@3.1.2: {} - - call-bind-apply-helpers@1.0.2: - dependencies: - es-errors: 1.3.0 - function-bind: 1.1.2 - - call-bound@1.0.4: - dependencies: - call-bind-apply-helpers: 1.0.2 - get-intrinsic: 1.3.0 - - chokidar@3.6.0: - dependencies: - anymatch: 3.1.3 - braces: 3.0.3 - glob-parent: 5.1.2 - is-binary-path: 2.1.0 - is-glob: 4.0.3 - normalize-path: 3.0.0 - readdirp: 3.6.0 - optionalDependencies: - fsevents: 2.3.3 - - chownr@1.1.4: {} - - chownr@2.0.0: {} - - color-support@1.1.3: {} - - concat-map@0.0.1: {} - - console-control-strings@1.1.0: {} - - content-disposition@1.0.0: - dependencies: - safe-buffer: 5.2.1 - - content-type@1.0.5: {} - - cookie-signature@1.2.2: {} - - cookie@0.7.2: {} - - core-util-is@1.0.3: {} - - cssstyle@4.3.1: - dependencies: - '@asamuzakjp/css-color': 3.1.4 - rrweb-cssom: 0.8.0 - - data-urls@5.0.0: - dependencies: - whatwg-mimetype: 4.0.0 - whatwg-url: 14.2.0 - - debug@4.4.0(supports-color@5.5.0): - dependencies: - ms: 2.1.3 - optionalDependencies: - supports-color: 5.5.0 - - decimal.js@10.5.0: {} - - decompress-response@6.0.0: - dependencies: - mimic-response: 3.1.0 - - deep-extend@0.6.0: {} - - delegates@1.0.0: {} - - depd@2.0.0: {} - - detect-libc@2.0.4: {} - - dompurify@3.2.5: - optionalDependencies: - '@types/trusted-types': 2.0.7 - - dunder-proto@1.0.1: - dependencies: - call-bind-apply-helpers: 1.0.2 - es-errors: 1.3.0 - gopd: 1.2.0 - - ecdsa-sig-formatter@1.0.11: - dependencies: - safe-buffer: 5.2.1 - - ee-first@1.1.1: {} - - emoji-regex@8.0.0: {} - - encodeurl@2.0.0: {} - - end-of-stream@1.4.4: - dependencies: - once: 1.4.0 - - entities@6.0.0: {} - - es-define-property@1.0.1: {} - - es-errors@1.3.0: {} - - es-object-atoms@1.1.1: - dependencies: - es-errors: 1.3.0 - - escape-html@1.0.3: {} - - etag@1.8.1: {} - - expand-template@2.0.3: {} - - express@5.1.0: - dependencies: - accepts: 2.0.0 - body-parser: 2.2.0 - content-disposition: 1.0.0 - content-type: 1.0.5 - cookie: 0.7.2 - cookie-signature: 1.2.2 - debug: 4.4.0(supports-color@5.5.0) - encodeurl: 2.0.0 - escape-html: 1.0.3 - etag: 1.8.1 - finalhandler: 2.1.0 - fresh: 2.0.0 - http-errors: 2.0.0 - merge-descriptors: 2.0.0 - mime-types: 3.0.1 - on-finished: 2.4.1 - once: 1.4.0 - parseurl: 1.3.3 - proxy-addr: 2.0.7 - qs: 6.14.0 - range-parser: 1.2.1 - router: 2.2.0 - send: 1.2.0 - serve-static: 2.2.0 - statuses: 2.0.1 - type-is: 2.0.1 - vary: 1.1.2 - transitivePeerDependencies: - - supports-color - - fast-deep-equal@3.1.3: {} - - fast-uri@3.0.6: {} - - file-uri-to-path@1.0.0: {} - - fill-range@7.1.1: - dependencies: - to-regex-range: 5.0.1 - - finalhandler@2.1.0: - dependencies: - debug: 4.4.0(supports-color@5.5.0) - encodeurl: 2.0.0 - escape-html: 1.0.3 - on-finished: 2.4.1 - parseurl: 1.3.3 - statuses: 2.0.1 - transitivePeerDependencies: - - supports-color - - forwarded@0.2.0: {} - - fresh@2.0.0: {} - - fs-constants@1.0.0: {} - - fs-minipass@2.1.0: - dependencies: - minipass: 3.3.6 - - fs.realpath@1.0.0: {} - - fsevents@2.3.3: - optional: true - - function-bind@1.1.2: {} - - gauge@3.0.2: - dependencies: - aproba: 2.0.0 - color-support: 1.1.3 - console-control-strings: 1.1.0 - has-unicode: 2.0.1 - object-assign: 4.1.1 - signal-exit: 3.0.7 - string-width: 4.2.3 - strip-ansi: 6.0.1 - wide-align: 1.1.5 - - get-intrinsic@1.3.0: - dependencies: - call-bind-apply-helpers: 1.0.2 - es-define-property: 1.0.1 - es-errors: 1.3.0 - es-object-atoms: 1.1.1 - function-bind: 1.1.2 - get-proto: 1.0.1 - gopd: 1.2.0 - has-symbols: 1.1.0 - hasown: 2.0.2 - math-intrinsics: 1.1.0 - - get-proto@1.0.1: - dependencies: - dunder-proto: 1.0.1 - es-object-atoms: 1.1.1 - - github-from-package@0.0.0: {} - - glob-parent@5.1.2: - dependencies: - is-glob: 4.0.3 - - glob@7.2.3: - dependencies: - fs.realpath: 1.0.0 - inflight: 1.0.6 - inherits: 2.0.4 - minimatch: 3.1.2 - once: 1.4.0 - path-is-absolute: 1.0.1 - - gopd@1.2.0: {} - - has-flag@3.0.0: {} - - has-symbols@1.1.0: {} - - has-unicode@2.0.1: {} - - hasown@2.0.2: - dependencies: - function-bind: 1.1.2 - - html-encoding-sniffer@4.0.0: - dependencies: - whatwg-encoding: 3.1.1 - - http-errors@2.0.0: - dependencies: - depd: 2.0.0 - inherits: 2.0.4 - setprototypeof: 1.2.0 - statuses: 2.0.1 - toidentifier: 1.0.1 - - http-proxy-agent@7.0.2: - dependencies: - agent-base: 7.1.3 - debug: 4.4.0(supports-color@5.5.0) - transitivePeerDependencies: - - supports-color - - https-proxy-agent@5.0.1: - dependencies: - agent-base: 6.0.2 - debug: 4.4.0(supports-color@5.5.0) - transitivePeerDependencies: - - supports-color - - https-proxy-agent@7.0.6: - dependencies: - agent-base: 7.1.3 - debug: 4.4.0(supports-color@5.5.0) - transitivePeerDependencies: - - supports-color - - iconv-lite@0.6.3: - dependencies: - safer-buffer: 2.1.2 - - ieee754@1.2.1: {} - - ignore-by-default@1.0.1: {} - - inflight@1.0.6: - dependencies: - once: 1.4.0 - wrappy: 1.0.2 - - inherits@2.0.4: {} - - ini@1.3.8: {} - - ipaddr.js@1.9.1: {} - - is-binary-path@2.1.0: - dependencies: - binary-extensions: 2.3.0 - - is-extglob@2.1.1: {} - - is-fullwidth-code-point@3.0.0: {} - - is-glob@4.0.3: - dependencies: - is-extglob: 2.1.1 - - is-number@7.0.0: {} - - is-potential-custom-element-name@1.0.1: {} - - is-promise@4.0.0: {} - - isarray@1.0.0: {} - - jsdom@26.1.0: - dependencies: - cssstyle: 4.3.1 - data-urls: 5.0.0 - decimal.js: 10.5.0 - html-encoding-sniffer: 4.0.0 - http-proxy-agent: 7.0.2 - https-proxy-agent: 7.0.6 - is-potential-custom-element-name: 1.0.1 - nwsapi: 2.2.20 - parse5: 7.3.0 - rrweb-cssom: 0.8.0 - saxes: 6.0.0 - symbol-tree: 3.2.4 - tough-cookie: 5.1.2 - w3c-xmlserializer: 5.0.0 - webidl-conversions: 7.0.0 - whatwg-encoding: 3.1.1 - whatwg-mimetype: 4.0.0 - whatwg-url: 14.2.0 - ws: 8.18.1 - xml-name-validator: 5.0.0 - transitivePeerDependencies: - - bufferutil - - supports-color - - utf-8-validate - - json-schema-traverse@1.0.0: {} - - jsonwebtoken@9.0.2: - dependencies: - jws: 3.2.2 - lodash.includes: 4.3.0 - lodash.isboolean: 3.0.3 - lodash.isinteger: 4.0.4 - lodash.isnumber: 3.0.3 - lodash.isplainobject: 4.0.6 - lodash.isstring: 4.0.1 - lodash.once: 4.1.1 - ms: 2.1.3 - semver: 7.7.1 - - jwa@1.4.1: - dependencies: - buffer-equal-constant-time: 1.0.1 - ecdsa-sig-formatter: 1.0.11 - safe-buffer: 5.2.1 - - jws@3.2.2: - dependencies: - jwa: 1.4.1 - safe-buffer: 5.2.1 - - lodash.includes@4.3.0: {} - - lodash.isboolean@3.0.3: {} - - lodash.isinteger@4.0.4: {} - - lodash.isnumber@3.0.3: {} - - lodash.isplainobject@4.0.6: {} - - lodash.isstring@4.0.1: {} - - lodash.once@4.1.1: {} - - lru-cache@10.4.3: {} - - make-dir@3.1.0: - dependencies: - semver: 6.3.1 - - marked@15.0.10: {} - - math-intrinsics@1.1.0: {} - - media-typer@1.1.0: {} - - merge-descriptors@2.0.0: {} - - mime-db@1.54.0: {} - - mime-types@3.0.1: - dependencies: - mime-db: 1.54.0 - - mimic-response@3.1.0: {} - - minimatch@3.1.2: - dependencies: - brace-expansion: 1.1.11 - - minimist@1.2.8: {} - - minipass@3.3.6: - dependencies: - yallist: 4.0.0 - - minipass@5.0.0: {} - - minizlib@2.1.2: - dependencies: - minipass: 3.3.6 - yallist: 4.0.0 - - mkdirp-classic@0.5.3: {} - - mkdirp@1.0.4: {} - - ms@2.1.3: {} - - mysql@2.18.1: - dependencies: - bignumber.js: 9.0.0 - readable-stream: 2.3.7 - safe-buffer: 5.1.2 - sqlstring: 2.3.1 - - napi-build-utils@2.0.0: {} - - negotiator@1.0.0: {} - - node-abi@3.74.0: - dependencies: - semver: 7.7.1 - - node-addon-api@5.1.0: {} - - node-fetch@2.7.0: - dependencies: - whatwg-url: 5.0.0 - - nodemon@3.1.10: - dependencies: - chokidar: 3.6.0 - debug: 4.4.0(supports-color@5.5.0) - ignore-by-default: 1.0.1 - minimatch: 3.1.2 - pstree.remy: 1.1.8 - semver: 7.7.1 - simple-update-notifier: 2.0.0 - supports-color: 5.5.0 - touch: 3.1.1 - undefsafe: 2.0.5 - - nopt@5.0.0: - dependencies: - abbrev: 1.1.1 - - normalize-path@3.0.0: {} - - npmlog@5.0.1: - dependencies: - are-we-there-yet: 2.0.0 - console-control-strings: 1.1.0 - gauge: 3.0.2 - set-blocking: 2.0.0 - - nwsapi@2.2.20: {} - - object-assign@4.1.1: {} - - object-inspect@1.13.4: {} - - on-finished@2.4.1: - dependencies: - ee-first: 1.1.1 - - once@1.4.0: - dependencies: - wrappy: 1.0.2 - - parse5@7.3.0: - dependencies: - entities: 6.0.0 - - parseurl@1.3.3: {} - - path-is-absolute@1.0.1: {} - - path-to-regexp@8.2.0: {} - - picomatch@2.3.1: {} - - prebuild-install@7.1.3: - dependencies: - detect-libc: 2.0.4 - expand-template: 2.0.3 - github-from-package: 0.0.0 - minimist: 1.2.8 - mkdirp-classic: 0.5.3 - napi-build-utils: 2.0.0 - node-abi: 3.74.0 - pump: 3.0.2 - rc: 1.2.8 - simple-get: 4.0.1 - tar-fs: 2.1.2 - tunnel-agent: 0.6.0 - - process-nextick-args@2.0.1: {} - - proxy-addr@2.0.7: - dependencies: - forwarded: 0.2.0 - ipaddr.js: 1.9.1 - - pstree.remy@1.1.8: {} - - pump@3.0.2: - dependencies: - end-of-stream: 1.4.4 - once: 1.4.0 - - punycode@2.3.1: {} - - qs@6.14.0: - dependencies: - side-channel: 1.1.0 - - range-parser@1.2.1: {} - - raw-body@3.0.0: - dependencies: - bytes: 3.1.2 - http-errors: 2.0.0 - iconv-lite: 0.6.3 - unpipe: 1.0.0 - - rc@1.2.8: - dependencies: - deep-extend: 0.6.0 - ini: 1.3.8 - minimist: 1.2.8 - strip-json-comments: 2.0.1 - - readable-stream@2.3.7: - dependencies: - core-util-is: 1.0.3 - inherits: 2.0.4 - isarray: 1.0.0 - process-nextick-args: 2.0.1 - safe-buffer: 5.1.2 - string_decoder: 1.1.1 - util-deprecate: 1.0.2 - - readable-stream@3.6.2: - dependencies: - inherits: 2.0.4 - string_decoder: 1.3.0 - util-deprecate: 1.0.2 - - readdirp@3.6.0: - dependencies: - picomatch: 2.3.1 - - require-from-string@2.0.2: {} - - rimraf@3.0.2: - dependencies: - glob: 7.2.3 - - router@2.2.0: - dependencies: - debug: 4.4.0(supports-color@5.5.0) - depd: 2.0.0 - is-promise: 4.0.0 - parseurl: 1.3.3 - path-to-regexp: 8.2.0 - transitivePeerDependencies: - - supports-color - - rrweb-cssom@0.8.0: {} - - safe-buffer@5.1.2: {} - - safe-buffer@5.2.1: {} - - safer-buffer@2.1.2: {} - - saxes@6.0.0: - dependencies: - xmlchars: 2.2.0 - - semver@6.3.1: {} - - semver@7.7.1: {} - - send@1.2.0: - dependencies: - debug: 4.4.0(supports-color@5.5.0) - encodeurl: 2.0.0 - escape-html: 1.0.3 - etag: 1.8.1 - fresh: 2.0.0 - http-errors: 2.0.0 - mime-types: 3.0.1 - ms: 2.1.3 - on-finished: 2.4.1 - range-parser: 1.2.1 - statuses: 2.0.1 - transitivePeerDependencies: - - supports-color - - serve-static@2.2.0: - dependencies: - encodeurl: 2.0.0 - escape-html: 1.0.3 - parseurl: 1.3.3 - send: 1.2.0 - transitivePeerDependencies: - - supports-color - - set-blocking@2.0.0: {} - - setprototypeof@1.2.0: {} - - side-channel-list@1.0.0: - dependencies: - es-errors: 1.3.0 - object-inspect: 1.13.4 - - side-channel-map@1.0.1: - dependencies: - call-bound: 1.0.4 - es-errors: 1.3.0 - get-intrinsic: 1.3.0 - object-inspect: 1.13.4 - - side-channel-weakmap@1.0.2: - dependencies: - call-bound: 1.0.4 - es-errors: 1.3.0 - get-intrinsic: 1.3.0 - object-inspect: 1.13.4 - side-channel-map: 1.0.1 - - side-channel@1.1.0: - dependencies: - es-errors: 1.3.0 - object-inspect: 1.13.4 - side-channel-list: 1.0.0 - side-channel-map: 1.0.1 - side-channel-weakmap: 1.0.2 - - signal-exit@3.0.7: {} - - simple-concat@1.0.1: {} - - simple-get@4.0.1: - dependencies: - decompress-response: 6.0.0 - once: 1.4.0 - simple-concat: 1.0.1 - - simple-update-notifier@2.0.0: - dependencies: - semver: 7.7.1 - - sqlstring@2.3.1: {} - - statuses@2.0.1: {} - - string-width@4.2.3: - dependencies: - emoji-regex: 8.0.0 - is-fullwidth-code-point: 3.0.0 - strip-ansi: 6.0.1 - - string_decoder@1.1.1: - dependencies: - safe-buffer: 5.1.2 - - string_decoder@1.3.0: - dependencies: - safe-buffer: 5.2.1 - - strip-ansi@6.0.1: - dependencies: - ansi-regex: 5.0.1 - - strip-json-comments@2.0.1: {} - - supports-color@5.5.0: - dependencies: - has-flag: 3.0.0 - - symbol-tree@3.2.4: {} - - tar-fs@2.1.2: - dependencies: - chownr: 1.1.4 - mkdirp-classic: 0.5.3 - pump: 3.0.2 - tar-stream: 2.2.0 - - tar-stream@2.2.0: - dependencies: - bl: 4.1.0 - end-of-stream: 1.4.4 - fs-constants: 1.0.0 - inherits: 2.0.4 - readable-stream: 3.6.2 - - tar@6.2.1: - dependencies: - chownr: 2.0.0 - fs-minipass: 2.1.0 - minipass: 5.0.0 - minizlib: 2.1.2 - mkdirp: 1.0.4 - yallist: 4.0.0 - - tldts-core@6.1.86: {} - - tldts@6.1.86: - dependencies: - tldts-core: 6.1.86 - - to-regex-range@5.0.1: - dependencies: - is-number: 7.0.0 - - toidentifier@1.0.1: {} - - touch@3.1.1: {} - - tough-cookie@5.1.2: - dependencies: - tldts: 6.1.86 - - tr46@0.0.3: {} - - tr46@5.1.1: - dependencies: - punycode: 2.3.1 - - tunnel-agent@0.6.0: - dependencies: - safe-buffer: 5.2.1 - - type-is@2.0.1: - dependencies: - content-type: 1.0.5 - media-typer: 1.1.0 - mime-types: 3.0.1 - - undefsafe@2.0.5: {} - - unpipe@1.0.0: {} - - util-deprecate@1.0.2: {} - - vary@1.1.2: {} - - w3c-xmlserializer@5.0.0: - dependencies: - xml-name-validator: 5.0.0 - - webidl-conversions@3.0.1: {} - - webidl-conversions@7.0.0: {} - - whatwg-encoding@3.1.1: - dependencies: - iconv-lite: 0.6.3 - - whatwg-mimetype@4.0.0: {} - - whatwg-url@14.2.0: - dependencies: - tr46: 5.1.1 - webidl-conversions: 7.0.0 - - whatwg-url@5.0.0: - dependencies: - tr46: 0.0.3 - webidl-conversions: 3.0.1 - - wide-align@1.1.5: - dependencies: - string-width: 4.2.3 - - wrappy@1.0.2: {} - - ws@8.18.1: {} - - xml-name-validator@5.0.0: {} - - xmlchars@2.2.0: {} - - yallist@4.0.0: {} diff --git a/server.js b/server.js deleted file mode 100644 index 33b1df6..0000000 --- a/server.js +++ /dev/null @@ -1,38 +0,0 @@ -// --- Imports --- - -const express = require("express"); -const app = express(); -const configManager = require("./src/utils/configManager"); -const { connectDatabase, initDatabase } = require('./src/database/index'); - - -// --- Load configuration --- -const config = configManager.loadConfig(); - -// --- Body parsing --- -app.use(express.json()); // Necessary to parse JSON bodies - -// Database connection -(async () => { - - - // --- Database connection --- - await connectDatabase(); - await initDatabase(); - - // --- Routing --- - app.use("/", require("./src/routes/index")); - app.use("/mods", require("./src/routes/mods")); - app.use("/users", require("./src/routes/users")); - app.use("/list", require("./src/routes/list")); - app.use("/login", require("./src/routes/login")); - -})(); - - -// --- Launch --- - -const port = config.port; -app.listen(port, () => { - console.log("Server listening on port " + port + "..."); -}) \ No newline at end of file diff --git a/src/controllers/auth.js b/src/controllers/auth.js deleted file mode 100644 index 7bd6571..0000000 --- a/src/controllers/auth.js +++ /dev/null @@ -1,17 +0,0 @@ -const handleError = require("../middleware/errors"); -const authService = require("../services/authService"); - -async function login(req, res) { - try { - const username = req.body.username; - const email = req.body.email; - const password = req.body.password - const token = await authService.login(username, email, password); - res.json({ token }); - } catch (err) { - handleError(err, res); - } - -} - -module.exports = { login }; \ No newline at end of file diff --git a/src/controllers/index.js b/src/controllers/index.js deleted file mode 100644 index 3580e6b..0000000 --- a/src/controllers/index.js +++ /dev/null @@ -1,14 +0,0 @@ -const index_service = require("../services/indexService"); -const handleError = require("../middleware/errors"); - - -async function getVersion(req, res) { - try { - const query_result = await index_service.getVersion(); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - -module.exports = { getVersion }; \ No newline at end of file diff --git a/src/controllers/modpacks.js b/src/controllers/modpacks.js deleted file mode 100644 index e69de29..0000000 diff --git a/src/controllers/mods.js b/src/controllers/mods.js deleted file mode 100644 index d1f36dc..0000000 --- a/src/controllers/mods.js +++ /dev/null @@ -1,68 +0,0 @@ -const handleError = require("../middleware/errors"); -const mod_service = require("../services/modService"); -const { authorizeModModification, authenticateToken } = require("../middleware/auth"); - -async function listMods(req, res) { - try { - // Query - const query_result = await mod_service.getAllMods(); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - -async function createMod(req, res) { - try { - // Authenticate - await authenticateToken(req); - // Query - const mod_data = req.body; - const user = req.token_infos.username; - const query_result = await mod_service.createMod(mod_data, user); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - -async function modifyMod(req, res) { - try { - // Authorize - authorizeModModification(req); - // Query - const mod_data = req.body; - const query_result = await mod_service.modifyMod(mod_data); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - -async function getModByName(req, res) { - try { - // Query - const name = req.params.name - const query_result = await mod_service.getModByName(name); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - -async function deleteMod(req, res) { - try { - // Authorize - authorizeModModification(req); - // Query - const name = req.params.name - const query_result = await mod_service.deleteMod(name); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - - - -module.exports = { listMods, getModByName, createMod, modifyMod, deleteMod }; \ No newline at end of file diff --git a/src/controllers/users.js b/src/controllers/users.js deleted file mode 100644 index 71e475f..0000000 --- a/src/controllers/users.js +++ /dev/null @@ -1,63 +0,0 @@ -const handleError = require("../middleware/errors"); -const user_service = require("../services/userService") -const { authorizeUserModification } = require("../middleware/auth"); - - -async function listUsers(req, res) { - try { - // Query - const query_result = await user_service.getAllUsers(); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - -async function getUserByName(req, res) { - try { - // Query - const query_result = await user_service.getUserByName(req.params.name); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - -async function createUser(req, res) { - try { - // Query - const query_result = await user_service.createUser(req.body); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - -async function modifyUser(req, res) { - try { - // Query - const diff_data = req.body; - const query_result = await user_service.modifyUser(diff_data); - res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - -async function deleteUser(req, res) { - try { - // Authenticate - await authorizeUserModification(req); - // Query - const user = req.params.name; - const token_user = req.token_infos - const query_result = await user_service.deleteUser(user, token_user); - return res.json(query_result); - } catch (error) { - handleError(error, res); - } -} - - - -module.exports = { listUsers, getUserByName, createUser, modifyUser, deleteUser }; \ No newline at end of file diff --git a/src/database/index.js b/src/database/index.js deleted file mode 100644 index 1399795..0000000 --- a/src/database/index.js +++ /dev/null @@ -1,112 +0,0 @@ -const MySQLDatabase = require("./mysql"); -const SQLiteDatabase = require("./sqlite"); -const { getConfig } = require("../utils/configManager"); - -let db; - -async function connectDatabase() { - - // Get config - const config = await getConfig(); - - // Choose database type - if (config.database.type === "mysql") { - db = new MySQLDatabase(config.database); - } else if (config.database.type === "sqlite") { - db = new SQLiteDatabase(config.database); - } else { - throw new Error("Invalid database type: ", config.database.type); - } - - // Connect - await db.connect(); - return db; -} - - -// Setups the database by creating the tables and the default objects -async function initDatabase() { - - if (!db) { - throw new Error("Database is not connected"); - } - - // --- Users --- - - // Uers table - db.exec(`CREATE TABLE IF NOT EXISTS Users ( - username TINYTEXT PRIMARY KEY, - display_name TINYTEXT NOT NULL, - email TINYTEXT NOT NULL, - password TINYTEXT NOT NULL, - profile_picture LONGTEXT, - role TINYTEXT NOT NULL, - settings LONGTEXT - );`); - - // --- Mods --- - - // Mods table - db.exec(`CREATE TABLE IF NOT EXISTS Mods ( - name TINYTEXT PRIMARY KEY, - display_name TINYTEXT NOT NULL, - author TINYTEXT NOT NULL, - description TINYTEXT NOT NULL, - - FOREIGN KEY (author) REFERENCES Users(username) - );`); - - // Mods complementary infos - db.exec(`CREATE TABLE IF NOT EXISTS ModInfos ( - mod TINYTEXT PRIMARY KEY, - full_description TEXT NOT NULL, - license TINYTEXT, - custom_license TEXT, - links TEXT, - creation_date TINYTEXT NOT NULL, - downloads_count INT NOT NULL, - - FOREIGN KEY (mod) REFERENCES Mods(name) - );`); - - // Mods tags - db.exec(`CREATE TABLE IF NOT EXISTS ModTags ( - mod TINYTEXT NOT NULL, - tag TINYTEXT NOT NULL, - - FOREIGN KEY (mod) REFERENCES Mods(name) - );`); - - // Mods versions - db.exec(`CREATE TABLE IF NOT EXISTS ModVersions ( - mod TINYTEXT NOT NULL, - version_number TINYTEXT NOT NULL, - channel TINYTEXT NOT NULL, - changelog TEXT NOT NULL, - release_date TINYTEXT NOT NULL, - game_version TINYTEXT NOT NULL, - platform TINYTEXT NOT NULL, - environment TINYTEXT NOT NULL, - url TINYTEXT NOT NULL, - - FOREIGN KEY (mod) REFERENCES Mods(name) - );`); - - // User favorites (mods) - db.exec(`CREATE TABLE IF NOT EXISTS UserFavoriteMods ( - username TINYTEXT NOT NULL, - mod TINYTEXT NOT NULL, - - FOREIGN KEY (username) REFERENCES Users(username), - FOREIGN KEY (mod) REFERENCES Mods(name) - );`); - -} - - -function getDatabase() { - return db; -} - - -module.exports = { getDatabase, connectDatabase, initDatabase }; \ No newline at end of file diff --git a/src/database/mysql.js b/src/database/mysql.js deleted file mode 100644 index df96f30..0000000 --- a/src/database/mysql.js +++ /dev/null @@ -1,30 +0,0 @@ -class MySQLDatabase { - constructor(config) { - const mysql = require("mysql2/promise"); - this.config = config; - } - - - async connect() { - this.db = await mysql.createConnection({ - host: this.config.host, - user: this.config.user, - password: this.config.password, - database: this.config.database, - }); - console.log("Connected to MySQL"); - } - - async close() { - await this.db.end(); - } - - async query(sql, params) { - throw new Error("Not implemented"); //TODO - const [results] = await this.db.execute(sql, params); - return results; - } -} - - -module.exports = MySQLDatabase; \ No newline at end of file diff --git a/src/database/sqlite.js b/src/database/sqlite.js deleted file mode 100644 index b81e219..0000000 --- a/src/database/sqlite.js +++ /dev/null @@ -1,70 +0,0 @@ -const sqlite = require("better-sqlite3"); - -class SQLiteDatabase { - - constructor(config) { - this.config = config; - this.db = null; - } - - async connect() { - try { - this.db = new sqlite("./data/sqlite.db"); - // this.db.pragma("journal_mode = WAL"); - console.log("Connected to SQLite"); - } catch (err) { - console.error("Error connecting to SQLite database: ", err); - process.exit(1); - } - } - - async close() { - if (this.db && this.db.open) { - this.db.close(); - console.debug("Closed database connection"); - } - } - - async query(sql, params = []) { - try { - if (params.length > 0) { - return this.db.prepare(sql).all(params); - } else { - return this.db.prepare(sql).all(); - } - } catch (err) { - console.error("Error executing prepared query:", err); - throw err; - } - } - - async exec(sql) { - try { - return this.db.exec(sql); - } catch (err) { - console.error("Error executing statement:", err)} - - } - - async prepare(sql, params = []) { - try { - if (params.length > 0) { - return this.db.prepare(sql).run(params); - } else { - return this.db.prepare(sql); - } - } catch (err) { - console.error("Error executing prepared statement:", err)} - } - - async exists(table, attribute, value) { - try { - return this.db.prepare(`SELECT COUNT(*) FROM ${table} WHERE ${attribute} = ?`).get(value)['COUNT(*)'] > 0; - } catch (err) { - console.error("Error checking item existence"); - } - } - -} - -module.exports = SQLiteDatabase; \ No newline at end of file diff --git a/src/middleware/auth.js b/src/middleware/auth.js deleted file mode 100644 index d43e385..0000000 --- a/src/middleware/auth.js +++ /dev/null @@ -1,85 +0,0 @@ -const { getModByName } = require("../services/modService"); -const { getModpackByName } = require("../services/modpackService"); -const { getUserByName } = require("../services/userService"); -const { verifyToken } = require("../utils/crypto"); -const AppError = require("../utils/appError"); - - -async function authenticateToken(req) { - - const token = req.header("Authorization"); - - if (!token) { - throw new AppError(401, "Missing authorization header", "Unauthorized"); - } - - try { - req.token_infos = await verifyToken(token); - console.debug("Authorizing token from", req.token_infos); - } catch (err) { - throw new AppError(403, "Forbidden: Error verifying the authorization token"); - } - - return req.token_infos; -} - - -async function authorizeModModification(req) { - - // Auth token - await authenticateToken(req); - // Get mod infos - if (!req.params || !req.params.name) { - throw new AppError(400, "No mod name was scpecified", "Bad request"); - } - const mod_name = req.params.name; - const mod = await getModByName(mod_name); - if (!mod) { - throw new AppError(404, "No mod was found with this name", "Not found"); - } - // Authorize - if ( mod.author != req.token_infos.username) { - throw new AppError(401, "Mod author differs from current user", "Unauthorized"); - } -} - -async function authorizeModpackModification(req) { - - // Auth token - await authenticateToken(req); - // Get mod infos - if (!req.params || !req.params.name) { - throw new AppError(400, "No mod name was scpecified", "Bad request"); - } - const modpack_name = req.params.name; - const modpack = await getModpackByName(modpack_name); - if (!modpack) { - throw new AppError(404, "No mod was found with this name", "Not found"); - } - // Authorize - if ( modpack.author != req.token_infos.username) { - throw new AppError(401, "Mod author differs from current user", "Unauthorized"); - } -} - -async function authorizeUserModification(req) { - - // Auth token - await authenticateToken(req); - // Get mod infos - if (!req.params || !req.params.name) { - throw new AppError(400, "No mod name was scpecified", "Bad request"); - } - const user_name = req.params.name; - const user = await getUserByName(user_name); - if (!user) { - throw new AppError(404, "No user was found with this name", "Not found"); - } - // Authorize - if ( user.username != req.token_infos.username) { - throw new AppError(401, "User to modify differs from current user", "Unauthorized"); - } -} - - -module.exports = { authenticateToken, authorizeModModification, authorizeModpackModification, authorizeUserModification }; \ No newline at end of file diff --git a/src/middleware/errors.js b/src/middleware/errors.js deleted file mode 100644 index f51e57a..0000000 --- a/src/middleware/errors.js +++ /dev/null @@ -1,31 +0,0 @@ -const AppError = require("../utils/appError"); - -const handleError = (err, res) => { - - // Send error infos - if (err instanceof AppError) { - - // Log - if (err.statusCode == 500) { - console.error("Error:", err.message); - if (err.debugMsg) { - console.debug(" >", err.debugMsg); - } - } - - // Response - return res.status(err.statusCode).json({ - status: err.status, - message: err.message - }); - } - - // Default error - console.error("Error:", err.message); - res.status(500).json({ - message: 'Internal server error', - status: 500 - }); -} - -module.exports = handleError; \ No newline at end of file diff --git a/src/models/index.js b/src/models/index.js deleted file mode 100644 index 7b8c71c..0000000 --- a/src/models/index.js +++ /dev/null @@ -1,12 +0,0 @@ -const configManager = require("../utils/configManager"); - -async function getVersion() { - - const version = await configManager.getVersion(); - const res = { - version: version - }; - return res; -} - -module.exports = { getVersion } \ No newline at end of file diff --git a/src/models/mod.js b/src/models/mod.js deleted file mode 100644 index f7abfd9..0000000 --- a/src/models/mod.js +++ /dev/null @@ -1,192 +0,0 @@ -const { getDatabase } = require('../database/index'); -const AppError = require('../utils/appError'); -const db = getDatabase(); - - -// --- Get --- - -async function getAllMods() { - return await db.query("SELECT name, display_name, author, description FROM Mods"); -} - -async function getModByName(name) { - return await db.query("SELECT name, display_name, author FROM Mods WHERE name = ?;", [name]); - -} - -async function getModFullInfos(name) { - - // Query - const base_infos = db.query(`SELECT * FROM Mods WHERE name = ?`, [name]); - const other_infos = db.query(`SELECT full_description, license, links, creation_date, downloads_count - FROM ModInfos WHERE name = ?`, [name]); - const tags = getModTags(name); - - // Merge - const res = {...await base_infos, ...await other_infos, ...tags}; - - return res; -} - -async function listVersions(mod_name) { - return await db.query("SELECT * FROM ModVersions WHERE mod = ?", [mod_name]); -} - -async function getVersionByNumber(mod_name, version_number) { - return await db.query(`SELECT * FROM ModVersions - WHERE mod = ? - AND version_number = ?;`, - [mod_name, version_number]); -} - -async function getVersion(mod_name, version_number, game_version, platform, environment) { - return await db.query(`SELECT * FROM ModVersions - WHERE mod = ? - AND version_number = ? - AND game_version = ? - AND platform = ? - AND environment = ?;`, - [mod_name, version_number, game_version, platform, environment]); -} - -// --- Create --- - -async function createMod(name, display_name, author, description, mod_infos) { - - // Extract infos - const { full_description, license, links, creation_date, tags } = mod_infos; - - // Mods table - await db.prepare("INSERT INTO Mods (name, display_name, author, description) \ - VALUES (?, ?, ?, ?)", - [name, display_name, author, description]); - - // ModInfos table - await db.prepare(`INSERT INTO ModInfos (mod, full_description, license, links, creation_date, downloads_count) - VALUES (?, ?, ?, ?, ?, ?)`, - [name, full_description, license.type, links.toString(), creation_date, 0]); - - // Tags - if (tags) { - const tags_proc = addTags(name, tags, []); - } - - - // License - if (license.type == "custom") { - await db.prepare(`UPDATE ModInfos SET custom_license = ? - WHERE mod = ?`, - [license.content, name]); - } - - // Await - if (tags) { - await tags_proc; - } - - return; -} - -async function addVersion(mod, version_number, channel, changelog, release_date, game_version, platform, environment, url) { - - await db.prepare(`INSERT INTO ModVersions (mod, version_number, channel, changelog, release_date, game_version, environment, platform, url) - VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?);`, - [mod, version_number, channel, changelog, release_date, game_version, environment, platform, url]); - return; -} - -async function addTags(mod, tags) { - // Add asynchronously - const promises = tags.map(async (tag) => { - db.query(`INSERT INTO ModTags (mod, tag) - VALUES (?, ?);`, - [mod, tag]); - }); - await Promise.all(promises); - - return; -} - - -// --- Update --- - -async function updateMod(name, display_name, author, description) { - - if (display_name) { - await updateModAttributes(name, "display_name", display_name); - } - - if (author) { - await updateModAttribute(nale, "author", author); - } - - if (description) { - await updateModAttribute(name, "description", description) - } -} - - -// --- Delete --- - -async function deleteMod(name) { - await db.prepare("DELETE FROM Mods WHERE name = ?", [name]); - return; -} - -async function deleteVersion(name, version_number, game_version, platform, environment) { - await db.prepare(`DELETE FROM ModVersions WHERE mod = ? - AND version_number = ? - AND game_version = ? - AND platform = ? - AND environment = ?;`, - [name, version_number, game_version, platform, environment]); - return; -} - -async function deleteTags(mod, tags) { - // Remove asynchronously - const promises = tags.map(async (tag) => { - db.query(`DELETE FROM ModTags - WHERE mod = ? AND tag = ?;`, [mod, tag]); - }); - await Promise.all(promises); - - return; -} - - -// --- Utils --- - -async function updateModAttribute(name, attribute, value) { - await db.prepare(`UPDATE Mods SET ${attribute} = ? WHERE name = ?`, [value, name]); - return; -} - -async function updateModInfosAttribute(name, attribute, value) { - await db.prepare(`UPDATE ModInfos SET ${attribute} = ? WHERE name = ?`, [value, name]); - return; -} - -async function exists(name) { - return db.exists("Mods", "name", name); -} - -async function containsVersion(name, version_number, game_version, platform, environment) { - throw new AppError(501, "Not implemented"); - // return db.exists("Mods", "name", name); -} - -async function containsTag(name, tag) { - throw new AppError(501, "Not implemented"); - // return db.exists("Mods", "name", name); -} - - -// --- Exports --- - -module.exports = { getAllMods, getModByName, getModFullInfos, - listVersions, getVersionByNumber, getVersion, - createMod, addVersion, addTags, - updateMod, - deleteMod, deleteVersion, deleteTags, - exists }; \ No newline at end of file diff --git a/src/models/modpack.js b/src/models/modpack.js deleted file mode 100644 index e69de29..0000000 diff --git a/src/models/user.js b/src/models/user.js deleted file mode 100644 index fc66eda..0000000 --- a/src/models/user.js +++ /dev/null @@ -1,125 +0,0 @@ -const { getDatabase } = require('../database/index'); -const AppError = require('../utils/appError'); -const db = getDatabase(); - - -// --- Get --- - -async function getAllUsers() { - return db.query("SELECT username, display_name, email, profile_picture FROM Users"); -} - -async function getUserByName(name) { - return await db.query("SELECT username, display_name, profile_picture, role FROM Users WHERE username = ?;", [name]); -} - -async function getUserByEmail(email) { - return await db.query("SELECT email, username FROM Users WHERE email = ?;", [email]); -} - -async function getFullUserInfos(name) { - return await db.query("SELECT username, display_name, email, profile_picture, role, settings FROM Users WHERE username = ?;", [name]); -} - -async function getUserPassword(name) { - return await db.query("SELECT username, password FROM Users WHERE username = ?;", [name]); -} - -async function exists(name) { - return await db.exists("Users", "username", name); -} - - -// --- Create --- - -async function createUser( username, email, password, displayName, profilePicture, settings ) { - - // Create user - await db.prepare(`INSERT INTO Users (username, email, password, display_name, role ) - VALUES (?, ?, ?, ?, ? )`, - [username, email, password, displayName, "user"]); - - // Handle nullable fields - if (profilePicture) { - await updateUserAttribute(username, "profile_picture", profilePicture); - } - - if (settings) { - await updateUserAttribute(username, "settings", settings); - } - return; -} - -async function addFavoriteMods(username, favs) { - - const promises = favs.map(async (mod) => { - db.query(`INSERT INTO UserFavoriteMods - (username, mod) VALUES (?, ?);`, - [username, mod]); - - }); - await Promise.all(promises); - - return; -} - - -// --- Update --- - -async function updateUser(username, display_name, email, profile_picture, settings) { - - if (display_name) { - await updateUserAttribute(username, "display_name", display_name); - } - - if (email) { - await updateUserAttribute(username, "email", email); - } - - if (profile_picture) { - await updateUserAttribute(username, "profile_picture", profile_picture) - } - - if (settings) { - await updateUserAttribute(username, "settings", settings); - } -} - -async function updateUserPassword(username, password) { - await db.prepare(`UPDATE Users SET password = ? WHERE username = ?`, [password, username]); -} - -async function updateUserAttribute(username, attribute, value) { - await db.prepare(`UPDATE Users SET ${attribute} = ? WHERE username = ?`, [value, username]); - return; -} - - -// --- Delete --- - -async function deleteUser(username) { - await db.prepare("DELETE FROM Users WHERE username = ?", [username]); - return; -} - -async function deleteFavoriteMods(username, favs) { - - const promises = favs.map(async (mod) => { - db.query(`DELETE FROM UserFavoriteMods - WHERE username = ? AND mod = ?;`, [username, mod]); - }); - - // Await - await Promise.all(promises); - - return; -} - - -// --- Exports --- - -module.exports = { getAllUsers, getUserByName, getUserByEmail, getFullUserInfos, getUserPassword, - createUser, addFavoriteMods, - updateUser, - deleteUser, deleteFavoriteMods, - exists } \ No newline at end of file diff --git a/src/routes/index.js b/src/routes/index.js deleted file mode 100644 index 36880b8..0000000 --- a/src/routes/index.js +++ /dev/null @@ -1,11 +0,0 @@ -const express = require("express"); -const controller = require("../controllers/index"); - -const router = express.Router(); - - -router.get('/version', async (res, req) => { - controller.getVersion(res, req); -}); - -module.exports = router; \ No newline at end of file diff --git a/src/routes/list.js b/src/routes/list.js deleted file mode 100644 index 2829954..0000000 --- a/src/routes/list.js +++ /dev/null @@ -1,24 +0,0 @@ -const express = require("express"); -const { listMods } = require("../controllers/mods"); -// const { listModpacks } = require("../controllers/modpacks"); -const { listUsers } = require("../controllers/users"); - -const router = express.Router(); - -// List mods -router.get("/mods", async (req,res) => { - listMods(req, res); -}); - -// List modpacks -// router.get("/modpacks", async (req,res) => { -// listModpacks(req, res); -// }); - -// List users -router.get("/users", async (req,res) => { - listUsers(req, res); -}); - - -module.exports = router; \ No newline at end of file diff --git a/src/routes/login.js b/src/routes/login.js deleted file mode 100644 index 14b8a87..0000000 --- a/src/routes/login.js +++ /dev/null @@ -1,11 +0,0 @@ -const express = require("express"); -const controller = require("../controllers/auth"); - -const router = express.Router(); - -// Login -router.post("/", async (req, res) => { - controller.login(req, res); -}); - -module.exports = router; \ No newline at end of file diff --git a/src/routes/modpacks.js b/src/routes/modpacks.js deleted file mode 100644 index e69de29..0000000 diff --git a/src/routes/mods.js b/src/routes/mods.js deleted file mode 100644 index 82c1e02..0000000 --- a/src/routes/mods.js +++ /dev/null @@ -1,27 +0,0 @@ -const express = require("express"); -const controller = require("../controllers/mods"); - -const router = express.Router(); - -// Create a mod -router.post("/", async (req, res) => { - controller.createMod(req, res); -}); - -// Modify mod -router.put("/:name", async (req,res) => { - controller.modifyMod(req,res); -}); - -// Get mod infos -router.get("/:name", async (req,res) => { - controller.getModByName(req, res); -}); - -// Delete mod -router.delete("/:name", async (req,res) => { - controller.deleteMod(req, res); -}); - - -module.exports = router; \ No newline at end of file diff --git a/src/routes/users.js b/src/routes/users.js deleted file mode 100644 index 390451f..0000000 --- a/src/routes/users.js +++ /dev/null @@ -1,27 +0,0 @@ -const express = require("express"); -const controller = require("../controllers/users"); - -const router = express.Router(); - -// List users -router.get("/", async (req,res) => { - controller.listUsers(req,res); -}); - -// Create a user -router.post("/", async (req, res) => { - controller.createUser(req, res); -}) - -// Get user infos -router.get("/:name", async (req,res) => { - controller.getUserByName(req, res); -}); - -// Delete user -router.delete("/:name", async (req,res) => { - controller.deleteUser(req, res); -}); - - -module.exports = router; \ No newline at end of file diff --git a/src/schemas/auth.js b/src/schemas/auth.js deleted file mode 100644 index e57a75c..0000000 --- a/src/schemas/auth.js +++ /dev/null @@ -1,21 +0,0 @@ -const Ajv = require("ajv"); -const ajv = new Ajv(); - -// --- Schemas --- - -const AuthUserSchema = { - type: 'object', - properties: { - email: { type: 'string', format: 'email' }, - password: { type: 'string', minLength: 3, maxLength: 30 }, - }, - required: ['email', 'password'], - additionalProperties: false -}; - -const validateAuthUserData = ajv.compile(AuthUserSchema); - - -// --- Exports --- - -module.exports = { validateAuthUserData, validateAuthNodeData }; \ No newline at end of file diff --git a/src/schemas/mod.js b/src/schemas/mod.js deleted file mode 100644 index 6d7dc9d..0000000 --- a/src/schemas/mod.js +++ /dev/null @@ -1,21 +0,0 @@ -const Ajv = require("ajv"); -const ajv = new Ajv(); - -// --- Schemas --- -//TODO - -const newModSchema = { - type: 'object', - properties: { - name: { type: 'string'}, - }, - required: ['name'], - additionalProperties: false -}; - -const validateNewModData = ajv.compile(newModSchema); - - -// --- Exports --- - -module.exports = { validateNewModData }; \ No newline at end of file diff --git a/src/schemas/modpack.js b/src/schemas/modpack.js deleted file mode 100644 index df4a49a..0000000 --- a/src/schemas/modpack.js +++ /dev/null @@ -1,21 +0,0 @@ -const Ajv = require("ajv"); -const ajv = new Ajv(); - -// --- Schemas --- -//TODO - -const newModpackSchema = { - type: 'object', - properties: { - name: { type: 'string'}, - }, - required: ['name'], - additionalProperties: false -}; - -const validateNewModpackData = ajv.compile(newModpackSchema); - - -// --- Exports --- - -module.exports = { validateNewModpackData }; \ No newline at end of file diff --git a/src/schemas/user.js b/src/schemas/user.js deleted file mode 100644 index 0c009a1..0000000 --- a/src/schemas/user.js +++ /dev/null @@ -1,23 +0,0 @@ -const Ajv = require("ajv"); -const ajv = new Ajv(); - -// --- Schemas --- -//TODO - -const newUserSchema = { - type: 'object', - properties: { - email: { type: 'string', format: 'email' }, - name: { type: 'string' }, - password: { type: 'string', minLength: 3, maxLength: 30 }, - }, - required: ['name', 'email', 'password'], - additionalProperties: false -}; - -const validateNewUserData = ajv.compile(newUserSchema); - - -// --- Exports --- - -module.exports = { validateNewUserData }; \ No newline at end of file diff --git a/src/services/authService.js b/src/services/authService.js deleted file mode 100644 index e9dee2b..0000000 --- a/src/services/authService.js +++ /dev/null @@ -1,85 +0,0 @@ -const userModel = require("../models/user"); -const AppError = require("../utils/appError"); -const cryptoUtils = require("../utils/crypto"); -const configManager = require("../utils/configManager"); -const validate = require("../utils/validate_legacy"); - -const JWT_Secret = configManager.getJWTSecret(); - -async function login(username, email, password) { - - // Check for null - if (!(username || email) || !password) { - throw new AppError(400, "Bad request", "missing credentials"); - } - - // Get user data - let user_get; - if (email) { // If matches email - user_get = await userModel.getUserByEmail(email); - } else - if (username) { // if matches username - user_get = await userModel.getUserByName(username); - } else { - console.debug("Failed finding user, weird...") - throw new AppError(401, "Unauthorized", "Invalid credentials"); - } - - // Check if user exists - if (!user_get || user_get.length == 0) { - // throw new AppError(401, "Unauthorized: No user with this name"); - throw new AppError(401, "Unauthorized", "Invalid credentials"); - } - // Just in case - if (user_get.length > 1) { - throw new AppError(500, "Internal server error", "Found multiple users with this name or email, please contact administration"); - } - - const user = user_get[0]; - - // Get user password - const saved_password_get = await userModel.getUserPassword(user.username); - // Check if retrieved password sucessfully - if (!saved_password_get || saved_password_get.length == 0) { - throw new AppError(500, "Unable to retrieve user password"); - } - saved_password = saved_password_get[0].password; - // Check if retrieved password sucessfully again - if (!saved_password) { - throw new AppError(500, "Unable to retrieve user password"); - } - - // Check if passwords match - const passwords_match = await cryptoUtils.passwordsMatch(password, saved_password) - if (!passwords_match) { - // throw new AppError(401, "Unauthorized: Invalid password"); - console.debug(password, "differs from", saved_password); - throw new AppError(401, "Unauthorized", "Invalid credentials"); - } - - const payload = { type: "user", - username: user.username, - email: user.email, - role: user.role }; - - const token = await cryptoUtils.signToken(payload); - return token; - - // // Check if passwords match - // const passwords_match = await bcrypt.compare(password, user[0].password); - // if (!passwords_match) { - // // throw new AppError(401, "Unauthorized: Invalid password"); - // console.debug("Password doesn't match") - // throw new AppError(401, "Unauthorized", "Invalid credentials"); - // } - - // return jwt.sign({ username: user[0].username, role: user[0].role }, await JWT_Secret); -} - -// function authorizeRole(user, roles) { -// if (!user || !roles.includes(user.role)) { -// throw new AppError(401, "Unauthorized: You don't have the necessary permissions to access this resource"); -// } -// } - -module.exports = { login }; \ No newline at end of file diff --git a/src/services/indexService.js b/src/services/indexService.js deleted file mode 100644 index d2fc506..0000000 --- a/src/services/indexService.js +++ /dev/null @@ -1,7 +0,0 @@ -const model = require("../models/index"); - -async function getVersion() { - return model.getVersion(); -} - -module.exports = { getVersion } diff --git a/src/services/modService.js b/src/services/modService.js deleted file mode 100644 index 4cd8862..0000000 --- a/src/services/modService.js +++ /dev/null @@ -1,164 +0,0 @@ -const model = require("../models/mod"); -const AppError = require("../utils/appError"); -const { validateModData } = require("../utils/validate_legacy"); -const { mdToHtml } = require("../utils/convert"); -const { sanitizeModData } = require("../utils/sanitize"); - - -// --- Get --- - -async function getAllMods() { - return model.getAllMods(); -} - -async function getModByName(name) { - const res = model.getModByName(name); - if (res.length == 0) { - throw new AppError(404, "Cannot find mod with this name", "Not found"); - } - return res[0]; -} - -async function getFullModInfos(name) { - const res = model.getFullModInfos(name); - if (res.length == 0) { - throw new AppError(404, "Cannot find mod with this name", "Not found"); - } - return res[0]; -} - -async function getModVersion(infos) { - const { mod, version_number, game_version, platform, environment} = infos; - const res = model.getModVersion(mod, version_number, game_version, platform, environment); - if (res.length == 0) { - throw new AppError(404, "Cannot find mod with this name", "Not found"); - } - return res[0]; -} - - -// --- Create --- - -async function createMod(mod_data, author) { - - // Check body validity - //TODO - console.warn("Skipping validity checks for createMod"); - // await validateModData(mod_data); - - // Generate data - const { name, display_name, description, mod_infos } = mod_data; - mod_infos.full_description = await mdToHtml(mod_infos.full_description); // Convert - await sanitizeModData(mod_data); // Sanitize - //TODO - mod_infos.creation_date = 0 - - // Write changes to database - await model.createMod(name, display_name, author, description, mod_infos); - - // Return - return getModByName(name); -} - -async function addVersion(version_data) { - - // Validate - //TODO - console.warn("Skipping validity checks for addVersion"); - - // Generate data - const { mod_name, version_number, channel, changelog, game_version, - platform, environment, url } = version_data; // Split - changelog = await mdToHtml(changelog); // Convert - await sanitizeModData(mod_data); // Sanitize - const release_date = (new Date()).toLocaleDateString(); - - // Write changes - await model.addVersion(mod_name, version_number, channel, changelog, - release_date, game_version, platform, environment, url); // Database - - // Return - return await model.getModVersion(mod_name, version_number, game_version, platform, environment ); -} - -async function addTags(mod, tags) { - - // Validate - //TODO - console.warn("Skipping validity checks for addTags"); - - // Write changes - await model.addTags(mod, tags); - - // Return - const { tags:res } = await model.getFullModInfos(mod); - return { "mod": mod, "tags": res}; - -} - -// --- Update --- - -async function updateMod(diff_data) { - //TODO - throw new AppError(501, "Not implemented"); -} - - - -// Delete - -async function deleteMod(name) { - - // Check existence - const mod = await model.getModByName(name); - if (!mod) { - throw new AppError(404, "No was found with this name", "Not found") - } - - // Authorize - // TODO move outside of this function - if (mod.author != mod.user) { - throw new AppError(403, "You don't have the necessary permissions to execute this action", "Forbidden"); - } - - // Write changes to database - await model.deleteMod(name); - - // Return - return mod; -} - -async function deleteVersion(version_infos) { - - // Validate - // TODO - - // Generate data - const res = await getModVersion(version_infos); - const { mod, version_number, game_version, platform, environment} = version_infos; - - // Write changes to db - await model.deleteVersion(mod, version_number, game_version, platform, environment); - - // Return - return res; -} - -async function deleteTags(mod, tags) { - - // Validate (check existence) - //TODO - console.warn("Skipping validity checks for deleteTags"); - - // Wites changes to db - await model.deleteTags(mod, tags); - - // Return - const { tags:res } = await model.getFullModInfos(mod); - return { "mod": mod, "tags": res}; -} - -module.exports = { getAllMods, getModByName, getFullModInfos, - createMod, addTags, addVersion, - updateMod, - deleteMod, deleteTags, deleteVersion }; \ No newline at end of file diff --git a/src/services/modpackService.js b/src/services/modpackService.js deleted file mode 100644 index e69de29..0000000 diff --git a/src/services/userService.js b/src/services/userService.js deleted file mode 100644 index 8020e25..0000000 --- a/src/services/userService.js +++ /dev/null @@ -1,46 +0,0 @@ -const model = require("../models/user"); -const AppError = require("../utils/appError"); -const cryptoUtils = require("../utils/crypto"); -const { validateUserData } = require("../utils/validate_legacy"); -const { sanitizeUserData } = require("../utils/sanitize"); - -async function getAllUsers() { - return await model.getAllUsers(); -} - -async function getUserByName(name) { - const res = await model.getUserByName(name); - return res[0]; -} - -async function createUser(user_data) { - - // Check body validity - // TODO - - // Sanitize - // TODO - - // Gather data - const { username, email, password, display_name, profile_picture, settings } = user_data - const password_hash = await cryptoUtils.hashPassword(password); - - await model.createUser(username, email, password_hash, display_name, null, null); - return model.getUserByName(username); -} - -async function deleteUser(name, token_user) { - - // Check existence - const exists = await model.exists(name); - if (!exists) { - throw new AppError(404, "Cannot find user with this name", "Not found"); - } - - const res = await model.getUserByName(name); - await model.deleteUser(name); - - return res; -} - -module.exports = { getAllUsers, getUserByName, createUser, deleteUser }; \ No newline at end of file diff --git a/src/utils/appError.js b/src/utils/appError.js deleted file mode 100644 index 5246dbc..0000000 --- a/src/utils/appError.js +++ /dev/null @@ -1,27 +0,0 @@ -class AppError extends Error { - constructor(statusCode, message, status = "", debugMsg = "") { - super(message); - this.statusCode = statusCode; - this.debugMsg = debugMsg; - // Get status - if (status === "") { - if (statusCode.toString().startsWith("4")) { - this.status = "Fail"; - } else { - this.status = "Error"; - } - } else { - this.status = status; - } - } -} - -exports.tryCatch = (controller) => async (req, res, next) => { - try { - await controller(req, res, next); - } catch(err) { - next(err); - } -} - -module.exports = AppError; \ No newline at end of file diff --git a/src/utils/configManager.js b/src/utils/configManager.js deleted file mode 100644 index 5017a6f..0000000 --- a/src/utils/configManager.js +++ /dev/null @@ -1,89 +0,0 @@ -// --- Define constants --- - -// Imports -const fs = require("fs"); -const path = require("path"); -const { version } = require("../../package.json"); - - -// Var decalaration -const config_folder = "config"; -const config_file_name = "config.json" - -// Global variables -let config = {}; - -// --- Default config --- - -const default_config = { - - "port": 8000, - - "users": { - "admin": { - "username": "admin", - "password": "admin" - } - }, - - "database": { - "type": "sqlite" - }, - - "auth" : { - "JWT_secret": "HGF7654EGBNKJNBJH6754356788GJHGY", - "tokenExpiry": "1h" - } -} - - -// --- Functions --- - -function loadConfig() { - - let user_config; - - // Parse - try { - // Get user config - user_config = JSON.parse(fs.readFileSync(path.resolve(path.join(config_folder, config_file_name)))); - - // Warns - if (!user_config.auth || !user_config.auth.JWT_secret) { - console.warn("WARNING: No JWT secret provided, using the default one. Please note that using the default secret is a major security risk.") - } - - // Merge default and user configs (default values) - config = { ...default_config, ...user_config }; - } - catch (err) { - // Error messages - console.debug("Error:", err) - console.error("Error loading configuration, using the default settings"); - console.debug("Search path:", path.resolve("./")); - console.debug("Config file:", path.resolve(path.join(config_folder, config_file_name))) - - config = default_config; - } - - return config; - -} - - -async function getConfig() { - return config; -} - -async function getJWTSecret() { - return config.auth.JWT_secret || process.env.JWT_secret; -} - -async function getVersion() { - // Could be done with process.env.npm_package_version - // but may not work without without npm - return version; -} - -// Exports -module.exports = { loadConfig, getConfig, getVersion, getJWTSecret }; \ No newline at end of file diff --git a/src/utils/convert.js b/src/utils/convert.js deleted file mode 100644 index 39a56a9..0000000 --- a/src/utils/convert.js +++ /dev/null @@ -1,11 +0,0 @@ -const marked = require("marked"); - -async function mdToHtml(md_content) { - if (md_content) { - return marked.parse(md_content); - } else { - return ""; - } -} - -module.exports = { mdToHtml }; \ No newline at end of file diff --git a/src/utils/crypto.js b/src/utils/crypto.js deleted file mode 100644 index be1ffc5..0000000 --- a/src/utils/crypto.js +++ /dev/null @@ -1,61 +0,0 @@ -// --- Imports --- -const jwt = require("jsonwebtoken"); -const bcrypt = require("bcrypt"); -const { getConfig, getJWTSecret } = require("./configManager"); - - -// --- Config --- - -// Declarations -let JWT_Secret; -let token_expiry; -// Constant values -const saltRounds = 12; -// Load -(async () => { - const config = await getConfig(); - JWT_Secret = await getJWTSecret(); - token_expiry = config.auth.tokenExpiry; - signature_algorithm = config.auth.signatureAlgorithm; -})(); - - -// --- Functions --- - -async function hashPassword(passwd) { - const hash = bcrypt.hashSync(passwd, saltRounds); - return hash; -} - - -async function passwordsMatch(password, hashed_password) { - return await bcrypt.compare(password, hashed_password); -} - - -async function signToken(payload, options = null) { - if (options == null) { - return jwt.sign(payload, JWT_Secret, { expiresIn: token_expiry, }); - } - else { - return jwt.sign(payload, JWT_Secret, options); - } - -} - - -function verifyToken(token) { - return new Promise( async (resolve, reject) => { - await jwt.verify( token, JWT_Secret, (err, user) => { - if (err) { - reject(err); - } else { - resolve(user); - } - }); - }); -} - - -// --- Exports --- -module.exports = { passwordsMatch, hashPassword, verifyToken, signToken }; \ No newline at end of file diff --git a/src/utils/sanitize.js b/src/utils/sanitize.js deleted file mode 100644 index be3885b..0000000 --- a/src/utils/sanitize.js +++ /dev/null @@ -1,19 +0,0 @@ -const createDOMPurify = require("dompurify"); -const { JSDOM } = require("jsdom"); - -// Initialize -const window = new JSDOM("").window; -const DOMPurify = createDOMPurify(window); - -async function sanitizeText(text) { - return DOMPurify.sanitize(text); -} - -async function sanitizeModData(mod_data) { - console.warn("Skipping sanitanization (not implemented)"); - // mod_data.displayName = await sanitizeText(mod_data.displayName); - // mod_data.otherInfos.description = await sanitizeText(mod_data.otherInfos.description); - // mod_data.otherInfos.changelogs = await sanitizeText(mod_data.otherInfos.changelogs); -} - -module.exports = { sanitizeText, sanitizeModData }; \ No newline at end of file diff --git a/src/utils/validate.js b/src/utils/validate.js deleted file mode 100644 index b7c3519..0000000 --- a/src/utils/validate.js +++ /dev/null @@ -1,51 +0,0 @@ -// --- Imports --- -const AppError = require("./appError"); - - -// --- Functions --- - -async function validateNewModData(mod_data) { - - throw new AppError(501, "Not implemented"); - //TODO - // try { - // node_schemas.validateNewModData(node_data); - // } catch (err) { - // throw new AppError(400, "Missing or invalid fields", "Bad request", err); - // } - -} - - -async function validateNewUserData(user_data) { - - throw new AppError(501, "Not implemented"); - //TODO - // try { - // node_schemas.validateNewUserData(node_data); - // } catch (err) { - // throw new AppError(400, "Missing or invalid fields", "Bad request", err); - // } - -} - -async function validateCretendials(identifier, password) { - - throw new AppError(501, "Not implemented"); -} - - -// --- Utils --- - -async function isEmail(text) { - const email_regex = /^[\w-\.]+@([\w-]+\.)+[\w-]{2,4}$/; - return email_regex.test(text); -} - -async function isID(text) { - const id_regex = /[a-zA-Z0-9_]+/; - return id_regex.test(text); -} - - -module.exports = { validateNewModData, validateNewUserData, isEmail, isID }; \ No newline at end of file diff --git a/src/utils/validate_legacy.js b/src/utils/validate_legacy.js deleted file mode 100644 index 63c605b..0000000 --- a/src/utils/validate_legacy.js +++ /dev/null @@ -1,98 +0,0 @@ -const mod_model = require("../models/mod"); -const user_model = require("../models/user"); -const AppError = require("./appError"); - -async function validateModData(mod_data) { - //TODO WIP - // Check fields existence - const not_null = mod_data && - Object.keys(mod_data).length == 5 && - mod_data.name && - mod_data.displayName && - mod_data.author && - mod_data.versions != null; - - // mod_data.otherInfos != null && - // Object.keys(mod_data.otherInfos).length == 0 && - // mod_data.otherInfos.description != null && - // mod_data.otherInfos.links != null && - // mod_data.otherInfos.tags != null && - // mod_data.otherInfos.screenshots != null && - // mod_data.otherInfos.license != null && - // mod_data.otherInfos.changelogs != null; - - if (!not_null) { - console.debug("Item is missing expected fields:", mod_data); - throw new AppError(400, "Bad request", "Missing expected fields"); - } - - // Check fields format (check if sanitized) - const is_valid_name = /^[a-zA-Z0-9_]+$/.test(mod_data.name); - const is_valid_displayName = true; - // const is_valid_displayName = /^[a-zA-Z0-9_]+$/.test(mod_data.name); // Temporary - // const - - const is_valid = is_valid_name && is_valid_displayName; - if (!is_valid) { - console.debug("Fields are not following the expected formats"); - throw new AppError(400, "Bad request", "The provided fields don't match the expected format"); - } - - // Check if mod already exists - const exists = await mod_model.exists(mod_data.name); - if (exists) { - console.debug("Error: Item already exists"); - throw new AppError(403, "Forbidden", "Content with this name already exists"); - } -} - - -async function validateUserData(user_data) { - throw new AppError(501, "Not implemented"); - - //TODO - - // Check fields existence - // ... - - if (!not_null) { - console.debug("Missing expected fields:", mod_data); - throw new AppError(400, "Bad request: Missing expected fields"); - } - - // Check fields format (check if sanitized) - const is_valid_username = /^[a-zA-Z0-9_]+$/.test(user_data.username); - // const is_valid_email = ... - // ... - - const is_valid = is_valid_username && is_valid_email; - if (!is_valid) { - console.debug("Fields are not following the expected formats"); - throw new AppError(400, "Bad request: The provided fields don't match the expected format"); - } - - // Check if user already exists - const exists = await user_model.exists(user_data.username); - if (exists) { - console.debug("Error: User already exists"); - throw new AppError(403, "Forbidden: User with this name already exists"); - } -} - -async function validateCretendials(identifier, password) { - - throw new AppError(501, "Not implemented"); -} - -async function isEmail(text) { - const email_regex = /^[\w-\.]+@([\w-]+\.)+[\w-]{2,4}$/; - return email_regex.test(text); -} - -async function isID(text) { - const id_regex = /[a-zA-Z0-9_]+/; - return id_regex.test(text); -} - - -module.exports = { validateModData, validateUserData, isEmail, isID }; \ No newline at end of file