diff --git a/Dockerfile b/Dockerfile
index c9b3a48..add3992 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -1,4 +1,4 @@
-FROM node:18-buster
+FROM node:18
WORKDIR /opt/app
@@ -11,6 +11,8 @@ RUN npm install
COPY . .
+RUN npx prisma generate
+
RUN npm run build
RUN chown node:node /opt/app/
diff --git a/package-lock.json b/package-lock.json
index 8b2e5e8..2be5b6f 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -9,32 +9,32 @@
"version": "0.0.1",
"license": "GPL-3.0-or-later",
"dependencies": {
- "@discordjs/builders": "^1.2.0",
+ "@discordjs/builders": "^1.3.0",
"@prisma/client": "^4.0.0",
"@sapphire/discord.js-utilities": "^5.0.0",
- "@sapphire/framework": "^3.1.1",
+ "@sapphire/framework": "^3.1.3",
"@sapphire/plugin-scheduled-tasks": "^4.0.0",
"@sapphire/plugin-subcommands": "^3.0.0",
"@sapphire/stopwatch": "^1.4.1",
- "@sapphire/ts-config": "^3.3.4",
"@sapphire/utilities": "^3.9.2",
"@types/node": "^18.0.3",
"bullmq": "^1.89.1",
"discord-api-types": "^0.33.3",
- "discord.js": "^13.10.3",
+ "discord.js": "^13.12.0",
"dotenv": "^16.0.1",
- "prisma": "^4.2.1",
"ts-node": "^10.8.2",
"typescript": "^4.7.4"
},
"devDependencies": {
+ "@sapphire/ts-config": "^3.3.4",
"@types/ioredis": "^4.28.10",
"@typescript-eslint/eslint-plugin": "^5.30.7",
"@typescript-eslint/parser": "^5.30.7",
"eslint": "8.22.0",
"eslint-config-airbnb-base": "^15.0.0",
"eslint-config-airbnb-typescript": "^17.0.0",
- "eslint-plugin-import": "^2.26.0"
+ "eslint-plugin-import": "^2.26.0",
+ "prisma": "^4.4.0"
}
},
"node_modules/@cspotcode/source-map-support": {
@@ -49,12 +49,13 @@
}
},
"node_modules/@discordjs/builders": {
- "version": "1.2.0",
- "resolved": "https://registry.npmjs.org/@discordjs/builders/-/builders-1.2.0.tgz",
- "integrity": "sha512-ARy4BUTMU+S0ZI6605NDqfWO+qZqV2d/xfY32z3hVSsd9IaAKJBZ1ILTZLy87oIjW8+gUpQmk9Kt0ZP9bmmd8Q==",
+ "version": "1.3.0",
+ "resolved": "https://registry.npmjs.org/@discordjs/builders/-/builders-1.3.0.tgz",
+ "integrity": "sha512-Pvca6Nw8Hp+n3N+Wp17xjygXmMvggbh5ywUsOYE2Et4xkwwVRwgzxDJiMUuYapPtnYt4w/8aKlf5khc8ipLvhg==",
"dependencies": {
- "@sapphire/shapeshift": "^3.5.1",
- "discord-api-types": "^0.37.3",
+ "@discordjs/util": "^0.1.0",
+ "@sapphire/shapeshift": "^3.7.0",
+ "discord-api-types": "^0.37.12",
"fast-deep-equal": "^3.1.3",
"ts-mixer": "^6.0.1",
"tslib": "^2.4.0"
@@ -64,22 +65,30 @@
}
},
"node_modules/@discordjs/builders/node_modules/discord-api-types": {
- "version": "0.37.8",
- "resolved": "https://registry.npmjs.org/discord-api-types/-/discord-api-types-0.37.8.tgz",
- "integrity": "sha512-uhol9KQ2moExZItMpuDMkf0R7sqqNHqcJBFN7S5iSdXBVCMRO7sC0GoyuRrv6ZDBYxoFU6nDy4dv0nld/aysqA=="
+ "version": "0.37.14",
+ "resolved": "https://registry.npmjs.org/discord-api-types/-/discord-api-types-0.37.14.tgz",
+ "integrity": "sha512-byBH7SfDCMJwxdqeS8k5sihltH88/YPhuwx+vF2cftSxFLdxyHyU/ZxDL3bq+LB2c4ls/TymE76/ISlLfniUXg=="
},
"node_modules/@discordjs/collection": {
- "version": "1.1.0",
- "resolved": "https://registry.npmjs.org/@discordjs/collection/-/collection-1.1.0.tgz",
- "integrity": "sha512-PQ2Bv6pnT7aGPCKWbvvNRww5tYCGpggIQVgpuF9TdDPeR6n6vQYxezXiLVOS9z2B62Dp4c+qepQ15SgJbLYtCQ==",
+ "version": "1.2.0",
+ "resolved": "https://registry.npmjs.org/@discordjs/collection/-/collection-1.2.0.tgz",
+ "integrity": "sha512-VvrrtGb7vbfPHzbhGq9qZB5o8FOB+kfazrxdt0OtxzSkoBuw9dURMkCwWizZ00+rDpiK2HmLHBZX+y6JsG9khw==",
+ "engines": {
+ "node": ">=16.9.0"
+ }
+ },
+ "node_modules/@discordjs/util": {
+ "version": "0.1.0",
+ "resolved": "https://registry.npmjs.org/@discordjs/util/-/util-0.1.0.tgz",
+ "integrity": "sha512-e7d+PaTLVQav6rOc2tojh2y6FE8S7REkqLldq1XF4soCx74XB/DIjbVbVLtBemf0nLW77ntz0v+o5DytKwFNLQ==",
"engines": {
"node": ">=16.9.0"
}
},
"node_modules/@eslint/eslintrc": {
- "version": "1.3.1",
- "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.3.1.tgz",
- "integrity": "sha512-OhSY22oQQdw3zgPOOwdoj01l/Dzl1Z+xyUP33tkSN+aqyEhymJCcPHyXt+ylW8FSe0TfRC2VG+ROQOapD0aZSQ==",
+ "version": "1.3.3",
+ "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.3.3.tgz",
+ "integrity": "sha512-uj3pT6Mg+3t39fvLrj8iuCIJ38zKO9FpGtJ4BBJebJhEwjoT+KLVNCcHT5QC9NGRIEi7fZ0ZR8YRb884auB4Lg==",
"dev": true,
"dependencies": {
"ajv": "^6.12.4",
@@ -100,9 +109,9 @@
}
},
"node_modules/@humanwhocodes/config-array": {
- "version": "0.10.4",
- "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.10.4.tgz",
- "integrity": "sha512-mXAIHxZT3Vcpg83opl1wGlVZ9xydbfZO3r5YfRSH6Gpp2J/PfdBP0wbDa2sO6/qRbcalpoevVyW6A/fI6LfeMw==",
+ "version": "0.10.7",
+ "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.10.7.tgz",
+ "integrity": "sha512-MDl6D6sBsaV452/QSdX+4CXIjZhIcI0PELsxUjk4U828yd58vk3bTIvk/6w5FY+4hIy9sLW0sfrV7K7Kc++j/w==",
"dev": true,
"dependencies": {
"@humanwhocodes/object-schema": "^1.2.1",
@@ -113,11 +122,14 @@
"node": ">=10.10.0"
}
},
- "node_modules/@humanwhocodes/gitignore-to-minimatch": {
- "version": "1.0.2",
- "resolved": "https://registry.npmjs.org/@humanwhocodes/gitignore-to-minimatch/-/gitignore-to-minimatch-1.0.2.tgz",
- "integrity": "sha512-rSqmMJDdLFUsyxR6FMtD00nfQKKLFb1kv+qBbOVKqErvloEIJLo5bDTJTQNTYgeyp78JsA7u/NPi5jT1GR/MuA==",
+ "node_modules/@humanwhocodes/module-importer": {
+ "version": "1.0.1",
+ "resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz",
+ "integrity": "sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==",
"dev": true,
+ "engines": {
+ "node": ">=12.22"
+ },
"funding": {
"type": "github",
"url": "https://github.com/sponsors/nzakas"
@@ -264,12 +276,12 @@
}
},
"node_modules/@prisma/client": {
- "version": "4.3.1",
- "resolved": "https://registry.npmjs.org/@prisma/client/-/client-4.3.1.tgz",
- "integrity": "sha512-FA0/d1VMJNWqzU7WVWTNWJ+lGOLR9JUBnF73GdIPAEVo/6dWk4gHx0EmgeU+SMv4MZoxgOeTBJF2azhg7x0hMw==",
+ "version": "4.5.0",
+ "resolved": "https://registry.npmjs.org/@prisma/client/-/client-4.5.0.tgz",
+ "integrity": "sha512-B2cV0OPI1smhdYUxsJoLYQLoMlLH06MUxgFUWQnHodGMX98VRVXKmQE/9OcrTNkqtke5RC+YU24Szxd04tZA2g==",
"hasInstallScript": true,
"dependencies": {
- "@prisma/engines-version": "4.3.0-32.c875e43600dfe042452e0b868f7a48b817b9640b"
+ "@prisma/engines-version": "4.5.0-43.0362da9eebca54d94c8ef5edd3b2e90af99ba452"
},
"engines": {
"node": ">=14.17"
@@ -284,15 +296,16 @@
}
},
"node_modules/@prisma/engines": {
- "version": "4.3.1",
- "resolved": "https://registry.npmjs.org/@prisma/engines/-/engines-4.3.1.tgz",
- "integrity": "sha512-4JF/uMaEDAPdcdZNOrnzE3BvrbGpjgV0FcPT3EVoi6I86fWkloqqxBt+KcK/+fIRR0Pxj66uGR9wVH8U1Y13JA==",
+ "version": "4.5.0",
+ "resolved": "https://registry.npmjs.org/@prisma/engines/-/engines-4.5.0.tgz",
+ "integrity": "sha512-4t9ir2SbQQr/wMCNU4YpHWp5hU14J2m3wHUZnGJPpmBF8YtkisxyVyQsKd1e6FyLTaGq8LOLhm6VLYHKqKNm+g==",
+ "devOptional": true,
"hasInstallScript": true
},
"node_modules/@prisma/engines-version": {
- "version": "4.3.0-32.c875e43600dfe042452e0b868f7a48b817b9640b",
- "resolved": "https://registry.npmjs.org/@prisma/engines-version/-/engines-version-4.3.0-32.c875e43600dfe042452e0b868f7a48b817b9640b.tgz",
- "integrity": "sha512-8yWpXkQRmiSfsi2Wb/ZS5D3RFbeu/btL9Pm/gdF4phB0Lo5KGsDFMxFMgaD64mwED2nHc8ZaEJg/+4Jymb9Znw=="
+ "version": "4.5.0-43.0362da9eebca54d94c8ef5edd3b2e90af99ba452",
+ "resolved": "https://registry.npmjs.org/@prisma/engines-version/-/engines-version-4.5.0-43.0362da9eebca54d94c8ef5edd3b2e90af99ba452.tgz",
+ "integrity": "sha512-o7LyVx8PPJBLrEzLl6lpxxk2D5VnlM4Fwmrbq0NoT6pr5aa1OuHD9ZG+WJY6TlR/iD9bhmo2LNcxddCMr5Rv2A=="
},
"node_modules/@sapphire/async-queue": {
"version": "1.5.0",
@@ -313,13 +326,13 @@
}
},
"node_modules/@sapphire/discord.js-utilities": {
- "version": "5.0.0",
- "resolved": "https://registry.npmjs.org/@sapphire/discord.js-utilities/-/discord.js-utilities-5.0.0.tgz",
- "integrity": "sha512-XvXkL0/e4AwKIipSxPeNNa8UPmSCoc+vwkNrnvV43a0JUJ1acxPPWrcpxAzE9lRxPY/vDLYaaEw7M/hkg3i5xQ==",
+ "version": "5.1.1",
+ "resolved": "https://registry.npmjs.org/@sapphire/discord.js-utilities/-/discord.js-utilities-5.1.1.tgz",
+ "integrity": "sha512-xWiduo2kYXMJ2IHKYjPGzL6VisTP/kwVh61BlxBbnPOKQ87F3EYe4WuXuX7JqoPUZVdRSG3ZuBgrz0mKGF4p3w==",
"dependencies": {
"@sapphire/discord-utilities": "^2.11.6",
- "@sapphire/time-utilities": "^1.7.6",
- "@sapphire/utilities": "^3.9.2",
+ "@sapphire/duration": "^1.0.0",
+ "@sapphire/utilities": "^3.11.0",
"tslib": "^2.4.0"
},
"engines": {
@@ -327,22 +340,29 @@
"npm": ">=7.0.0"
}
},
+ "node_modules/@sapphire/duration": {
+ "version": "1.0.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/duration/-/duration-1.0.0.tgz",
+ "integrity": "sha512-B+6nKYnBmIlqqbamcR4iBvbQHz6/Kq2JUVM0rA3lQ+aYUYDdcA1Spt66CKtPWwdTYEtSv0VY6Jv27WCtFNYTUg==",
+ "engines": {
+ "node": ">=v14.0.0",
+ "npm": ">=7.0.0"
+ }
+ },
"node_modules/@sapphire/framework": {
- "version": "3.1.1",
- "resolved": "https://registry.npmjs.org/@sapphire/framework/-/framework-3.1.1.tgz",
- "integrity": "sha512-dWWIhqFwVZ7nMJ6o7mIhgOAQhSfaue6IPyRSYhXuLEOU9uiQpLioXaYckVAVspRGAc5MqIalOV2htjQF2nCgjw==",
+ "version": "3.1.3",
+ "resolved": "https://registry.npmjs.org/@sapphire/framework/-/framework-3.1.3.tgz",
+ "integrity": "sha512-YHB6oeY095vrRv8ksW0zm/GSWuw+vDLvU0BzJBTGI0KYQfNq2d6OVCjY0ADxFgQSgC9AxOHj2h2GvGcLET+S4g==",
"dependencies": {
"@discordjs/builders": "^0.16.0",
"@sapphire/discord-utilities": "^2.11.6",
- "@sapphire/discord.js-utilities": "^5.0.0",
- "@sapphire/lexure": "^1.0.2",
- "@sapphire/pieces": "^3.5.1",
- "@sapphire/ratelimits": "^2.4.4",
- "@sapphire/result": "^2.4.1",
- "@sapphire/stopwatch": "^1.4.1",
- "@sapphire/utilities": "^3.9.3",
- "@types/object-hash": "^2.2.1",
- "object-hash": "^3.0.0",
+ "@sapphire/discord.js-utilities": "^5.0.1",
+ "@sapphire/lexure": "^1.1.1",
+ "@sapphire/pieces": "^3.5.2",
+ "@sapphire/ratelimits": "^2.4.5",
+ "@sapphire/result": "^2.5.0",
+ "@sapphire/stopwatch": "^1.5.0",
+ "@sapphire/utilities": "^3.10.0",
"tslib": "^2.4.0"
},
"engines": {
@@ -372,11 +392,11 @@
"integrity": "sha512-bz/NDyG0KBo/tY14vSkrwQ/n3HKPf87a0WFW/1M9+tXYK+vp5Z5EksawfCWo2zkAc6o7CClc0eff1Pjrqznlwg=="
},
"node_modules/@sapphire/lexure": {
- "version": "1.0.2",
- "resolved": "https://registry.npmjs.org/@sapphire/lexure/-/lexure-1.0.2.tgz",
- "integrity": "sha512-KKKcCvjkB6AImGzpWdrbLVI++VnRinpus+a4yu+PUT7zUlzUZdma1P/P8XlRDFEx6U+d5jk8ygKyTPzQKvkqRA==",
+ "version": "1.1.2",
+ "resolved": "https://registry.npmjs.org/@sapphire/lexure/-/lexure-1.1.2.tgz",
+ "integrity": "sha512-+v3P3EMDdFoybHH7c7cMcz30jEyxujkxWu5f958cf/Sm27fMM0IqwILnNFUpExZCBAueEM/eoSgbRl4q+K+0jg==",
"dependencies": {
- "@sapphire/result": "^2.4.1"
+ "@sapphire/result": "^2.6.0"
},
"engines": {
"node": ">=v14.0.0",
@@ -384,12 +404,12 @@
}
},
"node_modules/@sapphire/pieces": {
- "version": "3.5.1",
- "resolved": "https://registry.npmjs.org/@sapphire/pieces/-/pieces-3.5.1.tgz",
- "integrity": "sha512-GEm7W6hAMC1yN76z0SZlIij66MDcuvWf7ra2TPGhflmv5ZUG4vNHNMktexP4AwEgKeF1jKJouVrIs3lAC3e4ZQ==",
+ "version": "3.5.2",
+ "resolved": "https://registry.npmjs.org/@sapphire/pieces/-/pieces-3.5.2.tgz",
+ "integrity": "sha512-B8ghwre5naTIMnJIlqJGhKX6ZTpGqz4oAtBd/ihX0CY69cPtbem3VHfZ8Sf5C+50l3mfe2AU7CfZQn9kLQR2fQ==",
"dependencies": {
- "@discordjs/collection": "^1.0.1",
- "@sapphire/utilities": "^3.9.2",
+ "@discordjs/collection": "^1.1.0",
+ "@sapphire/utilities": "^3.10.0",
"tslib": "^2.4.0"
},
"engines": {
@@ -398,11 +418,12 @@
}
},
"node_modules/@sapphire/plugin-scheduled-tasks": {
- "version": "4.0.0",
- "resolved": "https://registry.npmjs.org/@sapphire/plugin-scheduled-tasks/-/plugin-scheduled-tasks-4.0.0.tgz",
- "integrity": "sha512-MIYiG40HW9kPeZGPcGlLX3uPkKaruG2GIkUhu5gNS1kJogtx6NdZlY5hKBDnpjl1jND5+d2gX9aaLNFA7+UxKA==",
+ "version": "4.0.1",
+ "resolved": "https://registry.npmjs.org/@sapphire/plugin-scheduled-tasks/-/plugin-scheduled-tasks-4.0.1.tgz",
+ "integrity": "sha512-vLxfHBu2vKaJZ9v2f4z+VDZaPeDqS8bm+Sc2minRwJPw1hWAHiPqmxCBPIONY7eOQ9qKayvhKYTIwwruxgO/Mg==",
"dependencies": {
- "@sapphire/time-utilities": "^1.7.6",
+ "@sapphire/stopwatch": "^1.4.1",
+ "@sapphire/utilities": "^3.9.3",
"tslib": "^2.4.0"
},
"engines": {
@@ -411,11 +432,11 @@
}
},
"node_modules/@sapphire/plugin-subcommands": {
- "version": "3.2.1",
- "resolved": "https://registry.npmjs.org/@sapphire/plugin-subcommands/-/plugin-subcommands-3.2.1.tgz",
- "integrity": "sha512-I+NmbewS85oEfFx/0t8cGtimLmNGMzF6k5eigUmRakb7t6m1EK54cvWwV3zFbkhCMWI6e+ObiIe5XJVel8oWqg==",
+ "version": "3.2.3",
+ "resolved": "https://registry.npmjs.org/@sapphire/plugin-subcommands/-/plugin-subcommands-3.2.3.tgz",
+ "integrity": "sha512-xUDkHdOXmqquO++I54ZOZg8Prh2YIJ7sSGBLXCU+FiNDbsfzbxr/McCfnKL65L6RBYOjf8d06up3GKPL8t9GpQ==",
"dependencies": {
- "@sapphire/utilities": "^3.9.2",
+ "@sapphire/utilities": "^3.11.0",
"tslib": "^2.4.0"
},
"engines": {
@@ -424,11 +445,11 @@
}
},
"node_modules/@sapphire/ratelimits": {
- "version": "2.4.4",
- "resolved": "https://registry.npmjs.org/@sapphire/ratelimits/-/ratelimits-2.4.4.tgz",
- "integrity": "sha512-9gZ1BaY99HLWOcfuhlu0WklirHhVc6QD1pm5/v2W0O9pBpMHrd1GImVMXjYZRoy1qpmE2ZggSmN1665lktTCMw==",
+ "version": "2.4.5",
+ "resolved": "https://registry.npmjs.org/@sapphire/ratelimits/-/ratelimits-2.4.5.tgz",
+ "integrity": "sha512-2wqpVPRaPUE+CWStLm6wGLj1uA4Ln/9qbH4Ue/eCHC6/R5lJz0+8nGD1LpiYOcyeVLTHbmwODGeD92obkPej2g==",
"dependencies": {
- "@sapphire/time-utilities": "^1.7.4"
+ "@sapphire/timer-manager": "^1.0.0"
},
"engines": {
"node": ">=v14.0.0",
@@ -436,18 +457,18 @@
}
},
"node_modules/@sapphire/result": {
- "version": "2.4.1",
- "resolved": "https://registry.npmjs.org/@sapphire/result/-/result-2.4.1.tgz",
- "integrity": "sha512-RWgp+cCm1dhE/voMGwp3z5xGmsOluXW9EPIXyO+khMXxZDL3iAgp4/ZCSFEw3nI98njwGmgWYIzdQfCu3WA4OA==",
+ "version": "2.6.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/result/-/result-2.6.0.tgz",
+ "integrity": "sha512-gdW6n/oDZ8aC1439Ub3RiLQ6L4VHAxbN0AhGJWNkEZ6Z6Ww2V62fwRiA/73OPfgYQKXk9ljhAFiqNO91KAonHQ==",
"engines": {
"node": ">=v14.0.0",
"npm": ">=7.0.0"
}
},
"node_modules/@sapphire/shapeshift": {
- "version": "3.6.0",
- "resolved": "https://registry.npmjs.org/@sapphire/shapeshift/-/shapeshift-3.6.0.tgz",
- "integrity": "sha512-tu2WLRdo5wotHRvsCkspg3qMiP6ETC3Q1dns1Q5V6zKUki+1itq6AbhMwohF9ZcLoYqg+Y8LkgRRtVxxTQVTBQ==",
+ "version": "3.7.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/shapeshift/-/shapeshift-3.7.0.tgz",
+ "integrity": "sha512-A6vI1zJoxhjWo4grsxpBRBgk96SqSdjLX5WlzKp9H+bJbkM07mvwcbtbVAmUZHbi/OG3HLfiZ1rlw4BhH6tsBQ==",
"dependencies": {
"fast-deep-equal": "^3.1.3",
"lodash.uniqwith": "^4.5.0"
@@ -458,24 +479,21 @@
}
},
"node_modules/@sapphire/stopwatch": {
- "version": "1.4.1",
- "resolved": "https://registry.npmjs.org/@sapphire/stopwatch/-/stopwatch-1.4.1.tgz",
- "integrity": "sha512-FoZIM7oQ1kwkjWpl/rKReuDFSlkCDjDp//1Np2mmQD+xQ2Zyo/J2MaYAITprwQr3AUBu/OOUJvqm7f8lA9R7gA==",
+ "version": "1.5.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/stopwatch/-/stopwatch-1.5.0.tgz",
+ "integrity": "sha512-DtyKugdy3JTqm6JnEepTY64fGJAqlusDVrlrzifEgSCfGYCqpvB+SBldkWtDH+z+zLcp+PyaFLq7xpVfkhmvGg==",
"dependencies": {
- "tslib": "^2.3.1"
+ "tslib": "^2.4.0"
},
"engines": {
"node": ">=v14.0.0",
"npm": ">=7.0.0"
}
},
- "node_modules/@sapphire/time-utilities": {
- "version": "1.7.6",
- "resolved": "https://registry.npmjs.org/@sapphire/time-utilities/-/time-utilities-1.7.6.tgz",
- "integrity": "sha512-VsMVYFmS9Iu0buPs7gwn1D6vqIC04ezVMBRIo8vRTB2s7UNN/vQReX2cLABFoDVqs7RHQsvr2DPoTWHEDYw9YA==",
- "dependencies": {
- "@sapphire/utilities": "^3.9.2"
- },
+ "node_modules/@sapphire/timer-manager": {
+ "version": "1.0.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/timer-manager/-/timer-manager-1.0.0.tgz",
+ "integrity": "sha512-vxxnv75QPMGKt6IB6nL2xRJfwzcUQ9DBGzJLg6G8eS5O4u7j3IR/yr/GQsa4gIpjw6kQOgn8lUdnSTlpnERTbQ==",
"engines": {
"node": ">=v14.0.0",
"npm": ">=7.0.0"
@@ -485,6 +503,7 @@
"version": "3.3.4",
"resolved": "https://registry.npmjs.org/@sapphire/ts-config/-/ts-config-3.3.4.tgz",
"integrity": "sha512-mWEUxCXh3cHKI7C8HJ049exVTMNaq+A/lJEDfM5ENSQ/OOZHd5DdmXn2jrYqFWbTRCHa0Vp2FAmACWBwePsBtg==",
+ "dev": true,
"dependencies": {
"tslib": "^2.3.1",
"typescript": "^4.6.3"
@@ -495,9 +514,9 @@
}
},
"node_modules/@sapphire/utilities": {
- "version": "3.9.3",
- "resolved": "https://registry.npmjs.org/@sapphire/utilities/-/utilities-3.9.3.tgz",
- "integrity": "sha512-7+ZjfbmRHqewmH32jpZfzrEuHpvTttTG7WjDl1GUtc4pkOMr0kYybrZmIEZYsUvF7PWzO0GrmOK2zWs3GuJo7g==",
+ "version": "3.11.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/utilities/-/utilities-3.11.0.tgz",
+ "integrity": "sha512-ich7J+329UTEgWxgk8b871rMhbFW/hvXdabdiKaUKd6g10eIMkIakWf+EGkDQsiDSiebIXll9TIPPmWtN3cVSw==",
"engines": {
"node": ">=v14.0.0",
"npm": ">=7.0.0"
@@ -545,9 +564,9 @@
"dev": true
},
"node_modules/@types/node": {
- "version": "18.7.16",
- "resolved": "https://registry.npmjs.org/@types/node/-/node-18.7.16.tgz",
- "integrity": "sha512-EQHhixfu+mkqHMZl1R2Ovuvn47PUw18azMJOTwSZr9/fhzHNGXAJ0ma0dayRVchprpCj0Kc1K1xKoWaATWF1qg=="
+ "version": "18.11.3",
+ "resolved": "https://registry.npmjs.org/@types/node/-/node-18.11.3.tgz",
+ "integrity": "sha512-fNjDQzzOsZeKZu5NATgXUPsaFaTxeRgFXoosrHivTl8RGeV733OLawXsGfEk9a8/tySyZUyiZ6E8LcjPFZ2y1A=="
},
"node_modules/@types/node-fetch": {
"version": "2.6.2",
@@ -571,10 +590,11 @@
"node": ">= 6"
}
},
- "node_modules/@types/object-hash": {
- "version": "2.2.1",
- "resolved": "https://registry.npmjs.org/@types/object-hash/-/object-hash-2.2.1.tgz",
- "integrity": "sha512-i/rtaJFCsPljrZvP/akBqEwUP2y5cZLOmvO+JaYnz01aPknrQ+hB5MRcO7iqCUsFaYfTG8kGfKUyboA07xeDHQ=="
+ "node_modules/@types/semver": {
+ "version": "7.3.12",
+ "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.3.12.tgz",
+ "integrity": "sha512-WwA1MW0++RfXmCr12xeYOOC5baSC9mSb0ZqCquFzKhcoF4TvHu5MKOuXsncgZcpVFhB1pXd5hZmM0ryAoCp12A==",
+ "dev": true
},
"node_modules/@types/ws": {
"version": "8.5.3",
@@ -585,16 +605,15 @@
}
},
"node_modules/@typescript-eslint/eslint-plugin": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.36.2.tgz",
- "integrity": "sha512-OwwR8LRwSnI98tdc2z7mJYgY60gf7I9ZfGjN5EjCwwns9bdTuQfAXcsjSB2wSQ/TVNYSGKf4kzVXbNGaZvwiXw==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.40.1.tgz",
+ "integrity": "sha512-FsWboKkWdytGiXT5O1/R9j37YgcjO8MKHSUmWnIEjVaz0krHkplPnYi7mwdb+5+cs0toFNQb0HIrN7zONdIEWg==",
"dev": true,
"dependencies": {
- "@typescript-eslint/scope-manager": "5.36.2",
- "@typescript-eslint/type-utils": "5.36.2",
- "@typescript-eslint/utils": "5.36.2",
+ "@typescript-eslint/scope-manager": "5.40.1",
+ "@typescript-eslint/type-utils": "5.40.1",
+ "@typescript-eslint/utils": "5.40.1",
"debug": "^4.3.4",
- "functional-red-black-tree": "^1.0.1",
"ignore": "^5.2.0",
"regexpp": "^3.2.0",
"semver": "^7.3.7",
@@ -618,14 +637,14 @@
}
},
"node_modules/@typescript-eslint/parser": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.36.2.tgz",
- "integrity": "sha512-qS/Kb0yzy8sR0idFspI9Z6+t7mqk/oRjnAYfewG+VN73opAUvmYL3oPIMmgOX6CnQS6gmVIXGshlb5RY/R22pA==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.40.1.tgz",
+ "integrity": "sha512-IK6x55va5w4YvXd4b3VrXQPldV9vQTxi5ov+g4pMANsXPTXOcfjx08CRR1Dfrcc51syPtXHF5bgLlMHYFrvQtg==",
"dev": true,
"dependencies": {
- "@typescript-eslint/scope-manager": "5.36.2",
- "@typescript-eslint/types": "5.36.2",
- "@typescript-eslint/typescript-estree": "5.36.2",
+ "@typescript-eslint/scope-manager": "5.40.1",
+ "@typescript-eslint/types": "5.40.1",
+ "@typescript-eslint/typescript-estree": "5.40.1",
"debug": "^4.3.4"
},
"engines": {
@@ -645,13 +664,13 @@
}
},
"node_modules/@typescript-eslint/scope-manager": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.36.2.tgz",
- "integrity": "sha512-cNNP51L8SkIFSfce8B1NSUBTJTu2Ts4nWeWbFrdaqjmn9yKrAaJUBHkyTZc0cL06OFHpb+JZq5AUHROS398Orw==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.40.1.tgz",
+ "integrity": "sha512-jkn4xsJiUQucI16OLCXrLRXDZ3afKhOIqXs4R3O+M00hdQLKR58WuyXPZZjhKLFCEP2g+TXdBRtLQ33UfAdRUg==",
"dev": true,
"dependencies": {
- "@typescript-eslint/types": "5.36.2",
- "@typescript-eslint/visitor-keys": "5.36.2"
+ "@typescript-eslint/types": "5.40.1",
+ "@typescript-eslint/visitor-keys": "5.40.1"
},
"engines": {
"node": "^12.22.0 || ^14.17.0 || >=16.0.0"
@@ -662,13 +681,13 @@
}
},
"node_modules/@typescript-eslint/type-utils": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.36.2.tgz",
- "integrity": "sha512-rPQtS5rfijUWLouhy6UmyNquKDPhQjKsaKH0WnY6hl/07lasj8gPaH2UD8xWkePn6SC+jW2i9c2DZVDnL+Dokw==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.40.1.tgz",
+ "integrity": "sha512-DLAs+AHQOe6n5LRraXiv27IYPhleF0ldEmx6yBqBgBLaNRKTkffhV1RPsjoJBhVup2zHxfaRtan8/YRBgYhU9Q==",
"dev": true,
"dependencies": {
- "@typescript-eslint/typescript-estree": "5.36.2",
- "@typescript-eslint/utils": "5.36.2",
+ "@typescript-eslint/typescript-estree": "5.40.1",
+ "@typescript-eslint/utils": "5.40.1",
"debug": "^4.3.4",
"tsutils": "^3.21.0"
},
@@ -689,9 +708,9 @@
}
},
"node_modules/@typescript-eslint/types": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.36.2.tgz",
- "integrity": "sha512-9OJSvvwuF1L5eS2EQgFUbECb99F0mwq501w0H0EkYULkhFa19Qq7WFbycdw1PexAc929asupbZcgjVIe6OK/XQ==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.40.1.tgz",
+ "integrity": "sha512-Icg9kiuVJSwdzSQvtdGspOlWNjVDnF3qVIKXdJ103o36yRprdl3Ge5cABQx+csx960nuMF21v8qvO31v9t3OHw==",
"dev": true,
"engines": {
"node": "^12.22.0 || ^14.17.0 || >=16.0.0"
@@ -702,13 +721,13 @@
}
},
"node_modules/@typescript-eslint/typescript-estree": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.36.2.tgz",
- "integrity": "sha512-8fyH+RfbKc0mTspfuEjlfqA4YywcwQK2Amcf6TDOwaRLg7Vwdu4bZzyvBZp4bjt1RRjQ5MDnOZahxMrt2l5v9w==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.40.1.tgz",
+ "integrity": "sha512-5QTP/nW5+60jBcEPfXy/EZL01qrl9GZtbgDZtDPlfW5zj/zjNrdI2B5zMUHmOsfvOr2cWqwVdWjobCiHcedmQA==",
"dev": true,
"dependencies": {
- "@typescript-eslint/types": "5.36.2",
- "@typescript-eslint/visitor-keys": "5.36.2",
+ "@typescript-eslint/types": "5.40.1",
+ "@typescript-eslint/visitor-keys": "5.40.1",
"debug": "^4.3.4",
"globby": "^11.1.0",
"is-glob": "^4.0.3",
@@ -729,17 +748,19 @@
}
},
"node_modules/@typescript-eslint/utils": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.36.2.tgz",
- "integrity": "sha512-uNcopWonEITX96v9pefk9DC1bWMdkweeSsewJ6GeC7L6j2t0SJywisgkr9wUTtXk90fi2Eljj90HSHm3OGdGRg==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.40.1.tgz",
+ "integrity": "sha512-a2TAVScoX9fjryNrW6BZRnreDUszxqm9eQ9Esv8n5nXApMW0zeANUYlwh/DED04SC/ifuBvXgZpIK5xeJHQ3aw==",
"dev": true,
"dependencies": {
"@types/json-schema": "^7.0.9",
- "@typescript-eslint/scope-manager": "5.36.2",
- "@typescript-eslint/types": "5.36.2",
- "@typescript-eslint/typescript-estree": "5.36.2",
+ "@types/semver": "^7.3.12",
+ "@typescript-eslint/scope-manager": "5.40.1",
+ "@typescript-eslint/types": "5.40.1",
+ "@typescript-eslint/typescript-estree": "5.40.1",
"eslint-scope": "^5.1.1",
- "eslint-utils": "^3.0.0"
+ "eslint-utils": "^3.0.0",
+ "semver": "^7.3.7"
},
"engines": {
"node": "^12.22.0 || ^14.17.0 || >=16.0.0"
@@ -753,12 +774,12 @@
}
},
"node_modules/@typescript-eslint/visitor-keys": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.36.2.tgz",
- "integrity": "sha512-BtRvSR6dEdrNt7Net2/XDjbYKU5Ml6GqJgVfXT0CxTCJlnIqK7rAGreuWKMT2t8cFUT2Msv5oxw0GMRD7T5J7A==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.40.1.tgz",
+ "integrity": "sha512-A2DGmeZ+FMja0geX5rww+DpvILpwo1OsiQs0M+joPWJYsiEFBLsH0y1oFymPNul6Z5okSmHpP4ivkc2N0Cgfkw==",
"dev": true,
"dependencies": {
- "@typescript-eslint/types": "5.36.2",
+ "@typescript-eslint/types": "5.40.1",
"eslint-visitor-keys": "^3.3.0"
},
"engines": {
@@ -927,9 +948,9 @@
}
},
"node_modules/bullmq": {
- "version": "1.90.1",
- "resolved": "https://registry.npmjs.org/bullmq/-/bullmq-1.90.1.tgz",
- "integrity": "sha512-JY8mNzfnl+lfzFFzLJa6if+4YFvCMuJZDtQ8gvkcedoet+fDPEETF0iZ2fuzxCizuneARCniAiwIR/ESnqbuKw==",
+ "version": "1.91.1",
+ "resolved": "https://registry.npmjs.org/bullmq/-/bullmq-1.91.1.tgz",
+ "integrity": "sha512-u7dat9I8ZwouZ651AMZkBSvB6NVUPpnAjd4iokd9DM41whqIBnDjuL11h7+kEjcpiDKj6E+wxZiER00FqirZQg==",
"dependencies": {
"cron-parser": "^4.6.0",
"get-port": "6.1.2",
@@ -939,7 +960,7 @@
"msgpackr": "^1.6.2",
"semver": "^7.3.7",
"tslib": "^2.0.0",
- "uuid": "^8.3.2"
+ "uuid": "^9.0.0"
}
},
"node_modules/call-bind": {
@@ -981,9 +1002,9 @@
}
},
"node_modules/cluster-key-slot": {
- "version": "1.1.0",
- "resolved": "https://registry.npmjs.org/cluster-key-slot/-/cluster-key-slot-1.1.0.tgz",
- "integrity": "sha512-2Nii8p3RwAPiFwsnZvukotvow2rIHM+yQ6ZcBXGHdniadkYGZYiGmkHJIbZPIV9nfv7m/U1IPMVVcAhoWFeklw==",
+ "version": "1.1.1",
+ "resolved": "https://registry.npmjs.org/cluster-key-slot/-/cluster-key-slot-1.1.1.tgz",
+ "integrity": "sha512-rwHwUfXL40Chm1r08yrhU3qpUvdVlgkKNeyeGPOxnW8/SyVDvgRaed/Uz54AqWNaTCAThlj6QAs3TZcKI0xDEw==",
"engines": {
"node": ">=0.10.0"
}
@@ -1139,19 +1160,19 @@
"integrity": "sha512-dvO5M52v7m7Dy96+XUnzXNsQ/0npsYpU6dL205kAtEDueswoz3aU3bh1UMoK4cQmcGtB1YRyLKqp+DXi05lzFg=="
},
"node_modules/discord.js": {
- "version": "13.10.3",
- "resolved": "https://registry.npmjs.org/discord.js/-/discord.js-13.10.3.tgz",
- "integrity": "sha512-cIARuxfpQDeqA9Zw3fz4IL20xAhtMsjwJIf7/K82R3n2xROG9/fAx+7qjX8ysp9BfflYqMu2ZskyWq1EAmL5BA==",
+ "version": "13.12.0",
+ "resolved": "https://registry.npmjs.org/discord.js/-/discord.js-13.12.0.tgz",
+ "integrity": "sha512-K5qhREsYcTHkEqt7+7LcSoXTeQYZpI+SQRs9ei/FhbhUpirmjqFtN99P8W2mrKUyhhy7WXWm7rnna0AooKtIpw==",
"dependencies": {
"@discordjs/builders": "^0.16.0",
"@discordjs/collection": "^0.7.0",
"@sapphire/async-queue": "^1.5.0",
"@types/node-fetch": "^2.6.2",
"@types/ws": "^8.5.3",
- "discord-api-types": "^0.33.3",
+ "discord-api-types": "^0.33.5",
"form-data": "^4.0.0",
"node-fetch": "^2.6.7",
- "ws": "^8.8.1"
+ "ws": "^8.9.0"
},
"engines": {
"node": ">=16.6.0",
@@ -1201,30 +1222,30 @@
}
},
"node_modules/dotenv": {
- "version": "16.0.2",
- "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.0.2.tgz",
- "integrity": "sha512-JvpYKUmzQhYoIFgK2MOnF3bciIZoItIIoryihy0rIA+H4Jy0FmgyKYAHCTN98P5ybGSJcIFbh6QKeJdtZd1qhA==",
+ "version": "16.0.3",
+ "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.0.3.tgz",
+ "integrity": "sha512-7GO6HghkA5fYG9TYnNxi14/7K9f5occMlp3zXAuSxn7CKCxt9xbNWG7yF8hTCSUchlfWSe3uLmlPfigevRItzQ==",
"engines": {
"node": ">=12"
}
},
"node_modules/es-abstract": {
- "version": "1.20.2",
- "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.20.2.tgz",
- "integrity": "sha512-XxXQuVNrySBNlEkTYJoDNFe5+s2yIOpzq80sUHEdPdQr0S5nTLz4ZPPPswNIpKseDDUS5yghX1gfLIHQZ1iNuQ==",
+ "version": "1.20.4",
+ "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.20.4.tgz",
+ "integrity": "sha512-0UtvRN79eMe2L+UNEF1BwRe364sj/DXhQ/k5FmivgoSdpM90b8Jc0mDzKMGo7QS0BVbOP/bTwBKNnDc9rNzaPA==",
"dev": true,
"dependencies": {
"call-bind": "^1.0.2",
"es-to-primitive": "^1.2.1",
"function-bind": "^1.1.1",
"function.prototype.name": "^1.1.5",
- "get-intrinsic": "^1.1.2",
+ "get-intrinsic": "^1.1.3",
"get-symbol-description": "^1.0.0",
"has": "^1.0.3",
"has-property-descriptors": "^1.0.0",
"has-symbols": "^1.0.3",
"internal-slot": "^1.0.3",
- "is-callable": "^1.2.4",
+ "is-callable": "^1.2.7",
"is-negative-zero": "^2.0.2",
"is-regex": "^1.1.4",
"is-shared-array-buffer": "^1.0.2",
@@ -1234,6 +1255,7 @@
"object-keys": "^1.1.1",
"object.assign": "^4.1.4",
"regexp.prototype.flags": "^1.4.3",
+ "safe-regex-test": "^1.0.0",
"string.prototype.trimend": "^1.0.5",
"string.prototype.trimstart": "^1.0.5",
"unbox-primitive": "^1.0.2"
@@ -1284,14 +1306,14 @@
}
},
"node_modules/eslint": {
- "version": "8.22.0",
- "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.22.0.tgz",
- "integrity": "sha512-ci4t0sz6vSRKdmkOGmprBo6fmI4PrphDFMy5JEq/fNS0gQkJM3rLmrqcp8ipMcdobH3KtUP40KniAE9W19S4wA==",
+ "version": "8.25.0",
+ "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.25.0.tgz",
+ "integrity": "sha512-DVlJOZ4Pn50zcKW5bYH7GQK/9MsoQG2d5eDH0ebEkE8PbgzTTmtt/VTH9GGJ4BfeZCpBLqFfvsjX35UacUL83A==",
"dev": true,
"dependencies": {
- "@eslint/eslintrc": "^1.3.0",
- "@humanwhocodes/config-array": "^0.10.4",
- "@humanwhocodes/gitignore-to-minimatch": "^1.0.2",
+ "@eslint/eslintrc": "^1.3.3",
+ "@humanwhocodes/config-array": "^0.10.5",
+ "@humanwhocodes/module-importer": "^1.0.1",
"ajv": "^6.10.0",
"chalk": "^4.0.0",
"cross-spawn": "^7.0.2",
@@ -1301,13 +1323,12 @@
"eslint-scope": "^7.1.1",
"eslint-utils": "^3.0.0",
"eslint-visitor-keys": "^3.3.0",
- "espree": "^9.3.3",
+ "espree": "^9.4.0",
"esquery": "^1.4.0",
"esutils": "^2.0.2",
"fast-deep-equal": "^3.1.3",
"file-entry-cache": "^6.0.1",
"find-up": "^5.0.0",
- "functional-red-black-tree": "^1.0.1",
"glob-parent": "^6.0.1",
"globals": "^13.15.0",
"globby": "^11.1.0",
@@ -1316,6 +1337,7 @@
"import-fresh": "^3.0.0",
"imurmurhash": "^0.1.4",
"is-glob": "^4.0.0",
+ "js-sdsl": "^4.1.4",
"js-yaml": "^4.1.0",
"json-stable-stringify-without-jsonify": "^1.0.1",
"levn": "^0.4.1",
@@ -1326,8 +1348,7 @@
"regexpp": "^3.2.0",
"strip-ansi": "^6.0.1",
"strip-json-comments": "^3.1.0",
- "text-table": "^0.2.0",
- "v8-compile-cache": "^2.0.3"
+ "text-table": "^0.2.0"
},
"bin": {
"eslint": "bin/eslint.js"
@@ -1635,9 +1656,9 @@
"integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q=="
},
"node_modules/fast-glob": {
- "version": "3.2.11",
- "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.11.tgz",
- "integrity": "sha512-xrO3+1bxSo3ZVHAnqzyuewYT6aMFHRAd4Kcs92MAonjwQZLsK9d0SF1IyQ3k5PoirxTW0Oe/RqFgMQ6TcNE5Ew==",
+ "version": "3.2.12",
+ "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.12.tgz",
+ "integrity": "sha512-DVj4CQIYYow0BlaelwK1pHl5n5cRSJfM60UA0zK891sVInoPri2Ekj7+e1CT3/3qxXenpI+nBBmQAcJPJgaj4w==",
"dev": true,
"dependencies": {
"@nodelib/fs.stat": "^2.0.2",
@@ -1784,12 +1805,6 @@
"url": "https://github.com/sponsors/ljharb"
}
},
- "node_modules/functional-red-black-tree": {
- "version": "1.0.1",
- "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz",
- "integrity": "sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g==",
- "dev": true
- },
"node_modules/functions-have-names": {
"version": "1.2.3",
"resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz",
@@ -1800,9 +1815,9 @@
}
},
"node_modules/get-intrinsic": {
- "version": "1.1.2",
- "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.1.2.tgz",
- "integrity": "sha512-Jfm3OyCxHh9DJyc28qGk+JmfkpO41A4XkneDSujN9MDXrm4oDKdHvndhZ2dN94+ERNfkYJWDclW6k2L/ZGHjXA==",
+ "version": "1.1.3",
+ "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.1.3.tgz",
+ "integrity": "sha512-QJVz1Tj7MS099PevUG5jvnt9tSkXN8K14dxQlikJuPt4uD9hHAHjLyLBiLR5zELelBdD9QNRAXZzsJx0WaDL9A==",
"dev": true,
"dependencies": {
"function-bind": "^1.1.1",
@@ -2113,9 +2128,9 @@
}
},
"node_modules/is-callable": {
- "version": "1.2.4",
- "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.4.tgz",
- "integrity": "sha512-nsuwtxZfMX67Oryl9LCQ+upnC0Z0BgpwntpS89m1H/TLF0zNfzfLMV/9Wa/6MZsj0acpEjAO0KF1xT6ZdLl95w==",
+ "version": "1.2.7",
+ "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz",
+ "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==",
"dev": true,
"engines": {
"node": ">= 0.4"
@@ -2125,9 +2140,9 @@
}
},
"node_modules/is-core-module": {
- "version": "2.10.0",
- "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.10.0.tgz",
- "integrity": "sha512-Erxj2n/LDAZ7H8WNJXd9tw38GYM3dv8rk8Zcs+jJuxYTW7sozH+SS8NtrSjVL1/vpLvWi1hxy96IzjJ3EHTJJg==",
+ "version": "2.11.0",
+ "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.11.0.tgz",
+ "integrity": "sha512-RRjxlvLDkD1YJwDbroBHMb+cukurkDWNyHx7D3oNB5x9rb5ogcksMC5wHCadcXoo67gVr/+3GFySh3134zi6rw==",
"dev": true,
"dependencies": {
"has": "^1.0.3"
@@ -2284,6 +2299,12 @@
"integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==",
"dev": true
},
+ "node_modules/js-sdsl": {
+ "version": "4.1.5",
+ "resolved": "https://registry.npmjs.org/js-sdsl/-/js-sdsl-4.1.5.tgz",
+ "integrity": "sha512-08bOAKweV2NUC1wqTtf3qZlnpOX/R2DU9ikpjOHs0H+ibQv3zpncVQg6um4uYtRtrwIX8M4Nh3ytK4HGlYAq7Q==",
+ "dev": true
+ },
"node_modules/js-yaml": {
"version": "4.1.0",
"resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz",
@@ -2386,9 +2407,9 @@
}
},
"node_modules/luxon": {
- "version": "3.0.3",
- "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.0.3.tgz",
- "integrity": "sha512-+EfHWnF+UT7GgTnq5zXg3ldnTKL2zdv7QJgsU5bjjpbH17E3qi/puMhQyJVYuCq+FRkogvB5WB6iVvUr+E4a7w==",
+ "version": "3.0.4",
+ "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.0.4.tgz",
+ "integrity": "sha512-aV48rGUwP/Vydn8HT+5cdr26YYQiUZ42NM6ToMoaGKwYfWbfLeRkEu1wXWMHBZT6+KyLfcbbtVcoQFCbbPjKlw==",
"engines": {
"node": ">=12"
}
@@ -2452,10 +2473,13 @@
}
},
"node_modules/minimist": {
- "version": "1.2.6",
- "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.6.tgz",
- "integrity": "sha512-Jsjnk4bw3YJqYzbdyBiNsPWHPfO++UGG749Cxs6peCu5Xg4nrena6OVxOYxrQTqww0Jmwt+Ref8rggumkTLz9Q==",
- "dev": true
+ "version": "1.2.7",
+ "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.7.tgz",
+ "integrity": "sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g==",
+ "dev": true,
+ "funding": {
+ "url": "https://github.com/sponsors/ljharb"
+ }
},
"node_modules/ms": {
"version": "2.1.2",
@@ -2463,11 +2487,11 @@
"integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w=="
},
"node_modules/msgpackr": {
- "version": "1.6.2",
- "resolved": "https://registry.npmjs.org/msgpackr/-/msgpackr-1.6.2.tgz",
- "integrity": "sha512-bqSQ0DYJbXbrJcrZFmMygUZmqQiDfI2ewFVWcrZY12w5XHWtPuW4WppDT/e63Uu311ajwkRRXSoF0uILroBeTA==",
+ "version": "1.7.2",
+ "resolved": "https://registry.npmjs.org/msgpackr/-/msgpackr-1.7.2.tgz",
+ "integrity": "sha512-mWScyHTtG6TjivXX9vfIy2nBtRupaiAj0HQ2mtmpmYujAmqZmaaEVPaSZ1NKLMvicaMLFzEaMk0ManxMRg8rMQ==",
"optionalDependencies": {
- "msgpackr-extract": "^2.0.2"
+ "msgpackr-extract": "^2.1.2"
}
},
"node_modules/msgpackr-extract": {
@@ -2527,14 +2551,6 @@
"node-gyp-build-optional-packages-test": "build-test.js"
}
},
- "node_modules/object-hash": {
- "version": "3.0.0",
- "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-3.0.0.tgz",
- "integrity": "sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw==",
- "engines": {
- "node": ">= 6"
- }
- },
"node_modules/object-inspect": {
"version": "1.12.2",
"resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.2.tgz",
@@ -2733,12 +2749,13 @@
}
},
"node_modules/prisma": {
- "version": "4.3.1",
- "resolved": "https://registry.npmjs.org/prisma/-/prisma-4.3.1.tgz",
- "integrity": "sha512-90xo06wtqil76Xsi3mNpc4Js3SdDRR5g4qb9h+4VWY4Y8iImJY6xc3PX+C9xxTSt1lr0Q89A0MLkJjd8ax6KiQ==",
+ "version": "4.5.0",
+ "resolved": "https://registry.npmjs.org/prisma/-/prisma-4.5.0.tgz",
+ "integrity": "sha512-9Aeg4qiKlv9Wsjz4NO8k2CzRzlvS3A4FYVJ5+28sBBZ0eEwbiVOE/Jj7v6rZC1tFW2s4GSICQOAyuOjc6WsNew==",
+ "devOptional": true,
"hasInstallScript": true,
"dependencies": {
- "@prisma/engines": "4.3.1"
+ "@prisma/engines": "4.5.0"
},
"bin": {
"prisma": "build/index.js",
@@ -2919,10 +2936,24 @@
"queue-microtask": "^1.2.2"
}
},
+ "node_modules/safe-regex-test": {
+ "version": "1.0.0",
+ "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.0.tgz",
+ "integrity": "sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA==",
+ "dev": true,
+ "dependencies": {
+ "call-bind": "^1.0.2",
+ "get-intrinsic": "^1.1.3",
+ "is-regex": "^1.1.4"
+ },
+ "funding": {
+ "url": "https://github.com/sponsors/ljharb"
+ }
+ },
"node_modules/semver": {
- "version": "7.3.7",
- "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.7.tgz",
- "integrity": "sha512-QlYTucUYOews+WeEujDoEGziz4K6c47V/Bd+LjSSYcA94p+DmINdf7ncaUinThfvZyu13lN9OY1XDxt8C0Tw0g==",
+ "version": "7.3.8",
+ "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz",
+ "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==",
"dependencies": {
"lru-cache": "^6.0.0"
},
@@ -3200,9 +3231,9 @@
}
},
"node_modules/typescript": {
- "version": "4.8.3",
- "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.8.3.tgz",
- "integrity": "sha512-goMHfm00nWPa8UvR/CPSvykqf6dVV8x/dp0c5mFTMTIu0u0FlGWRioyy7Nn0PGAdHxpJZnuO/ut+PpQ8UiHAig==",
+ "version": "4.8.4",
+ "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.8.4.tgz",
+ "integrity": "sha512-QCh+85mCy+h0IGff8r5XWzOVSbBO+KfeYrMQh7NJ58QujwcE22u+NUSmUxqF+un70P9GXKxa2HCNiTTMJknyjQ==",
"bin": {
"tsc": "bin/tsc",
"tsserver": "bin/tsserver"
@@ -3236,19 +3267,13 @@
}
},
"node_modules/uuid": {
- "version": "8.3.2",
- "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz",
- "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==",
+ "version": "9.0.0",
+ "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.0.tgz",
+ "integrity": "sha512-MXcSTerfPa4uqyzStbRoTgt5XIe3x5+42+q1sDuy3R5MDk66URdLMOZe5aPX/SQd+kuYAh0FdP/pO28IkQyTeg==",
"bin": {
"uuid": "dist/bin/uuid"
}
},
- "node_modules/v8-compile-cache": {
- "version": "2.3.0",
- "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz",
- "integrity": "sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==",
- "dev": true
- },
"node_modules/v8-compile-cache-lib": {
"version": "3.0.1",
"resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz",
@@ -3314,9 +3339,9 @@
"integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ=="
},
"node_modules/ws": {
- "version": "8.8.1",
- "resolved": "https://registry.npmjs.org/ws/-/ws-8.8.1.tgz",
- "integrity": "sha512-bGy2JzvzkPowEJV++hF07hAD6niYSr0JzBNo/J29WsB57A2r7Wlc1UFcTR9IzrPvuNVO4B8LGqF8qcpsVOhJCA==",
+ "version": "8.9.0",
+ "resolved": "https://registry.npmjs.org/ws/-/ws-8.9.0.tgz",
+ "integrity": "sha512-Ja7nszREasGaYUYCI2k4lCKIRTt+y7XuqVoHR44YpI49TtryyqbqvDMn5eqfW7e6HzTukDRIsXqzVHScqRcafg==",
"engines": {
"node": ">=10.0.0"
},
@@ -3369,33 +3394,39 @@
}
},
"@discordjs/builders": {
- "version": "1.2.0",
- "resolved": "https://registry.npmjs.org/@discordjs/builders/-/builders-1.2.0.tgz",
- "integrity": "sha512-ARy4BUTMU+S0ZI6605NDqfWO+qZqV2d/xfY32z3hVSsd9IaAKJBZ1ILTZLy87oIjW8+gUpQmk9Kt0ZP9bmmd8Q==",
+ "version": "1.3.0",
+ "resolved": "https://registry.npmjs.org/@discordjs/builders/-/builders-1.3.0.tgz",
+ "integrity": "sha512-Pvca6Nw8Hp+n3N+Wp17xjygXmMvggbh5ywUsOYE2Et4xkwwVRwgzxDJiMUuYapPtnYt4w/8aKlf5khc8ipLvhg==",
"requires": {
- "@sapphire/shapeshift": "^3.5.1",
- "discord-api-types": "^0.37.3",
+ "@discordjs/util": "^0.1.0",
+ "@sapphire/shapeshift": "^3.7.0",
+ "discord-api-types": "^0.37.12",
"fast-deep-equal": "^3.1.3",
"ts-mixer": "^6.0.1",
"tslib": "^2.4.0"
},
"dependencies": {
"discord-api-types": {
- "version": "0.37.8",
- "resolved": "https://registry.npmjs.org/discord-api-types/-/discord-api-types-0.37.8.tgz",
- "integrity": "sha512-uhol9KQ2moExZItMpuDMkf0R7sqqNHqcJBFN7S5iSdXBVCMRO7sC0GoyuRrv6ZDBYxoFU6nDy4dv0nld/aysqA=="
+ "version": "0.37.14",
+ "resolved": "https://registry.npmjs.org/discord-api-types/-/discord-api-types-0.37.14.tgz",
+ "integrity": "sha512-byBH7SfDCMJwxdqeS8k5sihltH88/YPhuwx+vF2cftSxFLdxyHyU/ZxDL3bq+LB2c4ls/TymE76/ISlLfniUXg=="
}
}
},
"@discordjs/collection": {
- "version": "1.1.0",
- "resolved": "https://registry.npmjs.org/@discordjs/collection/-/collection-1.1.0.tgz",
- "integrity": "sha512-PQ2Bv6pnT7aGPCKWbvvNRww5tYCGpggIQVgpuF9TdDPeR6n6vQYxezXiLVOS9z2B62Dp4c+qepQ15SgJbLYtCQ=="
+ "version": "1.2.0",
+ "resolved": "https://registry.npmjs.org/@discordjs/collection/-/collection-1.2.0.tgz",
+ "integrity": "sha512-VvrrtGb7vbfPHzbhGq9qZB5o8FOB+kfazrxdt0OtxzSkoBuw9dURMkCwWizZ00+rDpiK2HmLHBZX+y6JsG9khw=="
+ },
+ "@discordjs/util": {
+ "version": "0.1.0",
+ "resolved": "https://registry.npmjs.org/@discordjs/util/-/util-0.1.0.tgz",
+ "integrity": "sha512-e7d+PaTLVQav6rOc2tojh2y6FE8S7REkqLldq1XF4soCx74XB/DIjbVbVLtBemf0nLW77ntz0v+o5DytKwFNLQ=="
},
"@eslint/eslintrc": {
- "version": "1.3.1",
- "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.3.1.tgz",
- "integrity": "sha512-OhSY22oQQdw3zgPOOwdoj01l/Dzl1Z+xyUP33tkSN+aqyEhymJCcPHyXt+ylW8FSe0TfRC2VG+ROQOapD0aZSQ==",
+ "version": "1.3.3",
+ "resolved": "https://registry.npmjs.org/@eslint/eslintrc/-/eslintrc-1.3.3.tgz",
+ "integrity": "sha512-uj3pT6Mg+3t39fvLrj8iuCIJ38zKO9FpGtJ4BBJebJhEwjoT+KLVNCcHT5QC9NGRIEi7fZ0ZR8YRb884auB4Lg==",
"dev": true,
"requires": {
"ajv": "^6.12.4",
@@ -3410,9 +3441,9 @@
}
},
"@humanwhocodes/config-array": {
- "version": "0.10.4",
- "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.10.4.tgz",
- "integrity": "sha512-mXAIHxZT3Vcpg83opl1wGlVZ9xydbfZO3r5YfRSH6Gpp2J/PfdBP0wbDa2sO6/qRbcalpoevVyW6A/fI6LfeMw==",
+ "version": "0.10.7",
+ "resolved": "https://registry.npmjs.org/@humanwhocodes/config-array/-/config-array-0.10.7.tgz",
+ "integrity": "sha512-MDl6D6sBsaV452/QSdX+4CXIjZhIcI0PELsxUjk4U828yd58vk3bTIvk/6w5FY+4hIy9sLW0sfrV7K7Kc++j/w==",
"dev": true,
"requires": {
"@humanwhocodes/object-schema": "^1.2.1",
@@ -3420,10 +3451,10 @@
"minimatch": "^3.0.4"
}
},
- "@humanwhocodes/gitignore-to-minimatch": {
- "version": "1.0.2",
- "resolved": "https://registry.npmjs.org/@humanwhocodes/gitignore-to-minimatch/-/gitignore-to-minimatch-1.0.2.tgz",
- "integrity": "sha512-rSqmMJDdLFUsyxR6FMtD00nfQKKLFb1kv+qBbOVKqErvloEIJLo5bDTJTQNTYgeyp78JsA7u/NPi5jT1GR/MuA==",
+ "@humanwhocodes/module-importer": {
+ "version": "1.0.1",
+ "resolved": "https://registry.npmjs.org/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz",
+ "integrity": "sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==",
"dev": true
},
"@humanwhocodes/object-schema": {
@@ -3519,22 +3550,23 @@
}
},
"@prisma/client": {
- "version": "4.3.1",
- "resolved": "https://registry.npmjs.org/@prisma/client/-/client-4.3.1.tgz",
- "integrity": "sha512-FA0/d1VMJNWqzU7WVWTNWJ+lGOLR9JUBnF73GdIPAEVo/6dWk4gHx0EmgeU+SMv4MZoxgOeTBJF2azhg7x0hMw==",
+ "version": "4.5.0",
+ "resolved": "https://registry.npmjs.org/@prisma/client/-/client-4.5.0.tgz",
+ "integrity": "sha512-B2cV0OPI1smhdYUxsJoLYQLoMlLH06MUxgFUWQnHodGMX98VRVXKmQE/9OcrTNkqtke5RC+YU24Szxd04tZA2g==",
"requires": {
- "@prisma/engines-version": "4.3.0-32.c875e43600dfe042452e0b868f7a48b817b9640b"
+ "@prisma/engines-version": "4.5.0-43.0362da9eebca54d94c8ef5edd3b2e90af99ba452"
}
},
"@prisma/engines": {
- "version": "4.3.1",
- "resolved": "https://registry.npmjs.org/@prisma/engines/-/engines-4.3.1.tgz",
- "integrity": "sha512-4JF/uMaEDAPdcdZNOrnzE3BvrbGpjgV0FcPT3EVoi6I86fWkloqqxBt+KcK/+fIRR0Pxj66uGR9wVH8U1Y13JA=="
+ "version": "4.5.0",
+ "resolved": "https://registry.npmjs.org/@prisma/engines/-/engines-4.5.0.tgz",
+ "integrity": "sha512-4t9ir2SbQQr/wMCNU4YpHWp5hU14J2m3wHUZnGJPpmBF8YtkisxyVyQsKd1e6FyLTaGq8LOLhm6VLYHKqKNm+g==",
+ "devOptional": true
},
"@prisma/engines-version": {
- "version": "4.3.0-32.c875e43600dfe042452e0b868f7a48b817b9640b",
- "resolved": "https://registry.npmjs.org/@prisma/engines-version/-/engines-version-4.3.0-32.c875e43600dfe042452e0b868f7a48b817b9640b.tgz",
- "integrity": "sha512-8yWpXkQRmiSfsi2Wb/ZS5D3RFbeu/btL9Pm/gdF4phB0Lo5KGsDFMxFMgaD64mwED2nHc8ZaEJg/+4Jymb9Znw=="
+ "version": "4.5.0-43.0362da9eebca54d94c8ef5edd3b2e90af99ba452",
+ "resolved": "https://registry.npmjs.org/@prisma/engines-version/-/engines-version-4.5.0-43.0362da9eebca54d94c8ef5edd3b2e90af99ba452.tgz",
+ "integrity": "sha512-o7LyVx8PPJBLrEzLl6lpxxk2D5VnlM4Fwmrbq0NoT6pr5aa1OuHD9ZG+WJY6TlR/iD9bhmo2LNcxddCMr5Rv2A=="
},
"@sapphire/async-queue": {
"version": "1.5.0",
@@ -3547,32 +3579,35 @@
"integrity": "sha512-oFZYl7Prtqy8nD3ymmMpSMRy9Sdhp8E5PSI8n3OoBkHr4eSBvoOcBTxKapvRkHWes+amWeH/uB4UH31x7mG0KQ=="
},
"@sapphire/discord.js-utilities": {
- "version": "5.0.0",
- "resolved": "https://registry.npmjs.org/@sapphire/discord.js-utilities/-/discord.js-utilities-5.0.0.tgz",
- "integrity": "sha512-XvXkL0/e4AwKIipSxPeNNa8UPmSCoc+vwkNrnvV43a0JUJ1acxPPWrcpxAzE9lRxPY/vDLYaaEw7M/hkg3i5xQ==",
+ "version": "5.1.1",
+ "resolved": "https://registry.npmjs.org/@sapphire/discord.js-utilities/-/discord.js-utilities-5.1.1.tgz",
+ "integrity": "sha512-xWiduo2kYXMJ2IHKYjPGzL6VisTP/kwVh61BlxBbnPOKQ87F3EYe4WuXuX7JqoPUZVdRSG3ZuBgrz0mKGF4p3w==",
"requires": {
"@sapphire/discord-utilities": "^2.11.6",
- "@sapphire/time-utilities": "^1.7.6",
- "@sapphire/utilities": "^3.9.2",
+ "@sapphire/duration": "^1.0.0",
+ "@sapphire/utilities": "^3.11.0",
"tslib": "^2.4.0"
}
},
+ "@sapphire/duration": {
+ "version": "1.0.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/duration/-/duration-1.0.0.tgz",
+ "integrity": "sha512-B+6nKYnBmIlqqbamcR4iBvbQHz6/Kq2JUVM0rA3lQ+aYUYDdcA1Spt66CKtPWwdTYEtSv0VY6Jv27WCtFNYTUg=="
+ },
"@sapphire/framework": {
- "version": "3.1.1",
- "resolved": "https://registry.npmjs.org/@sapphire/framework/-/framework-3.1.1.tgz",
- "integrity": "sha512-dWWIhqFwVZ7nMJ6o7mIhgOAQhSfaue6IPyRSYhXuLEOU9uiQpLioXaYckVAVspRGAc5MqIalOV2htjQF2nCgjw==",
+ "version": "3.1.3",
+ "resolved": "https://registry.npmjs.org/@sapphire/framework/-/framework-3.1.3.tgz",
+ "integrity": "sha512-YHB6oeY095vrRv8ksW0zm/GSWuw+vDLvU0BzJBTGI0KYQfNq2d6OVCjY0ADxFgQSgC9AxOHj2h2GvGcLET+S4g==",
"requires": {
"@discordjs/builders": "^0.16.0",
"@sapphire/discord-utilities": "^2.11.6",
- "@sapphire/discord.js-utilities": "^5.0.0",
- "@sapphire/lexure": "^1.0.2",
- "@sapphire/pieces": "^3.5.1",
- "@sapphire/ratelimits": "^2.4.4",
- "@sapphire/result": "^2.4.1",
- "@sapphire/stopwatch": "^1.4.1",
- "@sapphire/utilities": "^3.9.3",
- "@types/object-hash": "^2.2.1",
- "object-hash": "^3.0.0",
+ "@sapphire/discord.js-utilities": "^5.0.1",
+ "@sapphire/lexure": "^1.1.1",
+ "@sapphire/pieces": "^3.5.2",
+ "@sapphire/ratelimits": "^2.4.5",
+ "@sapphire/result": "^2.5.0",
+ "@sapphire/stopwatch": "^1.5.0",
+ "@sapphire/utilities": "^3.10.0",
"tslib": "^2.4.0"
},
"dependencies": {
@@ -3596,92 +3631,91 @@
}
},
"@sapphire/lexure": {
- "version": "1.0.2",
- "resolved": "https://registry.npmjs.org/@sapphire/lexure/-/lexure-1.0.2.tgz",
- "integrity": "sha512-KKKcCvjkB6AImGzpWdrbLVI++VnRinpus+a4yu+PUT7zUlzUZdma1P/P8XlRDFEx6U+d5jk8ygKyTPzQKvkqRA==",
+ "version": "1.1.2",
+ "resolved": "https://registry.npmjs.org/@sapphire/lexure/-/lexure-1.1.2.tgz",
+ "integrity": "sha512-+v3P3EMDdFoybHH7c7cMcz30jEyxujkxWu5f958cf/Sm27fMM0IqwILnNFUpExZCBAueEM/eoSgbRl4q+K+0jg==",
"requires": {
- "@sapphire/result": "^2.4.1"
+ "@sapphire/result": "^2.6.0"
}
},
"@sapphire/pieces": {
- "version": "3.5.1",
- "resolved": "https://registry.npmjs.org/@sapphire/pieces/-/pieces-3.5.1.tgz",
- "integrity": "sha512-GEm7W6hAMC1yN76z0SZlIij66MDcuvWf7ra2TPGhflmv5ZUG4vNHNMktexP4AwEgKeF1jKJouVrIs3lAC3e4ZQ==",
+ "version": "3.5.2",
+ "resolved": "https://registry.npmjs.org/@sapphire/pieces/-/pieces-3.5.2.tgz",
+ "integrity": "sha512-B8ghwre5naTIMnJIlqJGhKX6ZTpGqz4oAtBd/ihX0CY69cPtbem3VHfZ8Sf5C+50l3mfe2AU7CfZQn9kLQR2fQ==",
"requires": {
- "@discordjs/collection": "^1.0.1",
- "@sapphire/utilities": "^3.9.2",
+ "@discordjs/collection": "^1.1.0",
+ "@sapphire/utilities": "^3.10.0",
"tslib": "^2.4.0"
}
},
"@sapphire/plugin-scheduled-tasks": {
- "version": "4.0.0",
- "resolved": "https://registry.npmjs.org/@sapphire/plugin-scheduled-tasks/-/plugin-scheduled-tasks-4.0.0.tgz",
- "integrity": "sha512-MIYiG40HW9kPeZGPcGlLX3uPkKaruG2GIkUhu5gNS1kJogtx6NdZlY5hKBDnpjl1jND5+d2gX9aaLNFA7+UxKA==",
+ "version": "4.0.1",
+ "resolved": "https://registry.npmjs.org/@sapphire/plugin-scheduled-tasks/-/plugin-scheduled-tasks-4.0.1.tgz",
+ "integrity": "sha512-vLxfHBu2vKaJZ9v2f4z+VDZaPeDqS8bm+Sc2minRwJPw1hWAHiPqmxCBPIONY7eOQ9qKayvhKYTIwwruxgO/Mg==",
"requires": {
- "@sapphire/time-utilities": "^1.7.6",
+ "@sapphire/stopwatch": "^1.4.1",
+ "@sapphire/utilities": "^3.9.3",
"tslib": "^2.4.0"
}
},
"@sapphire/plugin-subcommands": {
- "version": "3.2.1",
- "resolved": "https://registry.npmjs.org/@sapphire/plugin-subcommands/-/plugin-subcommands-3.2.1.tgz",
- "integrity": "sha512-I+NmbewS85oEfFx/0t8cGtimLmNGMzF6k5eigUmRakb7t6m1EK54cvWwV3zFbkhCMWI6e+ObiIe5XJVel8oWqg==",
+ "version": "3.2.3",
+ "resolved": "https://registry.npmjs.org/@sapphire/plugin-subcommands/-/plugin-subcommands-3.2.3.tgz",
+ "integrity": "sha512-xUDkHdOXmqquO++I54ZOZg8Prh2YIJ7sSGBLXCU+FiNDbsfzbxr/McCfnKL65L6RBYOjf8d06up3GKPL8t9GpQ==",
"requires": {
- "@sapphire/utilities": "^3.9.2",
+ "@sapphire/utilities": "^3.11.0",
"tslib": "^2.4.0"
}
},
"@sapphire/ratelimits": {
- "version": "2.4.4",
- "resolved": "https://registry.npmjs.org/@sapphire/ratelimits/-/ratelimits-2.4.4.tgz",
- "integrity": "sha512-9gZ1BaY99HLWOcfuhlu0WklirHhVc6QD1pm5/v2W0O9pBpMHrd1GImVMXjYZRoy1qpmE2ZggSmN1665lktTCMw==",
+ "version": "2.4.5",
+ "resolved": "https://registry.npmjs.org/@sapphire/ratelimits/-/ratelimits-2.4.5.tgz",
+ "integrity": "sha512-2wqpVPRaPUE+CWStLm6wGLj1uA4Ln/9qbH4Ue/eCHC6/R5lJz0+8nGD1LpiYOcyeVLTHbmwODGeD92obkPej2g==",
"requires": {
- "@sapphire/time-utilities": "^1.7.4"
+ "@sapphire/timer-manager": "^1.0.0"
}
},
"@sapphire/result": {
- "version": "2.4.1",
- "resolved": "https://registry.npmjs.org/@sapphire/result/-/result-2.4.1.tgz",
- "integrity": "sha512-RWgp+cCm1dhE/voMGwp3z5xGmsOluXW9EPIXyO+khMXxZDL3iAgp4/ZCSFEw3nI98njwGmgWYIzdQfCu3WA4OA=="
+ "version": "2.6.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/result/-/result-2.6.0.tgz",
+ "integrity": "sha512-gdW6n/oDZ8aC1439Ub3RiLQ6L4VHAxbN0AhGJWNkEZ6Z6Ww2V62fwRiA/73OPfgYQKXk9ljhAFiqNO91KAonHQ=="
},
"@sapphire/shapeshift": {
- "version": "3.6.0",
- "resolved": "https://registry.npmjs.org/@sapphire/shapeshift/-/shapeshift-3.6.0.tgz",
- "integrity": "sha512-tu2WLRdo5wotHRvsCkspg3qMiP6ETC3Q1dns1Q5V6zKUki+1itq6AbhMwohF9ZcLoYqg+Y8LkgRRtVxxTQVTBQ==",
+ "version": "3.7.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/shapeshift/-/shapeshift-3.7.0.tgz",
+ "integrity": "sha512-A6vI1zJoxhjWo4grsxpBRBgk96SqSdjLX5WlzKp9H+bJbkM07mvwcbtbVAmUZHbi/OG3HLfiZ1rlw4BhH6tsBQ==",
"requires": {
"fast-deep-equal": "^3.1.3",
"lodash.uniqwith": "^4.5.0"
}
},
"@sapphire/stopwatch": {
- "version": "1.4.1",
- "resolved": "https://registry.npmjs.org/@sapphire/stopwatch/-/stopwatch-1.4.1.tgz",
- "integrity": "sha512-FoZIM7oQ1kwkjWpl/rKReuDFSlkCDjDp//1Np2mmQD+xQ2Zyo/J2MaYAITprwQr3AUBu/OOUJvqm7f8lA9R7gA==",
+ "version": "1.5.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/stopwatch/-/stopwatch-1.5.0.tgz",
+ "integrity": "sha512-DtyKugdy3JTqm6JnEepTY64fGJAqlusDVrlrzifEgSCfGYCqpvB+SBldkWtDH+z+zLcp+PyaFLq7xpVfkhmvGg==",
"requires": {
- "tslib": "^2.3.1"
+ "tslib": "^2.4.0"
}
},
- "@sapphire/time-utilities": {
- "version": "1.7.6",
- "resolved": "https://registry.npmjs.org/@sapphire/time-utilities/-/time-utilities-1.7.6.tgz",
- "integrity": "sha512-VsMVYFmS9Iu0buPs7gwn1D6vqIC04ezVMBRIo8vRTB2s7UNN/vQReX2cLABFoDVqs7RHQsvr2DPoTWHEDYw9YA==",
- "requires": {
- "@sapphire/utilities": "^3.9.2"
- }
+ "@sapphire/timer-manager": {
+ "version": "1.0.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/timer-manager/-/timer-manager-1.0.0.tgz",
+ "integrity": "sha512-vxxnv75QPMGKt6IB6nL2xRJfwzcUQ9DBGzJLg6G8eS5O4u7j3IR/yr/GQsa4gIpjw6kQOgn8lUdnSTlpnERTbQ=="
},
"@sapphire/ts-config": {
"version": "3.3.4",
"resolved": "https://registry.npmjs.org/@sapphire/ts-config/-/ts-config-3.3.4.tgz",
"integrity": "sha512-mWEUxCXh3cHKI7C8HJ049exVTMNaq+A/lJEDfM5ENSQ/OOZHd5DdmXn2jrYqFWbTRCHa0Vp2FAmACWBwePsBtg==",
+ "dev": true,
"requires": {
"tslib": "^2.3.1",
"typescript": "^4.6.3"
}
},
"@sapphire/utilities": {
- "version": "3.9.3",
- "resolved": "https://registry.npmjs.org/@sapphire/utilities/-/utilities-3.9.3.tgz",
- "integrity": "sha512-7+ZjfbmRHqewmH32jpZfzrEuHpvTttTG7WjDl1GUtc4pkOMr0kYybrZmIEZYsUvF7PWzO0GrmOK2zWs3GuJo7g=="
+ "version": "3.11.0",
+ "resolved": "https://registry.npmjs.org/@sapphire/utilities/-/utilities-3.11.0.tgz",
+ "integrity": "sha512-ich7J+329UTEgWxgk8b871rMhbFW/hvXdabdiKaUKd6g10eIMkIakWf+EGkDQsiDSiebIXll9TIPPmWtN3cVSw=="
},
"@tsconfig/node10": {
"version": "1.0.9",
@@ -3725,9 +3759,9 @@
"dev": true
},
"@types/node": {
- "version": "18.7.16",
- "resolved": "https://registry.npmjs.org/@types/node/-/node-18.7.16.tgz",
- "integrity": "sha512-EQHhixfu+mkqHMZl1R2Ovuvn47PUw18azMJOTwSZr9/fhzHNGXAJ0ma0dayRVchprpCj0Kc1K1xKoWaATWF1qg=="
+ "version": "18.11.3",
+ "resolved": "https://registry.npmjs.org/@types/node/-/node-18.11.3.tgz",
+ "integrity": "sha512-fNjDQzzOsZeKZu5NATgXUPsaFaTxeRgFXoosrHivTl8RGeV733OLawXsGfEk9a8/tySyZUyiZ6E8LcjPFZ2y1A=="
},
"@types/node-fetch": {
"version": "2.6.2",
@@ -3750,10 +3784,11 @@
}
}
},
- "@types/object-hash": {
- "version": "2.2.1",
- "resolved": "https://registry.npmjs.org/@types/object-hash/-/object-hash-2.2.1.tgz",
- "integrity": "sha512-i/rtaJFCsPljrZvP/akBqEwUP2y5cZLOmvO+JaYnz01aPknrQ+hB5MRcO7iqCUsFaYfTG8kGfKUyboA07xeDHQ=="
+ "@types/semver": {
+ "version": "7.3.12",
+ "resolved": "https://registry.npmjs.org/@types/semver/-/semver-7.3.12.tgz",
+ "integrity": "sha512-WwA1MW0++RfXmCr12xeYOOC5baSC9mSb0ZqCquFzKhcoF4TvHu5MKOuXsncgZcpVFhB1pXd5hZmM0ryAoCp12A==",
+ "dev": true
},
"@types/ws": {
"version": "8.5.3",
@@ -3764,16 +3799,15 @@
}
},
"@typescript-eslint/eslint-plugin": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.36.2.tgz",
- "integrity": "sha512-OwwR8LRwSnI98tdc2z7mJYgY60gf7I9ZfGjN5EjCwwns9bdTuQfAXcsjSB2wSQ/TVNYSGKf4kzVXbNGaZvwiXw==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-5.40.1.tgz",
+ "integrity": "sha512-FsWboKkWdytGiXT5O1/R9j37YgcjO8MKHSUmWnIEjVaz0krHkplPnYi7mwdb+5+cs0toFNQb0HIrN7zONdIEWg==",
"dev": true,
"requires": {
- "@typescript-eslint/scope-manager": "5.36.2",
- "@typescript-eslint/type-utils": "5.36.2",
- "@typescript-eslint/utils": "5.36.2",
+ "@typescript-eslint/scope-manager": "5.40.1",
+ "@typescript-eslint/type-utils": "5.40.1",
+ "@typescript-eslint/utils": "5.40.1",
"debug": "^4.3.4",
- "functional-red-black-tree": "^1.0.1",
"ignore": "^5.2.0",
"regexpp": "^3.2.0",
"semver": "^7.3.7",
@@ -3781,53 +3815,53 @@
}
},
"@typescript-eslint/parser": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.36.2.tgz",
- "integrity": "sha512-qS/Kb0yzy8sR0idFspI9Z6+t7mqk/oRjnAYfewG+VN73opAUvmYL3oPIMmgOX6CnQS6gmVIXGshlb5RY/R22pA==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/parser/-/parser-5.40.1.tgz",
+ "integrity": "sha512-IK6x55va5w4YvXd4b3VrXQPldV9vQTxi5ov+g4pMANsXPTXOcfjx08CRR1Dfrcc51syPtXHF5bgLlMHYFrvQtg==",
"dev": true,
"requires": {
- "@typescript-eslint/scope-manager": "5.36.2",
- "@typescript-eslint/types": "5.36.2",
- "@typescript-eslint/typescript-estree": "5.36.2",
+ "@typescript-eslint/scope-manager": "5.40.1",
+ "@typescript-eslint/types": "5.40.1",
+ "@typescript-eslint/typescript-estree": "5.40.1",
"debug": "^4.3.4"
}
},
"@typescript-eslint/scope-manager": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.36.2.tgz",
- "integrity": "sha512-cNNP51L8SkIFSfce8B1NSUBTJTu2Ts4nWeWbFrdaqjmn9yKrAaJUBHkyTZc0cL06OFHpb+JZq5AUHROS398Orw==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/scope-manager/-/scope-manager-5.40.1.tgz",
+ "integrity": "sha512-jkn4xsJiUQucI16OLCXrLRXDZ3afKhOIqXs4R3O+M00hdQLKR58WuyXPZZjhKLFCEP2g+TXdBRtLQ33UfAdRUg==",
"dev": true,
"requires": {
- "@typescript-eslint/types": "5.36.2",
- "@typescript-eslint/visitor-keys": "5.36.2"
+ "@typescript-eslint/types": "5.40.1",
+ "@typescript-eslint/visitor-keys": "5.40.1"
}
},
"@typescript-eslint/type-utils": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.36.2.tgz",
- "integrity": "sha512-rPQtS5rfijUWLouhy6UmyNquKDPhQjKsaKH0WnY6hl/07lasj8gPaH2UD8xWkePn6SC+jW2i9c2DZVDnL+Dokw==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/type-utils/-/type-utils-5.40.1.tgz",
+ "integrity": "sha512-DLAs+AHQOe6n5LRraXiv27IYPhleF0ldEmx6yBqBgBLaNRKTkffhV1RPsjoJBhVup2zHxfaRtan8/YRBgYhU9Q==",
"dev": true,
"requires": {
- "@typescript-eslint/typescript-estree": "5.36.2",
- "@typescript-eslint/utils": "5.36.2",
+ "@typescript-eslint/typescript-estree": "5.40.1",
+ "@typescript-eslint/utils": "5.40.1",
"debug": "^4.3.4",
"tsutils": "^3.21.0"
}
},
"@typescript-eslint/types": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.36.2.tgz",
- "integrity": "sha512-9OJSvvwuF1L5eS2EQgFUbECb99F0mwq501w0H0EkYULkhFa19Qq7WFbycdw1PexAc929asupbZcgjVIe6OK/XQ==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/types/-/types-5.40.1.tgz",
+ "integrity": "sha512-Icg9kiuVJSwdzSQvtdGspOlWNjVDnF3qVIKXdJ103o36yRprdl3Ge5cABQx+csx960nuMF21v8qvO31v9t3OHw==",
"dev": true
},
"@typescript-eslint/typescript-estree": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.36.2.tgz",
- "integrity": "sha512-8fyH+RfbKc0mTspfuEjlfqA4YywcwQK2Amcf6TDOwaRLg7Vwdu4bZzyvBZp4bjt1RRjQ5MDnOZahxMrt2l5v9w==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/typescript-estree/-/typescript-estree-5.40.1.tgz",
+ "integrity": "sha512-5QTP/nW5+60jBcEPfXy/EZL01qrl9GZtbgDZtDPlfW5zj/zjNrdI2B5zMUHmOsfvOr2cWqwVdWjobCiHcedmQA==",
"dev": true,
"requires": {
- "@typescript-eslint/types": "5.36.2",
- "@typescript-eslint/visitor-keys": "5.36.2",
+ "@typescript-eslint/types": "5.40.1",
+ "@typescript-eslint/visitor-keys": "5.40.1",
"debug": "^4.3.4",
"globby": "^11.1.0",
"is-glob": "^4.0.3",
@@ -3836,26 +3870,28 @@
}
},
"@typescript-eslint/utils": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.36.2.tgz",
- "integrity": "sha512-uNcopWonEITX96v9pefk9DC1bWMdkweeSsewJ6GeC7L6j2t0SJywisgkr9wUTtXk90fi2Eljj90HSHm3OGdGRg==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/utils/-/utils-5.40.1.tgz",
+ "integrity": "sha512-a2TAVScoX9fjryNrW6BZRnreDUszxqm9eQ9Esv8n5nXApMW0zeANUYlwh/DED04SC/ifuBvXgZpIK5xeJHQ3aw==",
"dev": true,
"requires": {
"@types/json-schema": "^7.0.9",
- "@typescript-eslint/scope-manager": "5.36.2",
- "@typescript-eslint/types": "5.36.2",
- "@typescript-eslint/typescript-estree": "5.36.2",
+ "@types/semver": "^7.3.12",
+ "@typescript-eslint/scope-manager": "5.40.1",
+ "@typescript-eslint/types": "5.40.1",
+ "@typescript-eslint/typescript-estree": "5.40.1",
"eslint-scope": "^5.1.1",
- "eslint-utils": "^3.0.0"
+ "eslint-utils": "^3.0.0",
+ "semver": "^7.3.7"
}
},
"@typescript-eslint/visitor-keys": {
- "version": "5.36.2",
- "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.36.2.tgz",
- "integrity": "sha512-BtRvSR6dEdrNt7Net2/XDjbYKU5Ml6GqJgVfXT0CxTCJlnIqK7rAGreuWKMT2t8cFUT2Msv5oxw0GMRD7T5J7A==",
+ "version": "5.40.1",
+ "resolved": "https://registry.npmjs.org/@typescript-eslint/visitor-keys/-/visitor-keys-5.40.1.tgz",
+ "integrity": "sha512-A2DGmeZ+FMja0geX5rww+DpvILpwo1OsiQs0M+joPWJYsiEFBLsH0y1oFymPNul6Z5okSmHpP4ivkc2N0Cgfkw==",
"dev": true,
"requires": {
- "@typescript-eslint/types": "5.36.2",
+ "@typescript-eslint/types": "5.40.1",
"eslint-visitor-keys": "^3.3.0"
}
},
@@ -3975,9 +4011,9 @@
}
},
"bullmq": {
- "version": "1.90.1",
- "resolved": "https://registry.npmjs.org/bullmq/-/bullmq-1.90.1.tgz",
- "integrity": "sha512-JY8mNzfnl+lfzFFzLJa6if+4YFvCMuJZDtQ8gvkcedoet+fDPEETF0iZ2fuzxCizuneARCniAiwIR/ESnqbuKw==",
+ "version": "1.91.1",
+ "resolved": "https://registry.npmjs.org/bullmq/-/bullmq-1.91.1.tgz",
+ "integrity": "sha512-u7dat9I8ZwouZ651AMZkBSvB6NVUPpnAjd4iokd9DM41whqIBnDjuL11h7+kEjcpiDKj6E+wxZiER00FqirZQg==",
"requires": {
"cron-parser": "^4.6.0",
"get-port": "6.1.2",
@@ -3987,7 +4023,7 @@
"msgpackr": "^1.6.2",
"semver": "^7.3.7",
"tslib": "^2.0.0",
- "uuid": "^8.3.2"
+ "uuid": "^9.0.0"
}
},
"call-bind": {
@@ -4017,9 +4053,9 @@
}
},
"cluster-key-slot": {
- "version": "1.1.0",
- "resolved": "https://registry.npmjs.org/cluster-key-slot/-/cluster-key-slot-1.1.0.tgz",
- "integrity": "sha512-2Nii8p3RwAPiFwsnZvukotvow2rIHM+yQ6ZcBXGHdniadkYGZYiGmkHJIbZPIV9nfv7m/U1IPMVVcAhoWFeklw=="
+ "version": "1.1.1",
+ "resolved": "https://registry.npmjs.org/cluster-key-slot/-/cluster-key-slot-1.1.1.tgz",
+ "integrity": "sha512-rwHwUfXL40Chm1r08yrhU3qpUvdVlgkKNeyeGPOxnW8/SyVDvgRaed/Uz54AqWNaTCAThlj6QAs3TZcKI0xDEw=="
},
"color-convert": {
"version": "2.0.1",
@@ -4134,19 +4170,19 @@
"integrity": "sha512-dvO5M52v7m7Dy96+XUnzXNsQ/0npsYpU6dL205kAtEDueswoz3aU3bh1UMoK4cQmcGtB1YRyLKqp+DXi05lzFg=="
},
"discord.js": {
- "version": "13.10.3",
- "resolved": "https://registry.npmjs.org/discord.js/-/discord.js-13.10.3.tgz",
- "integrity": "sha512-cIARuxfpQDeqA9Zw3fz4IL20xAhtMsjwJIf7/K82R3n2xROG9/fAx+7qjX8ysp9BfflYqMu2ZskyWq1EAmL5BA==",
+ "version": "13.12.0",
+ "resolved": "https://registry.npmjs.org/discord.js/-/discord.js-13.12.0.tgz",
+ "integrity": "sha512-K5qhREsYcTHkEqt7+7LcSoXTeQYZpI+SQRs9ei/FhbhUpirmjqFtN99P8W2mrKUyhhy7WXWm7rnna0AooKtIpw==",
"requires": {
"@discordjs/builders": "^0.16.0",
"@discordjs/collection": "^0.7.0",
"@sapphire/async-queue": "^1.5.0",
"@types/node-fetch": "^2.6.2",
"@types/ws": "^8.5.3",
- "discord-api-types": "^0.33.3",
+ "discord-api-types": "^0.33.5",
"form-data": "^4.0.0",
"node-fetch": "^2.6.7",
- "ws": "^8.8.1"
+ "ws": "^8.9.0"
},
"dependencies": {
"@discordjs/builders": {
@@ -4185,27 +4221,27 @@
}
},
"dotenv": {
- "version": "16.0.2",
- "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.0.2.tgz",
- "integrity": "sha512-JvpYKUmzQhYoIFgK2MOnF3bciIZoItIIoryihy0rIA+H4Jy0FmgyKYAHCTN98P5ybGSJcIFbh6QKeJdtZd1qhA=="
+ "version": "16.0.3",
+ "resolved": "https://registry.npmjs.org/dotenv/-/dotenv-16.0.3.tgz",
+ "integrity": "sha512-7GO6HghkA5fYG9TYnNxi14/7K9f5occMlp3zXAuSxn7CKCxt9xbNWG7yF8hTCSUchlfWSe3uLmlPfigevRItzQ=="
},
"es-abstract": {
- "version": "1.20.2",
- "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.20.2.tgz",
- "integrity": "sha512-XxXQuVNrySBNlEkTYJoDNFe5+s2yIOpzq80sUHEdPdQr0S5nTLz4ZPPPswNIpKseDDUS5yghX1gfLIHQZ1iNuQ==",
+ "version": "1.20.4",
+ "resolved": "https://registry.npmjs.org/es-abstract/-/es-abstract-1.20.4.tgz",
+ "integrity": "sha512-0UtvRN79eMe2L+UNEF1BwRe364sj/DXhQ/k5FmivgoSdpM90b8Jc0mDzKMGo7QS0BVbOP/bTwBKNnDc9rNzaPA==",
"dev": true,
"requires": {
"call-bind": "^1.0.2",
"es-to-primitive": "^1.2.1",
"function-bind": "^1.1.1",
"function.prototype.name": "^1.1.5",
- "get-intrinsic": "^1.1.2",
+ "get-intrinsic": "^1.1.3",
"get-symbol-description": "^1.0.0",
"has": "^1.0.3",
"has-property-descriptors": "^1.0.0",
"has-symbols": "^1.0.3",
"internal-slot": "^1.0.3",
- "is-callable": "^1.2.4",
+ "is-callable": "^1.2.7",
"is-negative-zero": "^2.0.2",
"is-regex": "^1.1.4",
"is-shared-array-buffer": "^1.0.2",
@@ -4215,6 +4251,7 @@
"object-keys": "^1.1.1",
"object.assign": "^4.1.4",
"regexp.prototype.flags": "^1.4.3",
+ "safe-regex-test": "^1.0.0",
"string.prototype.trimend": "^1.0.5",
"string.prototype.trimstart": "^1.0.5",
"unbox-primitive": "^1.0.2"
@@ -4247,14 +4284,14 @@
"dev": true
},
"eslint": {
- "version": "8.22.0",
- "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.22.0.tgz",
- "integrity": "sha512-ci4t0sz6vSRKdmkOGmprBo6fmI4PrphDFMy5JEq/fNS0gQkJM3rLmrqcp8ipMcdobH3KtUP40KniAE9W19S4wA==",
+ "version": "8.25.0",
+ "resolved": "https://registry.npmjs.org/eslint/-/eslint-8.25.0.tgz",
+ "integrity": "sha512-DVlJOZ4Pn50zcKW5bYH7GQK/9MsoQG2d5eDH0ebEkE8PbgzTTmtt/VTH9GGJ4BfeZCpBLqFfvsjX35UacUL83A==",
"dev": true,
"requires": {
- "@eslint/eslintrc": "^1.3.0",
- "@humanwhocodes/config-array": "^0.10.4",
- "@humanwhocodes/gitignore-to-minimatch": "^1.0.2",
+ "@eslint/eslintrc": "^1.3.3",
+ "@humanwhocodes/config-array": "^0.10.5",
+ "@humanwhocodes/module-importer": "^1.0.1",
"ajv": "^6.10.0",
"chalk": "^4.0.0",
"cross-spawn": "^7.0.2",
@@ -4264,13 +4301,12 @@
"eslint-scope": "^7.1.1",
"eslint-utils": "^3.0.0",
"eslint-visitor-keys": "^3.3.0",
- "espree": "^9.3.3",
+ "espree": "^9.4.0",
"esquery": "^1.4.0",
"esutils": "^2.0.2",
"fast-deep-equal": "^3.1.3",
"file-entry-cache": "^6.0.1",
"find-up": "^5.0.0",
- "functional-red-black-tree": "^1.0.1",
"glob-parent": "^6.0.1",
"globals": "^13.15.0",
"globby": "^11.1.0",
@@ -4279,6 +4315,7 @@
"import-fresh": "^3.0.0",
"imurmurhash": "^0.1.4",
"is-glob": "^4.0.0",
+ "js-sdsl": "^4.1.4",
"js-yaml": "^4.1.0",
"json-stable-stringify-without-jsonify": "^1.0.1",
"levn": "^0.4.1",
@@ -4289,8 +4326,7 @@
"regexpp": "^3.2.0",
"strip-ansi": "^6.0.1",
"strip-json-comments": "^3.1.0",
- "text-table": "^0.2.0",
- "v8-compile-cache": "^2.0.3"
+ "text-table": "^0.2.0"
},
"dependencies": {
"eslint-scope": {
@@ -4524,9 +4560,9 @@
"integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q=="
},
"fast-glob": {
- "version": "3.2.11",
- "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.11.tgz",
- "integrity": "sha512-xrO3+1bxSo3ZVHAnqzyuewYT6aMFHRAd4Kcs92MAonjwQZLsK9d0SF1IyQ3k5PoirxTW0Oe/RqFgMQ6TcNE5Ew==",
+ "version": "3.2.12",
+ "resolved": "https://registry.npmjs.org/fast-glob/-/fast-glob-3.2.12.tgz",
+ "integrity": "sha512-DVj4CQIYYow0BlaelwK1pHl5n5cRSJfM60UA0zK891sVInoPri2Ekj7+e1CT3/3qxXenpI+nBBmQAcJPJgaj4w==",
"dev": true,
"requires": {
"@nodelib/fs.stat": "^2.0.2",
@@ -4645,12 +4681,6 @@
"functions-have-names": "^1.2.2"
}
},
- "functional-red-black-tree": {
- "version": "1.0.1",
- "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz",
- "integrity": "sha512-dsKNQNdj6xA3T+QlADDA7mOSlX0qiMINjn0cgr+eGHGsbSHzTabcIogz2+p/iqP1Xs6EP/sS2SbqH+brGTbq0g==",
- "dev": true
- },
"functions-have-names": {
"version": "1.2.3",
"resolved": "https://registry.npmjs.org/functions-have-names/-/functions-have-names-1.2.3.tgz",
@@ -4658,9 +4688,9 @@
"dev": true
},
"get-intrinsic": {
- "version": "1.1.2",
- "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.1.2.tgz",
- "integrity": "sha512-Jfm3OyCxHh9DJyc28qGk+JmfkpO41A4XkneDSujN9MDXrm4oDKdHvndhZ2dN94+ERNfkYJWDclW6k2L/ZGHjXA==",
+ "version": "1.1.3",
+ "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.1.3.tgz",
+ "integrity": "sha512-QJVz1Tj7MS099PevUG5jvnt9tSkXN8K14dxQlikJuPt4uD9hHAHjLyLBiLR5zELelBdD9QNRAXZzsJx0WaDL9A==",
"dev": true,
"requires": {
"function-bind": "^1.1.1",
@@ -4879,15 +4909,15 @@
}
},
"is-callable": {
- "version": "1.2.4",
- "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.4.tgz",
- "integrity": "sha512-nsuwtxZfMX67Oryl9LCQ+upnC0Z0BgpwntpS89m1H/TLF0zNfzfLMV/9Wa/6MZsj0acpEjAO0KF1xT6ZdLl95w==",
+ "version": "1.2.7",
+ "resolved": "https://registry.npmjs.org/is-callable/-/is-callable-1.2.7.tgz",
+ "integrity": "sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==",
"dev": true
},
"is-core-module": {
- "version": "2.10.0",
- "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.10.0.tgz",
- "integrity": "sha512-Erxj2n/LDAZ7H8WNJXd9tw38GYM3dv8rk8Zcs+jJuxYTW7sozH+SS8NtrSjVL1/vpLvWi1hxy96IzjJ3EHTJJg==",
+ "version": "2.11.0",
+ "resolved": "https://registry.npmjs.org/is-core-module/-/is-core-module-2.11.0.tgz",
+ "integrity": "sha512-RRjxlvLDkD1YJwDbroBHMb+cukurkDWNyHx7D3oNB5x9rb5ogcksMC5wHCadcXoo67gVr/+3GFySh3134zi6rw==",
"dev": true,
"requires": {
"has": "^1.0.3"
@@ -4990,6 +5020,12 @@
"integrity": "sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==",
"dev": true
},
+ "js-sdsl": {
+ "version": "4.1.5",
+ "resolved": "https://registry.npmjs.org/js-sdsl/-/js-sdsl-4.1.5.tgz",
+ "integrity": "sha512-08bOAKweV2NUC1wqTtf3qZlnpOX/R2DU9ikpjOHs0H+ibQv3zpncVQg6um4uYtRtrwIX8M4Nh3ytK4HGlYAq7Q==",
+ "dev": true
+ },
"js-yaml": {
"version": "4.1.0",
"resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-4.1.0.tgz",
@@ -5074,9 +5110,9 @@
}
},
"luxon": {
- "version": "3.0.3",
- "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.0.3.tgz",
- "integrity": "sha512-+EfHWnF+UT7GgTnq5zXg3ldnTKL2zdv7QJgsU5bjjpbH17E3qi/puMhQyJVYuCq+FRkogvB5WB6iVvUr+E4a7w=="
+ "version": "3.0.4",
+ "resolved": "https://registry.npmjs.org/luxon/-/luxon-3.0.4.tgz",
+ "integrity": "sha512-aV48rGUwP/Vydn8HT+5cdr26YYQiUZ42NM6ToMoaGKwYfWbfLeRkEu1wXWMHBZT6+KyLfcbbtVcoQFCbbPjKlw=="
},
"make-error": {
"version": "1.3.6",
@@ -5122,9 +5158,9 @@
}
},
"minimist": {
- "version": "1.2.6",
- "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.6.tgz",
- "integrity": "sha512-Jsjnk4bw3YJqYzbdyBiNsPWHPfO++UGG749Cxs6peCu5Xg4nrena6OVxOYxrQTqww0Jmwt+Ref8rggumkTLz9Q==",
+ "version": "1.2.7",
+ "resolved": "https://registry.npmjs.org/minimist/-/minimist-1.2.7.tgz",
+ "integrity": "sha512-bzfL1YUZsP41gmu/qjrEk0Q6i2ix/cVeAhbCbqH9u3zYutS1cLg00qhrD0M2MVdCcx4Sc0UpP2eBWo9rotpq6g==",
"dev": true
},
"ms": {
@@ -5133,11 +5169,11 @@
"integrity": "sha512-sGkPx+VjMtmA6MX27oA4FBFELFCZZ4S4XqeGOXCv68tT+jb3vk/RyaKWP0PTKyWtmLSM0b+adUTEvbs1PEaH2w=="
},
"msgpackr": {
- "version": "1.6.2",
- "resolved": "https://registry.npmjs.org/msgpackr/-/msgpackr-1.6.2.tgz",
- "integrity": "sha512-bqSQ0DYJbXbrJcrZFmMygUZmqQiDfI2ewFVWcrZY12w5XHWtPuW4WppDT/e63Uu311ajwkRRXSoF0uILroBeTA==",
+ "version": "1.7.2",
+ "resolved": "https://registry.npmjs.org/msgpackr/-/msgpackr-1.7.2.tgz",
+ "integrity": "sha512-mWScyHTtG6TjivXX9vfIy2nBtRupaiAj0HQ2mtmpmYujAmqZmaaEVPaSZ1NKLMvicaMLFzEaMk0ManxMRg8rMQ==",
"requires": {
- "msgpackr-extract": "^2.0.2"
+ "msgpackr-extract": "^2.1.2"
}
},
"msgpackr-extract": {
@@ -5175,11 +5211,6 @@
"integrity": "sha512-k75jcVzk5wnnc/FMxsf4udAoTEUv2jY3ycfdSd3yWu6Cnd1oee6/CfZJApyscA4FJOmdoixWwiwOyf16RzD5JA==",
"optional": true
},
- "object-hash": {
- "version": "3.0.0",
- "resolved": "https://registry.npmjs.org/object-hash/-/object-hash-3.0.0.tgz",
- "integrity": "sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw=="
- },
"object-inspect": {
"version": "1.12.2",
"resolved": "https://registry.npmjs.org/object-inspect/-/object-inspect-1.12.2.tgz",
@@ -5318,11 +5349,12 @@
"dev": true
},
"prisma": {
- "version": "4.3.1",
- "resolved": "https://registry.npmjs.org/prisma/-/prisma-4.3.1.tgz",
- "integrity": "sha512-90xo06wtqil76Xsi3mNpc4Js3SdDRR5g4qb9h+4VWY4Y8iImJY6xc3PX+C9xxTSt1lr0Q89A0MLkJjd8ax6KiQ==",
+ "version": "4.5.0",
+ "resolved": "https://registry.npmjs.org/prisma/-/prisma-4.5.0.tgz",
+ "integrity": "sha512-9Aeg4qiKlv9Wsjz4NO8k2CzRzlvS3A4FYVJ5+28sBBZ0eEwbiVOE/Jj7v6rZC1tFW2s4GSICQOAyuOjc6WsNew==",
+ "devOptional": true,
"requires": {
- "@prisma/engines": "4.3.1"
+ "@prisma/engines": "4.5.0"
}
},
"punycode": {
@@ -5424,10 +5456,21 @@
"queue-microtask": "^1.2.2"
}
},
+ "safe-regex-test": {
+ "version": "1.0.0",
+ "resolved": "https://registry.npmjs.org/safe-regex-test/-/safe-regex-test-1.0.0.tgz",
+ "integrity": "sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA==",
+ "dev": true,
+ "requires": {
+ "call-bind": "^1.0.2",
+ "get-intrinsic": "^1.1.3",
+ "is-regex": "^1.1.4"
+ }
+ },
"semver": {
- "version": "7.3.7",
- "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.7.tgz",
- "integrity": "sha512-QlYTucUYOews+WeEujDoEGziz4K6c47V/Bd+LjSSYcA94p+DmINdf7ncaUinThfvZyu13lN9OY1XDxt8C0Tw0g==",
+ "version": "7.3.8",
+ "resolved": "https://registry.npmjs.org/semver/-/semver-7.3.8.tgz",
+ "integrity": "sha512-NB1ctGL5rlHrPJtFDVIVzTyQylMLu9N9VICA6HSFJo8MCGVTMW6gfpicwKmmK/dAjTOrqu5l63JJOpDSrAis3A==",
"requires": {
"lru-cache": "^6.0.0"
}
@@ -5622,9 +5665,9 @@
"dev": true
},
"typescript": {
- "version": "4.8.3",
- "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.8.3.tgz",
- "integrity": "sha512-goMHfm00nWPa8UvR/CPSvykqf6dVV8x/dp0c5mFTMTIu0u0FlGWRioyy7Nn0PGAdHxpJZnuO/ut+PpQ8UiHAig=="
+ "version": "4.8.4",
+ "resolved": "https://registry.npmjs.org/typescript/-/typescript-4.8.4.tgz",
+ "integrity": "sha512-QCh+85mCy+h0IGff8r5XWzOVSbBO+KfeYrMQh7NJ58QujwcE22u+NUSmUxqF+un70P9GXKxa2HCNiTTMJknyjQ=="
},
"unbox-primitive": {
"version": "1.0.2",
@@ -5648,15 +5691,9 @@
}
},
"uuid": {
- "version": "8.3.2",
- "resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz",
- "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg=="
- },
- "v8-compile-cache": {
- "version": "2.3.0",
- "resolved": "https://registry.npmjs.org/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz",
- "integrity": "sha512-l8lCEmLcLYZh4nbunNZvQCJc5pv7+RCwa8q/LdUx8u7lsWvPDKmpodJAJNwkAhJC//dFY48KuIEmjtd4RViDrA==",
- "dev": true
+ "version": "9.0.0",
+ "resolved": "https://registry.npmjs.org/uuid/-/uuid-9.0.0.tgz",
+ "integrity": "sha512-MXcSTerfPa4uqyzStbRoTgt5XIe3x5+42+q1sDuy3R5MDk66URdLMOZe5aPX/SQd+kuYAh0FdP/pO28IkQyTeg=="
},
"v8-compile-cache-lib": {
"version": "3.0.1",
@@ -5711,9 +5748,9 @@
"integrity": "sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ=="
},
"ws": {
- "version": "8.8.1",
- "resolved": "https://registry.npmjs.org/ws/-/ws-8.8.1.tgz",
- "integrity": "sha512-bGy2JzvzkPowEJV++hF07hAD6niYSr0JzBNo/J29WsB57A2r7Wlc1UFcTR9IzrPvuNVO4B8LGqF8qcpsVOhJCA==",
+ "version": "8.9.0",
+ "resolved": "https://registry.npmjs.org/ws/-/ws-8.9.0.tgz",
+ "integrity": "sha512-Ja7nszREasGaYUYCI2k4lCKIRTt+y7XuqVoHR44YpI49TtryyqbqvDMn5eqfW7e6HzTukDRIsXqzVHScqRcafg==",
"requires": {}
},
"yallist": {
diff --git a/package.json b/package.json
index 66ccf9b..df446a7 100644
--- a/package.json
+++ b/package.json
@@ -26,31 +26,31 @@
},
"homepage": "https://github.com/veganhacktivists/arabot#readme",
"dependencies": {
- "@discordjs/builders": "^1.2.0",
+ "@discordjs/builders": "^1.3.0",
"@prisma/client": "^4.0.0",
"@sapphire/discord.js-utilities": "^5.0.0",
- "@sapphire/framework": "^3.1.1",
+ "@sapphire/framework": "^3.1.3",
"@sapphire/plugin-scheduled-tasks": "^4.0.0",
"@sapphire/plugin-subcommands": "^3.0.0",
"@sapphire/stopwatch": "^1.4.1",
- "@sapphire/ts-config": "^3.3.4",
"@sapphire/utilities": "^3.9.2",
"@types/node": "^18.0.3",
"bullmq": "^1.89.1",
"discord-api-types": "^0.33.3",
- "discord.js": "^13.10.3",
+ "discord.js": "^13.12.0",
"dotenv": "^16.0.1",
- "prisma": "^4.2.1",
"ts-node": "^10.8.2",
"typescript": "^4.7.4"
},
"devDependencies": {
+ "@sapphire/ts-config": "^3.3.4",
"@types/ioredis": "^4.28.10",
"@typescript-eslint/eslint-plugin": "^5.30.7",
"@typescript-eslint/parser": "^5.30.7",
"eslint": "8.22.0",
"eslint-config-airbnb-base": "^15.0.0",
"eslint-config-airbnb-typescript": "^17.0.0",
- "eslint-plugin-import": "^2.26.0"
+ "eslint-plugin-import": "^2.26.0",
+ "prisma": "^4.4.0"
}
}
diff --git a/prisma/migrations/20220806153942_/migration.sql b/prisma/migrations/20220806153942_/migration.sql
new file mode 100644
index 0000000..066741c
--- /dev/null
+++ b/prisma/migrations/20220806153942_/migration.sql
@@ -0,0 +1,14 @@
+/*
+ Warnings:
+
+ - You are about to drop the column `balance` on the `User` table. All the data in the column will be lost.
+ - You are about to drop the column `lastDaily` on the `User` table. All the data in the column will be lost.
+ - You are about to drop the column `level` on the `User` table. All the data in the column will be lost.
+ - You are about to drop the column `xp` on the `User` table. All the data in the column will be lost.
+
+*/
+-- AlterTable
+ALTER TABLE "User" DROP COLUMN "balance",
+DROP COLUMN "lastDaily",
+DROP COLUMN "level",
+DROP COLUMN "xp";
diff --git a/prisma/migrations/20220806162141_verification_channel/migration.sql b/prisma/migrations/20220806162141_verification_channel/migration.sql
new file mode 100644
index 0000000..3c49694
--- /dev/null
+++ b/prisma/migrations/20220806162141_verification_channel/migration.sql
@@ -0,0 +1,8 @@
+/*
+ Warnings:
+
+ - Added the required column `channelId` to the `VerifyUnblock` table without a default value. This is not possible if the table is not empty.
+
+*/
+-- AlterTable
+ALTER TABLE "Verify" ADD COLUMN "channelId" TEXT NOT NULL;
diff --git a/prisma/migrations/20220806193317_verification_time/migration.sql b/prisma/migrations/20220806193317_verification_time/migration.sql
new file mode 100644
index 0000000..6ea66f1
--- /dev/null
+++ b/prisma/migrations/20220806193317_verification_time/migration.sql
@@ -0,0 +1,10 @@
+/*
+ Warnings:
+
+ - You are about to drop the column `time` on the `VerifyUnblock` table. All the data in the column will be lost.
+
+*/
+-- AlterTable
+ALTER TABLE "Verify" DROP COLUMN "time",
+ADD COLUMN "finishTime" TIMESTAMP(3),
+ADD COLUMN "startTime" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP;
diff --git a/prisma/migrations/20220806194157_verification_time/migration.sql b/prisma/migrations/20220806194157_verification_time/migration.sql
new file mode 100644
index 0000000..576590b
--- /dev/null
+++ b/prisma/migrations/20220806194157_verification_time/migration.sql
@@ -0,0 +1,3 @@
+-- AlterTable
+ALTER TABLE "Verify" ADD COLUMN "joinTime" TIMESTAMP(3) NOT NULL DEFAULT CURRENT_TIMESTAMP,
+ALTER COLUMN "startTime" DROP NOT NULL;
diff --git a/prisma/migrations/20220806202004_change_id/migration.sql b/prisma/migrations/20220806202004_change_id/migration.sql
new file mode 100644
index 0000000..d4fec5f
--- /dev/null
+++ b/prisma/migrations/20220806202004_change_id/migration.sql
@@ -0,0 +1,14 @@
+/*
+ Warnings:
+
+ - The primary key for the `VerifyUnblock` table will be changed. If it partially fails, the table could be left without primary key constraint.
+ - You are about to drop the column `channelId` on the `VerifyUnblock` table. All the data in the column will be lost.
+
+*/
+-- AlterTable
+ALTER TABLE "Verify" DROP CONSTRAINT "Verify_pkey",
+DROP COLUMN "channelId",
+ALTER COLUMN "id" DROP DEFAULT,
+ALTER COLUMN "id" SET DATA TYPE TEXT,
+ADD CONSTRAINT "Verify_pkey" PRIMARY KEY ("id");
+DROP SEQUENCE "Verify_id_seq";
diff --git a/prisma/migrations/20220806203429_verify_date/migration.sql b/prisma/migrations/20220806203429_verify_date/migration.sql
new file mode 100644
index 0000000..4c82c7e
--- /dev/null
+++ b/prisma/migrations/20220806203429_verify_date/migration.sql
@@ -0,0 +1,2 @@
+-- AlterTable
+ALTER TABLE "Verify" ALTER COLUMN "startTime" DROP DEFAULT;
diff --git a/prisma/migrations/20220826220735_verification_info/migration.sql b/prisma/migrations/20220826220735_verification_info/migration.sql
new file mode 100644
index 0000000..d613c76
--- /dev/null
+++ b/prisma/migrations/20220826220735_verification_info/migration.sql
@@ -0,0 +1,10 @@
+-- AlterTable
+ALTER TABLE "Verify" ADD COLUMN "activist" BOOLEAN NOT NULL DEFAULT false,
+ADD COLUMN "food" INTEGER,
+ADD COLUMN "length" INTEGER,
+ADD COLUMN "life" INTEGER,
+ADD COLUMN "reason" INTEGER,
+ADD COLUMN "reasoning" INTEGER,
+ADD COLUMN "trusted" BOOLEAN NOT NULL DEFAULT false,
+ADD COLUMN "vegCurious" BOOLEAN NOT NULL DEFAULT false,
+ADD COLUMN "where" INTEGER;
diff --git a/prisma/migrations/20220826221107_add_ver_convinced/migration.sql b/prisma/migrations/20220826221107_add_ver_convinced/migration.sql
new file mode 100644
index 0000000..4ae2e1c
--- /dev/null
+++ b/prisma/migrations/20220826221107_add_ver_convinced/migration.sql
@@ -0,0 +1,2 @@
+-- AlterTable
+ALTER TABLE "Verify" ADD COLUMN "convinced" BOOLEAN NOT NULL DEFAULT false;
diff --git a/prisma/schema.prisma b/prisma/schema.prisma
index 796dbdd..3e4f17f 100644
--- a/prisma/schema.prisma
+++ b/prisma/schema.prisma
@@ -27,10 +27,6 @@ datasource db {
model User {
id String @id @db.VarChar(255)
- level Int @default(0)
- xp Int @default(0)
- balance Int @default(0)
- lastDaily DateTime?
vegan Boolean @default(false)
trusted Boolean @default(false)
activist Boolean @default(false)
@@ -52,16 +48,31 @@ model User {
}
model Verify {
- id Int @id @default(autoincrement())
- user User @relation("verUser", fields: [userId], references: [id])
+ id String @id
+ user User @relation("verUser", fields: [userId], references: [id])
userId String
- verifier User? @relation("verVerifier", fields: [verifierId], references: [id])
+ verifier User? @relation("verVerifier", fields: [verifierId], references: [id])
verifierId String?
- time DateTime @default(now())
- timedOut Boolean @default(false) // If they got kicked out of verification because they timed out
- vegan Boolean @default(false) // If they got verified as a vegan
- text Boolean @default(false) // If they used text verification
- serverVegan Boolean @default(false) // People that went vegan on the server
+ joinTime DateTime @default(now())
+ startTime DateTime?
+ finishTime DateTime?
+ timedOut Boolean @default(false) // If they got kicked out of verification because they timed out
+ //complete Boolean @default(false) // If the verification was incomplete
+ // Roles they got from verification
+ vegan Boolean @default(false) // If they got verified as a vegan
+ activist Boolean @default(false) // If they got the activist role when they verified
+ trusted Boolean @default(false) // If they got the trusted role when they verified
+ vegCurious Boolean @default(false) // If they got the Veg Curious role
+ convinced Boolean @default(false)
+ text Boolean @default(false) // If they used text verification
+ serverVegan Boolean @default(false) // People that went vegan on the server
+ // Stats on verification
+ reason Int?
+ where Int?
+ length Int?
+ reasoning Int?
+ life Int?
+ food Int?
notes String?
}
diff --git a/src/commands/mod/sus.ts b/src/commands/mod/sus.ts
index 098420b..d635970 100644
--- a/src/commands/mod/sus.ts
+++ b/src/commands/mod/sus.ts
@@ -21,113 +21,19 @@ import { Command, RegisterBehavior, Args } from '@sapphire/framework';
import {
MessageEmbed, MessageActionRow, MessageButton, Constants, ButtonInteraction,
} from 'discord.js';
-import type { Message, GuildMember } from 'discord.js';
-import { PrismaClient } from '@prisma/client';
import { isMessageInstance } from '@sapphire/discord.js-utilities';
-import { addExistingUser, userExists } from '../../utils/dbExistingUser';
+import { addExistingUser, userExists } from '../../utils/database/dbExistingUser';
+import {
+ addToDatabase,
+ findNotes,
+ getNote,
+ deactivateNote,
+ deactivateAllNotes,
+} from '../../utils/database/sus';
import IDs from '../../utils/ids';
// TODO add a check when they join the server to give the user the sus role again
-async function addToDatabase(userId: string, modId: string, message: string) {
- // Initialise the database connection
- const prisma = new PrismaClient();
-
- // Add the user to the database
- await prisma.sus.create({
- data: {
- user: {
- connect: {
- id: userId,
- },
- },
- mod: {
- connect: {
- id: modId,
- },
- },
- note: message,
- },
- });
-
- // Close the database connection
- await prisma.$disconnect();
-}
-
-// Get a list of sus notes from the user
-async function findNotes(userId: string, active: boolean) {
- // Initialise the database connection
- const prisma = new PrismaClient();
-
- // Query to get the specific user's sus notes
- const note = await prisma.sus.findMany({
- where: {
- userId,
- active,
- },
- });
-
- // Close the database connection
- await prisma.$disconnect();
- return note;
-}
-
-// Get one note from the id
-async function getNote(noteId: number) {
- // Initialise the database connection
- const prisma = new PrismaClient();
-
- // Query to get the specific user's sus notes
- const note = await prisma.sus.findUnique({
- where: {
- id: noteId,
- },
- });
-
- // Close the database connection
- await prisma.$disconnect();
- return note;
-}
-
-async function deactivateNote(noteId: number) {
- // Initialise the database connection
- const prisma = new PrismaClient();
-
- // Query to deactivate the specific sus note
- await prisma.sus.update({
- where: {
- id: noteId,
- },
- data: {
- active: false,
- },
- });
-
- // Close the database connection
- await prisma.$disconnect();
-}
-
-async function deactivateAllNotes(userId: string) {
- // Initialise the database connection
- const prisma = new PrismaClient();
-
- // Query to deactivate the specific user's sus notes
- await prisma.sus.updateMany({
- where: {
- userId: {
- contains: userId,
- },
- },
- data: {
- active: false,
- },
- });
-
- // Close the database connection
- await prisma.$disconnect();
-}
-
-// Main command
class SusCommand extends Command {
public constructor(context: Command.Context) {
super(context, {
diff --git a/src/listeners/verification/joinServer.ts b/src/listeners/verification/joinServer.ts
new file mode 100644
index 0000000..a305481
--- /dev/null
+++ b/src/listeners/verification/joinServer.ts
@@ -0,0 +1,50 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+import { Listener } from '@sapphire/framework';
+import type { GuildMember } from 'discord.js';
+import { fetchRoles } from '../../utils/database/dbExistingUser';
+import IDs from '../../utils/ids';
+import { blockTime } from '../../utils/database/verification';
+
+class VerificationReady extends Listener {
+ public constructor(context: Listener.Context, options: Listener.Options) {
+ super(context, {
+ ...options,
+ once: true,
+ event: 'guildMemberAdd',
+ });
+ }
+
+ public async run(user: GuildMember) {
+ // Add basic roles
+ const roles = await fetchRoles(user.id);
+
+ // Check if the user has a verification block
+ const timeout = await blockTime(user.id);
+ if (timeout > 0) {
+ roles.push(IDs.roles.verifyBlock);
+ }
+
+ // Add roles if they don't have verification block
+ await user.roles.add(roles);
+ }
+}
+
+export default VerificationReady;
diff --git a/src/listeners/verification/joinVC.ts b/src/listeners/verification/joinVC.ts
new file mode 100644
index 0000000..8dfd570
--- /dev/null
+++ b/src/listeners/verification/joinVC.ts
@@ -0,0 +1,720 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+import { container, Listener } from '@sapphire/framework';
+import type {
+ CategoryChannel,
+ ColorResolvable,
+ TextChannel,
+ VoiceChannel,
+ VoiceState,
+ GuildMember,
+ Guild,
+ User,
+} from 'discord.js';
+import {
+ ButtonInteraction,
+ Constants,
+ MessageActionRow,
+ MessageButton,
+ MessageEmbed,
+} from 'discord.js';
+import { time } from '@discordjs/builders';
+import { maxVCs, questionInfo, serverFind } from '../../utils/verificationConfig';
+import { joinVerification, startVerification, finishVerification } from '../../utils/database/verification';
+import { findNotes } from '../../utils/database/sus';
+import { userExists, addExistingUser } from '../../utils/database/dbExistingUser';
+import { rolesToString } from '../../utils/formatter';
+import IDs from '../../utils/ids';
+
+class VerificationJoinVCListener extends Listener {
+ public constructor(context: Listener.Context, options: Listener.Options) {
+ super(context, {
+ ...options,
+ event: 'voiceStateUpdate',
+ });
+ }
+
+ public async run(oldState: VoiceState, newState: VoiceState) {
+ // If the event was not a user joining the channel
+ if (oldState.channel?.parent?.id === IDs.categories.verification
+ || newState.channel?.parent?.id !== IDs.categories.verification
+ ) {
+ return;
+ }
+
+ // Variable if this channel is a Verifiers only VC
+ let verifier = false;
+
+ // Checks for not null
+ const { channel } = newState;
+ const { member } = newState;
+ const { client } = container;
+ const guild = client.guilds.cache.get(newState.guild.id);
+
+ if (channel === null || member === null || guild === undefined) {
+ console.error('Verification channel not found');
+ return;
+ }
+
+ // Get current category and channel
+ const categoryGuild = guild.channels.cache.get(IDs.categories.verification);
+ const currentChannelGuild = guild.channels.cache.get(channel.id);
+ if (currentChannelGuild === undefined || categoryGuild === undefined) {
+ console.error('Verification channel not found');
+ return;
+ }
+ const currentChannel = currentChannelGuild as VoiceChannel;
+ const category = categoryGuild as CategoryChannel;
+
+ const roles = rolesToString(member.roles.cache.map((r) => r.id));
+
+ // Checks if a verifier has joined
+ if (channel.members.size === 2) {
+ await newState.channel!.permissionOverwrites.set([
+ {
+ id: guild.roles.everyone,
+ allow: ['SEND_MESSAGES'],
+ },
+ ]);
+ return;
+ }
+
+ // Check if a verifier joined a verification VC and update database
+ if (channel.members.size === 2) {
+ if (!channel.name.includes(' - Verification')) {
+ return;
+ }
+
+ await startVerification(channel.id);
+ return;
+ }
+
+ // Checks if there is more than one person who has joined or if the channel has members
+ if (channel.members.size !== 1
+ || !channel.members.has(member.id)) {
+ return;
+ }
+
+ // Check if the user has the verifiers role
+ if (member.roles.cache.has(IDs.roles.staff.verifier)
+ || member.roles.cache.has(IDs.roles.staff.trialVerifier)) {
+ await channel.setName('Verifier Meeting');
+ verifier = true;
+ } else {
+ await channel.setName(`${member.displayName} - Verification`);
+ await currentChannel.send(`Hiya ${member.user}, please be patient as a verifier has been called out to verify you.\n\n`
+ + 'If you leave this voice channel, you will automatically be given the non-vegan role where you gain access to this server and if you\'d like to verify as a vegan again, you\'d have to contact a Mod, which could be done via ModMail.');
+ // Adds to the database that the user joined verification
+ await joinVerification(channel.id, member);
+
+ // Remove all roles from the user
+ await member.roles.remove([
+ IDs.roles.vegan.vegan,
+ IDs.roles.trusted,
+ IDs.roles.nonvegan.nonvegan,
+ IDs.roles.nonvegan.convinced,
+ IDs.roles.nonvegan.vegCurious,
+ ]);
+
+ // Start 15-minute timer if verifier does not join
+ // @ts-ignore
+ this.container.tasks.create('verifyTimeout', {
+ channelId: channel.id,
+ userId: member.id,
+ }, 900_000); // 15 minutes
+ }
+
+ // Check how many voice channels there are
+ const listVoiceChannels = category.children.filter((c) => c.type === 'GUILD_VOICE');
+
+ // Create a text channel for verifiers only
+ // Checks if there are more than 10 voice channels
+ if (!verifier) {
+ const verificationText = await guild.channels.create(`✅┃${member.displayName}-verification`, {
+ type: 'GUILD_TEXT',
+ topic: `Channel for verifiers only. ${member.id} ${channel.id} (Please do not change this)`,
+ parent: category.id,
+ userLimit: 1,
+ permissionOverwrites: [
+ {
+ id: guild.roles.everyone,
+ deny: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.verifyBlock,
+ deny: ['VIEW_CHANNEL', 'SEND_MESSAGES'],
+ },
+ {
+ id: IDs.roles.staff.verifier,
+ allow: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ ],
+ });
+
+ // Send a message that someone wants to be verified
+ const userInfoEmbed = await this.getUserInfo(member, roles);
+ const susNotes = await this.getSus(member, guild);
+ await verificationText.send({
+ content: `${member.user} wants to be verified in ${channel}
+ \n<@&${IDs.roles.staff.verifier}> <@&${IDs.roles.staff.trialVerifier}>`,
+ embeds: [userInfoEmbed, susNotes],
+ });
+
+ await this.verificationProcess(verificationText, channel.id, member, guild);
+ }
+
+ // Create a new channel for others to join
+
+ // Checks if there are more than 10 voice channels
+ if (listVoiceChannels.size > maxVCs - 1) {
+ await guild.channels.create('Verification', {
+ type: 'GUILD_VOICE',
+ parent: category.id,
+ userLimit: 1,
+ permissionOverwrites: [
+ {
+ id: guild.roles.everyone,
+ deny: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.verifyBlock,
+ deny: ['VIEW_CHANNEL', 'CONNECT', 'SEND_MESSAGES'],
+ },
+ {
+ id: IDs.roles.nonvegan.nonvegan,
+ allow: ['VIEW_CHANNEL'],
+ deny: ['CONNECT'],
+ },
+ {
+ id: IDs.roles.vegan.vegan,
+ allow: ['VIEW_CHANNEL'],
+ deny: ['CONNECT'],
+ },
+ {
+ id: IDs.roles.vegan.activist,
+ deny: ['VIEW_CHANNEL', 'CONNECT'],
+ },
+ {
+ id: IDs.roles.staff.verifier,
+ allow: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ ],
+ });
+ } else {
+ await guild.channels.create('Verification', {
+ type: 'GUILD_VOICE',
+ parent: category.id,
+ userLimit: 1,
+ permissionOverwrites: [
+ {
+ id: guild.roles.everyone,
+ deny: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.verifyBlock,
+ deny: ['VIEW_CHANNEL', 'CONNECT', 'SEND_MESSAGES'],
+ },
+ {
+ id: IDs.roles.nonvegan.nonvegan,
+ allow: ['VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.vegan.vegan,
+ allow: ['VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.vegan.activist,
+ deny: ['VIEW_CHANNEL', 'CONNECT'],
+ },
+ {
+ id: IDs.roles.staff.verifier,
+ allow: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ ],
+ });
+ }
+
+ // Change permissions to join the current channel
+ await currentChannel.permissionOverwrites.set([
+ {
+ id: guild.roles.everyone,
+ deny: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.nonvegan.nonvegan,
+ deny: ['VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.vegan.vegan,
+ deny: ['VIEW_CHANNEL'],
+ },
+ {
+ id: member.id,
+ allow: ['VIEW_CHANNEL'],
+ },
+ ]);
+ await currentChannel.setUserLimit(0);
+ }
+
+ // Creates an embed for information about the user
+ private async getUserInfo(user: GuildMember, roles: string) {
+ const joinTime = time(user.joinedAt!);
+ const registerTime = time(user.user.createdAt);
+
+ const embed = new MessageEmbed()
+ .setColor(user.displayHexColor)
+ .setTitle(`Information on ${user.user.username}`)
+ .setThumbnail(user.user.avatarURL()!)
+ .addFields(
+ { name: 'Joined:', value: `${joinTime}`, inline: true },
+ { name: 'Created:', value: `${registerTime}`, inline: true },
+ { name: 'Roles:', value: roles },
+ );
+
+ return embed;
+ }
+
+ // Creates the embed to display the sus note
+ private async getSus(user: GuildMember, guild: Guild) {
+ const notes = await findNotes(user.id, true);
+
+ const embed = new MessageEmbed()
+ .setColor(user.displayHexColor)
+ .setTitle(`${notes.length} sus notes for ${user.user.username}`);
+
+ // Add up to 10 of the latest sus notes to the embed
+ for (let i = notes.length > 10 ? notes.length - 10 : 0; i < notes.length; i += 1) {
+ // Get mod name
+ const modGuildMember = guild!.members.cache.get(notes[i].modId);
+ let mod = notes[i].modId;
+ if (modGuildMember !== undefined) {
+ mod = modGuildMember!.displayName;
+ }
+ // Add sus note to embed
+ embed.addFields({
+ name: `Sus ID: ${notes[i].id} | Moderator: ${mod} | Date: `,
+ value: notes[i].note,
+ });
+ }
+
+ return embed;
+ }
+
+ private async verificationProcess(
+ channel: TextChannel,
+ verId: string,
+ user: GuildMember,
+ guild: Guild,
+ ) {
+ const embedColor = '#0099ff';
+ const info = {
+ page: 0,
+ find: {
+ reason: 0,
+ where: 0,
+ },
+ length: 0,
+ reasoning: 0,
+ life: 0,
+ food: 0,
+ roles: {
+ vegan: false,
+ activist: false,
+ trusted: false,
+ vegCurious: false,
+ convinced: false,
+ },
+ };
+
+ // TODO add a variable that tells if each order has a reversed value, e.g. 0-3 or 3-0
+ const questionLength = questionInfo.length;
+
+ let embed = await this.createEmbed(questionInfo[0].question, embedColor);
+ let buttons = await this.createButtons(questionInfo[0].buttons);
+
+ // Sends the note to verify this note is to be deleted
+ const message = await channel.send({
+ embeds: [embed],
+ components: buttons,
+ });
+
+ // Listen for the button presses
+ const collector = channel.createMessageComponentCollector({
+ // max: 2, // Maximum of 1 button press
+ });
+
+ // Button pressed
+ collector.on('collect', async (button: ButtonInteraction) => {
+ // Select roles
+ if (button.customId.includes('button')) {
+ await button.deferUpdate();
+ // Get the button choice
+ const buttonChoice = this.getButtonValue(button.customId);
+ if (Number.isNaN(buttonChoice)) {
+ return;
+ }
+ // Set the value of the button choice to the page the question was on
+ switch (info.page) {
+ case 0: {
+ info.find.reason = buttonChoice;
+ if (buttonChoice !== 0 && info.find.reason === 0) {
+ embed = await this.createEmbed(serverFind[info.page].question, embedColor);
+ buttons = await this.createButtons(serverFind[info.page].buttons);
+ await message.edit({
+ embeds: [embed],
+ components: buttons,
+ });
+ return;
+ }
+ if (info.find.reason !== 0) {
+ info.find.where = buttonChoice;
+ }
+ break;
+ }
+ case 1: {
+ info.length = buttonChoice;
+ break;
+ }
+ case 2: {
+ info.reasoning = buttonChoice;
+ break;
+ }
+ case 3: {
+ info.life = buttonChoice;
+ break;
+ }
+ case 4: {
+ info.food = buttonChoice;
+ break;
+ }
+ // If they are definitely vegan or not
+ case 5: {
+ if (buttonChoice === 0) {
+ info.roles.vegan = true;
+ info.roles.trusted = true;
+ } else {
+ info.page += 1;
+ }
+ break;
+ }
+ // If they are vegan but should get activist role
+ case 6: {
+ if (buttonChoice === 0) {
+ info.roles.activist = true;
+ }
+ info.page += 1;
+ break;
+ }
+ // If they should get vegan, convinced or non-vegan
+ case 7: {
+ if (buttonChoice === 0) {
+ info.roles.vegan = true;
+ } else if (buttonChoice === 1) {
+ info.roles.convinced = true;
+ }
+ break;
+ }
+ case 8: {
+ if (buttonChoice === 0) {
+ info.roles.vegCurious = true;
+ }
+ break;
+ }
+ default: {
+ console.error('Button clicked out of range');
+ return;
+ }
+ }
+ info.page += 1;
+ // Checks if finished all the questions
+ if (info.page < questionLength) {
+ embed = await this.createEmbed(questionInfo[info.page].question, embedColor);
+ buttons = await this.createButtons(questionInfo[info.page].buttons);
+ await message.edit({
+ embeds: [embed],
+ components: buttons,
+ });
+ }
+ // Confirmation to give roles to the user being verified
+ if (info.page === questionLength) {
+ // Create embed with all the roles the user has
+ embed = new MessageEmbed()
+ .setColor(embedColor)
+ .setTitle(`Give these roles to ${user.displayName}?`)
+ .setThumbnail(user.avatarURL()!)
+ .addFields(
+ { name: 'Roles:', value: this.getTextRoles(info.roles) },
+ );
+
+ // Create buttons for input
+ buttons = [new MessageActionRow()
+ .addComponents(
+ new MessageButton()
+ .setCustomId('confirm')
+ .setLabel('Yes')
+ .setStyle(Constants.MessageButtonStyles.SUCCESS),
+ new MessageButton()
+ .setCustomId('cancel')
+ .setLabel('No')
+ .setStyle(Constants.MessageButtonStyles.DANGER),
+ )];
+ await message.edit({
+ embeds: [embed],
+ components: buttons,
+ });
+ }
+ }
+ // Confirming and finishing the verification
+ if (button.customId === 'confirm' && info.page >= questionLength) {
+ // Check verifier is on the database
+ const verifierGuildMember = await guild.members.cache.get(button.user.id);
+ if (verifierGuildMember === undefined) {
+ await message.edit({ content: 'Verifier not found!' });
+ return;
+ }
+ // Add verifier to database if they're not on the database
+ if (!(await userExists(verifierGuildMember))) {
+ await addExistingUser(verifierGuildMember);
+ }
+
+ // Add verification data to database
+ await finishVerification(verId, button.user.id, info);
+ // Give roles on Discord
+ await this.giveRoles(user, info.roles);
+ // Add timeout if they do not have activist role
+ if (!info.roles.activist) {
+ // @ts-ignore
+ this.container.tasks.create('verifyUnblock', {
+ userId: user.id,
+ guildId: guild.id,
+ }, (info.roles.vegan || info.roles.convinced) ? 604800000 : 1814400000);
+ }
+ // Add embed saying verification completed
+ embed = new MessageEmbed()
+ .setColor('#34c000')
+ .setTitle(`Successfully verified ${user.displayName}!`)
+ .setThumbnail(user.user.avatarURL()!)
+ .addFields(
+ { name: 'Roles:', value: this.getTextRoles(info.roles) },
+ );
+ await message.edit({
+ embeds: [embed],
+ components: [],
+ });
+ // Send welcome message after verification
+ await this.finishMessages(user.user, info.roles);
+ }
+ if (button.customId === 'cancel' && info.page >= questionLength) {
+ info.page = 5;
+ info.roles.vegan = false;
+ info.roles.activist = false;
+ info.roles.trusted = false;
+ info.roles.vegCurious = false;
+ info.roles.convinced = false;
+ embed = await this.createEmbed(questionInfo[info.page].question, embedColor);
+ buttons = await this.createButtons(questionInfo[info.page].buttons);
+ await message.edit({
+ embeds: [embed],
+ components: buttons,
+ });
+ await button.deferUpdate();
+ }
+ });
+ }
+
+ private async createEmbed(title: string, color: ColorResolvable) {
+ return new MessageEmbed()
+ .setColor(color)
+ .setTitle(title);
+ }
+
+ private async createButtons(buttons: string[]) {
+ const buttonActions = [];
+
+ for (let i = 0; i < buttons.length; i += 1) {
+ // Check if it exceeds the maximum buttons in a ActionRow
+ if (i % 5 === 0) {
+ buttonActions.push(new MessageActionRow());
+ }
+ buttonActions[Math.floor(i / 5)]
+ .addComponents(
+ new MessageButton()
+ .setCustomId(`button${i}`)
+ .setLabel(buttons[i])
+ .setStyle(Constants.MessageButtonStyles.SECONDARY),
+ );
+ }
+
+ return buttonActions;
+ }
+
+ // Finds the value of the choice in the button
+ private getButtonValue(button: string) {
+ const buttonChoice = button.at(button.length - 1);
+ if (buttonChoice === undefined) {
+ return NaN;
+ }
+ return parseInt(buttonChoice, 10);
+ }
+
+ private getTextRoles(
+ roles: {
+ vegan: boolean,
+ activist: boolean,
+ trusted: boolean,
+ vegCurious: boolean,
+ convinced: boolean
+ },
+ ) {
+ let rolesText = '';
+ if (roles.convinced) {
+ rolesText += `<@&${IDs.roles.nonvegan.convinced}>`;
+ }
+ if (roles.vegan) {
+ rolesText += `<@&${IDs.roles.vegan.vegan}>`;
+ } else {
+ rolesText += `<@&${IDs.roles.nonvegan.nonvegan}>`;
+ }
+ if (roles.activist) {
+ rolesText += `<@&${IDs.roles.vegan.activist}>`;
+ }
+ if (roles.trusted) {
+ rolesText += `<@&${IDs.roles.trusted}>`;
+ }
+ if (roles.vegCurious) {
+ rolesText += `<@&${IDs.roles.nonvegan.vegCurious}>`;
+ }
+ return rolesText;
+ }
+
+ private async giveRoles(
+ user: GuildMember,
+ roles: {
+ vegan: boolean,
+ activist: boolean,
+ trusted: boolean,
+ vegCurious: boolean,
+ convinced: boolean
+ },
+ ) {
+ const rolesAdd = [];
+ if (roles.convinced) {
+ rolesAdd.push(IDs.roles.nonvegan.convinced);
+ }
+ if (roles.vegan) {
+ rolesAdd.push(IDs.roles.vegan.vegan);
+ } else {
+ rolesAdd.push(IDs.roles.nonvegan.nonvegan);
+ }
+ if (roles.activist) {
+ rolesAdd.push(IDs.roles.vegan.activist);
+ } else {
+ rolesAdd.push(IDs.roles.verifyBlock);
+ }
+ if (roles.trusted) {
+ rolesAdd.push(IDs.roles.trusted);
+ }
+ if (roles.vegCurious) {
+ rolesAdd.push(IDs.roles.nonvegan.vegCurious);
+ }
+ await user.roles.add(rolesAdd);
+ }
+
+ // Messages after verifying the user
+ private async finishMessages(user: User, roles: {
+ vegan: boolean,
+ activist: boolean,
+ trusted: boolean,
+ vegCurious: boolean,
+ convinced: boolean
+ }) {
+ // Send a DM with when their verification is finished
+ await this.finishDM(user, roles)
+ .catch(() => console.error('Verification: Closed DMs'));
+
+ // Not vegan
+ if (!roles.vegan) {
+ const general = this.container.client.channels.cache.get(IDs.channels.nonVegan.general) as TextChannel | undefined;
+ if (general === undefined) {
+ return;
+ }
+ let msg = `${user}, you have been verified! Please check <#${IDs.channels.information.roles}> `
+ + `and remember to follow the <#${IDs.channels.information.conduct}> and to respect ongoing discussion and debates.`;
+ // Add extra info if the user got veg curious or convinced.
+ if (roles.vegCurious || roles.convinced) {
+ msg += `\n\nYou also have access to <#${IDs.channels.dietSupport.main}> for help on going vegan.`;
+ }
+ await general.send(msg);
+ return;
+ }
+
+ // Vegan
+ const general = this.container.client.channels.cache.get(IDs.channels.vegan.general) as TextChannel | undefined;
+ if (general === undefined) {
+ return;
+ }
+ const msg = `Welcome ${user}! Please check out <#${IDs.channels.information.roles}> :)`;
+ await general.send(msg);
+
+ // Activist role
+ if (roles.activist) {
+ const activist = this.container.client.channels.cache.get(IDs.channels.activism.activism) as TextChannel | undefined;
+ if (activist === undefined) {
+ return;
+ }
+ const activistMsg = `${user} you have been given the activist role! This means that if you'd wish to engage with non-vegans in `
+ + `<#${IDs.channels.nonVegan.general}>, you should follow these rules:\n\n`
+ + '1. Try to move conversations with non-vegans towards veganism/animal ethics\n'
+ + '2. Don\'t discuss social topics while activism is happening\n'
+ + '3. Have evidence for claims you make. "I don\'t know" is an acceptable answer. Chances are someone here knows or you can take time to find out\n'
+ + '4. Don\'t advocate for baby steps towards veganism. Participation in exploitation can stop today\n'
+ + '5. Differences in opinion between activists should be resolved in vegan spaces, not in the chat with non-vegans';
+ await activist.send(activistMsg);
+ }
+ }
+
+ // Messages after verifying the user
+ private async finishDM(user: User, roles: {
+ vegan: boolean,
+ activist: boolean,
+ trusted: boolean,
+ vegCurious: boolean,
+ convinced: boolean
+ }) {
+ if (!roles.vegan && !roles.convinced) {
+ const message = 'You\'ve been verified as non-vegan!'
+ + `\n\nYou can next verify on ${time(Math.round(Date.now() / 1000) + 1814400)}`;
+
+ await user.send(message);
+ } else if (roles.convinced) {
+ const message = 'You\'ve been verified as convinced!'
+ + `\n\nYou can next verify on ${time(Math.round(Date.now() / 1000) + 604800)}`;
+
+ await user.send(message);
+ } else if (roles.vegan && !roles.activist) {
+ const message = 'You\'ve been verified as a vegan!'
+ + `\n\nYou can next get verified on ${time(Math.round(Date.now() / 1000) + 604800)} if you would wish to have the activist role.`;
+
+ await user.send(message);
+ }
+ }
+}
+
+export default VerificationJoinVCListener;
diff --git a/src/listeners/verification/leaveVC.ts b/src/listeners/verification/leaveVC.ts
new file mode 100644
index 0000000..47a64c8
--- /dev/null
+++ b/src/listeners/verification/leaveVC.ts
@@ -0,0 +1,183 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+import { container, Listener } from '@sapphire/framework';
+import type {
+ VoiceState, CategoryChannel, VoiceChannel, TextChannel,
+} from 'discord.js';
+import { time } from '@discordjs/builders';
+import { maxVCs, leaveBan } from '../../utils/verificationConfig';
+import { getUser, checkFinish, countIncomplete } from '../../utils/database/verification';
+import { fetchRoles } from '../../utils/database/dbExistingUser';
+import { fibonacci } from '../../utils/mathsSeries';
+import IDs from '../../utils/ids';
+
+class VerificationLeaveVCListener extends Listener {
+ public constructor(context: Listener.Context, options: Listener.Options) {
+ super(context, {
+ ...options,
+ event: 'voiceStateUpdate',
+ });
+ }
+
+ public async run(oldState: VoiceState, newState: VoiceState) {
+ // If the event was not a user joining the channel
+ if (oldState.channel?.parent?.id !== IDs.categories.verification
+ || newState.channel?.parent?.id === IDs.categories.verification
+ || oldState.channel.members.size > 0
+ ) {
+ return;
+ }
+
+ let verifier = false;
+
+ // Check for undefined variables
+ const { client } = container;
+ const { channel } = oldState;
+ const guild = client.guilds.cache.get(newState.guild.id);
+
+ if (channel === null || guild === undefined) {
+ console.error('Verification channel not found');
+ return;
+ }
+
+ // Get the category
+ const categoryGuild = guild.channels.cache.get(IDs.categories.verification);
+ if (categoryGuild === null) {
+ console.error('Verification channel not found');
+ return;
+ }
+ const category = categoryGuild as CategoryChannel;
+
+ // Get the user that was being verified
+ const userSnowflake = await getUser(channel.id);
+ if (userSnowflake === null) {
+ verifier = true;
+ }
+
+ // Allow more people to join VC if there are less than 10 VCs
+
+ if (!verifier) {
+ const user = guild.members.cache.get(userSnowflake!)!;
+
+ // Remove verify as vegan and give non vegan role
+ if (!await checkFinish(channel.id)) {
+ await user.roles.remove(IDs.roles.verifyingAsVegan);
+
+ // Get roles to give back to the user
+ const roles = await fetchRoles(user.id);
+ roles.push(IDs.roles.verifyBlock);
+ await user.roles.add(roles);
+ // Create timeout block for user
+ // Counts the recent times they have incomplete verifications
+ const incompleteCount = await countIncomplete(user.id) % (leaveBan + 1);
+ // Creates the length of the time for the ban
+ const banLength = fibonacci(incompleteCount) * 3600_000;
+
+ // @ts-ignore
+ this.container.tasks.create('verifyUnblock', {
+ userId: user.id,
+ guildId: guild.id,
+ }, banLength);
+
+ await user.user.send('You have been timed out as a verifier had not joined for 15 minutes or you disconnected from verification.\n\n'
+ + `You can verify again at: ${time(Math.round(Date.now() / 1000) + (banLength / 1000))}`)
+ .catch(() => console.error('Verification: Closed DMs'));
+ }
+ }
+
+ // Check how many voice channels there are
+ const listVoiceChannels = category.children.filter((c) => c.type === 'GUILD_VOICE');
+
+ // Check that it is not deleting the 'Verification' channel (in case bot crashes)
+ if (channel.name !== 'Verification') {
+ // Delete the channel
+ await channel.delete();
+ }
+
+ // Delete text channel
+ if (!verifier) {
+ // Gets a list of all the text channels in the verification category
+ const listTextChannels = category.children.filter((c) => c.type === 'GUILD_TEXT');
+ listTextChannels.forEach((c) => {
+ const textChannel = c as TextChannel;
+ // Checks if the channel topic has the user's snowflake
+ if (textChannel.topic!.includes(userSnowflake!)) {
+ textChannel.delete();
+ }
+ });
+ }
+
+ // If there are no VCs left in verification after having the channel deleted
+ if (listVoiceChannels.size === 0) {
+ // Create a verification channel
+ await guild.channels.create('Verification', {
+ type: 'GUILD_VOICE',
+ parent: IDs.categories.verification,
+ userLimit: 1,
+ permissionOverwrites: [
+ {
+ id: guild.roles.everyone,
+ deny: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.verifyBlock,
+ deny: ['VIEW_CHANNEL', 'CONNECT', 'SEND_MESSAGES'],
+ },
+ {
+ id: IDs.roles.nonvegan.nonvegan,
+ allow: ['VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.vegan.vegan,
+ allow: ['VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.vegan.activist,
+ deny: ['VIEW_CHANNEL', 'CONNECT'],
+ },
+ {
+ id: IDs.roles.staff.verifier,
+ allow: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ ],
+ });
+ }
+
+ // If there are less than 10, stop
+ if (listVoiceChannels.size < maxVCs) {
+ return;
+ }
+
+ const verification = listVoiceChannels.last() as VoiceChannel;
+
+ await verification!.permissionOverwrites.set([
+ {
+ id: IDs.roles.nonvegan.nonvegan,
+ allow: ['VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.vegan.vegan,
+ allow: ['VIEW_CHANNEL'],
+ },
+ ]);
+ }
+}
+
+export default VerificationLeaveVCListener;
diff --git a/src/listeners/verification/start.ts b/src/listeners/verification/start.ts
new file mode 100644
index 0000000..2410702
--- /dev/null
+++ b/src/listeners/verification/start.ts
@@ -0,0 +1,111 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+import { Listener } from '@sapphire/framework';
+import type {
+ Client,
+ CategoryChannel,
+ TextChannel,
+ VoiceChannel,
+} from 'discord.js';
+import IDs from '../../utils/ids';
+
+class VerificationReady extends Listener {
+ public constructor(context: Listener.Context, options: Listener.Options) {
+ super(context, {
+ ...options,
+ once: true,
+ event: 'ready',
+ });
+ }
+
+ public async run(client: Client) {
+ // Get verification category
+ let category = client.channels.cache.get(IDs.categories.verification) as CategoryChannel | undefined;
+ if (category === undefined) {
+ category = await client.channels.fetch(IDs.categories.verification) as CategoryChannel | undefined;
+ if (category === undefined) {
+ console.error('verifyStart: Channel not found');
+ return;
+ }
+ }
+
+ // Check how many voice channels there are
+ let voiceChannels = category.children.filter((c) => c.type === 'GUILD_VOICE');
+ const emptyVC: string[] = [];
+ // Delete voice channels
+ voiceChannels.forEach((c) => {
+ const voiceChannel = c as VoiceChannel;
+ if (voiceChannel.members.size === 0) {
+ emptyVC.push(voiceChannel.id);
+ voiceChannel.delete();
+ }
+ });
+
+ // Delete text channels
+ const textChannels = category.children.filter((c) => c.type === 'GUILD_TEXT');
+ textChannels.forEach((c) => {
+ const textChannel = c as TextChannel;
+ // Checks if the channel topic has the user's snowflake
+ emptyVC.forEach((snowflake) => {
+ if (textChannel.topic!.includes(snowflake)) {
+ textChannel.delete();
+ }
+ });
+ });
+
+ // Check if there is no voice channels, create verification
+ voiceChannels = category.children.filter((c) => c.type === 'GUILD_VOICE');
+ if (voiceChannels.size === emptyVC.length) {
+ await category.guild.channels.create('Verification', {
+ type: 'GUILD_VOICE',
+ parent: IDs.categories.verification,
+ userLimit: 1,
+ permissionOverwrites: [
+ {
+ id: category.guild.roles.everyone,
+ deny: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.verifyBlock,
+ deny: ['VIEW_CHANNEL', 'CONNECT', 'SEND_MESSAGES'],
+ },
+ {
+ id: IDs.roles.nonvegan.nonvegan,
+ allow: ['VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.vegan.vegan,
+ allow: ['VIEW_CHANNEL'],
+ },
+ {
+ id: IDs.roles.vegan.activist,
+ deny: ['VIEW_CHANNEL', 'CONNECT'],
+ },
+ {
+ id: IDs.roles.staff.verifier,
+ allow: ['SEND_MESSAGES', 'VIEW_CHANNEL'],
+ },
+ ],
+ });
+ }
+ }
+}
+
+export default VerificationReady;
diff --git a/src/scheduled-tasks/verifyTimeout.ts b/src/scheduled-tasks/verifyTimeout.ts
new file mode 100644
index 0000000..47a0a9d
--- /dev/null
+++ b/src/scheduled-tasks/verifyTimeout.ts
@@ -0,0 +1,56 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+import type { VoiceChannel } from 'discord.js';
+import { ScheduledTask } from '@sapphire/plugin-scheduled-tasks';
+
+export class VerifyTimeout extends ScheduledTask {
+ public constructor(context: ScheduledTask.Context, options: ScheduledTask.Options) {
+ super(context, options);
+ }
+
+ public async run(payload: { channelId: string, userId: string }) {
+ // Get the guild where the user is in
+ let channel = this.container.client.channels.cache.get(payload.channelId) as VoiceChannel | undefined;
+ if (channel === undefined) {
+ channel = await this.container.client.channels.fetch(payload.channelId) as VoiceChannel | undefined;
+ if (channel === undefined) {
+ console.error('verifyTimeout: Channel not found!');
+ return;
+ }
+ }
+
+ if (channel.members.size < 2 && channel.members.has(payload.userId)) {
+ const user = channel.members.get(payload.userId);
+ if (user === undefined) {
+ console.error('verifyTimeout: GuildMember not found!');
+ return;
+ }
+ await user.voice.disconnect();
+ }
+ }
+}
+
+declare module '@sapphire/plugin-scheduled-tasks' {
+ interface ScheduledTasks {
+ verifyUnblock: never;
+ }
+}
+
+export default VerifyTimeout;
diff --git a/src/scheduled-tasks/verifyUnblock.ts b/src/scheduled-tasks/verifyUnblock.ts
new file mode 100644
index 0000000..5af8534
--- /dev/null
+++ b/src/scheduled-tasks/verifyUnblock.ts
@@ -0,0 +1,60 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+import { ScheduledTask } from '@sapphire/plugin-scheduled-tasks';
+import IDs from '../utils/ids';
+
+export class VerifyUnblock extends ScheduledTask {
+ public constructor(context: ScheduledTask.Context, options: ScheduledTask.Options) {
+ super(context, options);
+ }
+
+ public async run(payload: { userId: string, guildId: string }) {
+ // Get the guild where the user is in
+ let guild = this.container.client.guilds.cache.get(payload.guildId);
+ if (guild === undefined) {
+ guild = await this.container.client.guilds.fetch(payload.guildId);
+ if (guild === undefined) {
+ console.error('verifyUnblock: Guild not found!');
+ return;
+ }
+ }
+
+ // Find GuildMember for the user
+ let user = guild.members.cache.get(payload.userId);
+ if (user === undefined) {
+ user = await guild.members.fetch(payload.userId);
+ if (user === undefined) {
+ console.error('verifyUnblock: GuildMember not found!');
+ return;
+ }
+ }
+
+ // Remove the 'verify block' role
+ await user.roles.remove(IDs.roles.verifyBlock);
+ }
+}
+
+declare module '@sapphire/plugin-scheduled-tasks' {
+ interface ScheduledTasks {
+ verifyUnblock: never;
+ }
+}
+
+export default VerifyUnblock;
diff --git a/src/utils/database/dbExistingUser.ts b/src/utils/database/dbExistingUser.ts
new file mode 100644
index 0000000..b0a2831
--- /dev/null
+++ b/src/utils/database/dbExistingUser.ts
@@ -0,0 +1,185 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+import type { GuildMember, GuildMemberRoleManager } from 'discord.js';
+import { PrismaClient } from '@prisma/client';
+import IDs from '../ids';
+
+// Checks if the user exists on the database
+export async function userExists(user: GuildMember) {
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ // Counts if the user is on the database by their snowflake
+ const userQuery = await prisma.user.count({
+ where: {
+ id: user.id,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+
+ // If the user is found on the database, then return true, otherwise, false.
+ return userQuery > 0;
+}
+
+function getRoles(roles: GuildMemberRoleManager) {
+ // Checks what roles the user has
+ const rolesDict = {
+ vegan: roles.cache.has(IDs.roles.vegan.vegan),
+ activist: roles.cache.has(IDs.roles.vegan.activist),
+ plus: roles.cache.has(IDs.roles.vegan.plus),
+ notVegan: roles.cache.has(IDs.roles.nonvegan.nonvegan),
+ vegCurious: roles.cache.has(IDs.roles.nonvegan.vegCurious),
+ convinced: roles.cache.has(IDs.roles.nonvegan.convinced),
+ trusted: roles.cache.has(IDs.roles.trusted),
+ muted: roles.cache.has(IDs.roles.restrictions.muted),
+ };
+
+ return rolesDict;
+}
+
+// Adds the user to the database if they were already on the server before the bot/database
+export async function addExistingUser(user: GuildMember) {
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ // Counts if the user is on the database by their snowflake
+ const userQuery = await prisma.user.count({
+ where: {
+ id: user.id,
+ },
+ });
+
+ // If the user is already in the database
+ if (userQuery > 0) {
+ return;
+ }
+
+ // Parse all the roles into a dictionary
+ const roles = getRoles(user.roles);
+
+ // Create the user in the database
+ await prisma.user.create({
+ data: {
+ id: user.id,
+ vegan: roles.vegan,
+ trusted: roles.trusted,
+ activist: roles.activist,
+ plus: roles.plus,
+ notVegan: roles.notVegan,
+ vegCurious: roles.vegCurious,
+ convinced: roles.convinced,
+ muted: roles.muted,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+}
+
+export async function updateUser(user: GuildMember) {
+ // Check if the user is already on the database
+ if (!(await userExists(user))) {
+ await addExistingUser(user);
+ return;
+ }
+
+ // Parse all the roles into a dictionary
+ const roles = getRoles(user.roles);
+
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ await prisma.user.update({
+ where: {
+ id: user.id,
+ },
+ data: {
+ id: user.id,
+ vegan: roles.vegan,
+ trusted: roles.trusted,
+ activist: roles.activist,
+ plus: roles.plus,
+ notVegan: roles.notVegan,
+ vegCurious: roles.vegCurious,
+ convinced: roles.convinced,
+ muted: roles.muted,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+}
+
+export async function fetchRoles(user: string) {
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ // Get the user's roles
+ const roleQuery = await prisma.user.findUnique({
+ where: {
+ id: user,
+ },
+ select: {
+ vegan: true,
+ trusted: true,
+ activist: true,
+ plus: true,
+ notVegan: true,
+ vegCurious: true,
+ convinced: true,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+
+ // Assign roles to role snowflakes
+ const roles = [];
+
+ if (roleQuery === null) {
+ roles.push('');
+ return roles;
+ }
+ if (roleQuery.vegan) {
+ roles.push(IDs.roles.vegan.vegan);
+ }
+ if (roleQuery.trusted) {
+ roles.push(IDs.roles.trusted);
+ }
+ if (roleQuery.activist) {
+ roles.push(IDs.roles.vegan.activist);
+ }
+ if (roleQuery.plus) {
+ roles.push(IDs.roles.vegan.plus);
+ }
+ if (roleQuery.notVegan) {
+ roles.push(IDs.roles.nonvegan.nonvegan);
+ }
+ if (roleQuery.vegCurious) {
+ roles.push(IDs.roles.nonvegan.vegCurious);
+ }
+ if (roleQuery.convinced) {
+ roles.push(IDs.roles.nonvegan.convinced);
+ }
+
+ return roles;
+}
diff --git a/src/utils/database/sus.ts b/src/utils/database/sus.ts
new file mode 100644
index 0000000..5017868
--- /dev/null
+++ b/src/utils/database/sus.ts
@@ -0,0 +1,99 @@
+import { PrismaClient } from '@prisma/client';
+
+export async function addToDatabase(userId: string, modId: string, message: string) {
+ // Initialise the database connection
+ const prisma = new PrismaClient();
+
+ // Add the user to the database
+ await prisma.sus.create({
+ data: {
+ user: {
+ connect: {
+ id: userId,
+ },
+ },
+ mod: {
+ connect: {
+ id: modId,
+ },
+ },
+ note: message,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+}
+
+// Get a list of sus notes from the user
+export async function findNotes(userId: string, active: boolean) {
+ // Initialise the database connection
+ const prisma = new PrismaClient();
+
+ // Query to get the specific user's sus notes
+ const note = await prisma.sus.findMany({
+ where: {
+ userId,
+ active,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+ return note;
+}
+
+// Get one note from the id
+export async function getNote(noteId: number) {
+ // Initialise the database connection
+ const prisma = new PrismaClient();
+
+ // Query to get the specific user's sus notes
+ const note = await prisma.sus.findUnique({
+ where: {
+ id: noteId,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+ return note;
+}
+
+export async function deactivateNote(noteId: number) {
+ // Initialise the database connection
+ const prisma = new PrismaClient();
+
+ // Query to deactivate the specific sus note
+ await prisma.sus.update({
+ where: {
+ id: noteId,
+ },
+ data: {
+ active: false,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+}
+
+export async function deactivateAllNotes(userId: string) {
+ // Initialise the database connection
+ const prisma = new PrismaClient();
+
+ // Query to deactivate the specific user's sus notes
+ await prisma.sus.updateMany({
+ where: {
+ userId: {
+ contains: userId,
+ },
+ },
+ data: {
+ active: false,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+}
diff --git a/src/utils/database/verification.ts b/src/utils/database/verification.ts
new file mode 100644
index 0000000..410dd7f
--- /dev/null
+++ b/src/utils/database/verification.ts
@@ -0,0 +1,230 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+import type { GuildMember } from 'discord.js';
+import { PrismaClient } from '@prisma/client';
+import { updateUser } from './dbExistingUser';
+import { leaveBan } from '../verificationConfig';
+import { fibonacci } from '../mathsSeries';
+
+export async function joinVerification(channelId: string, user: GuildMember) {
+ // Update the user on the database with the current roles they have
+ await updateUser(user);
+
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ await prisma.verify.create({
+ data: {
+ id: channelId,
+ user: {
+ connect: {
+ id: user.id,
+ },
+ },
+ },
+ });
+
+ // Close database connection
+ await prisma.$disconnect();
+}
+
+export async function startVerification(channelId: string) {
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ await prisma.verify.update({
+ where: {
+ id: channelId,
+ },
+ data: {
+ startTime: new Date(),
+ },
+ });
+
+ // Close database connection
+ await prisma.$disconnect();
+}
+
+export async function getUser(channelId: string) {
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ // Get the snowflake of the user verifying
+ const user = await prisma.verify.findUnique({
+ where: {
+ id: channelId,
+ },
+ select: {
+ userId: true,
+ },
+ });
+
+ // Close database connection
+ await prisma.$disconnect();
+
+ // Check the user could be found
+ if (user === null) {
+ return null;
+ }
+
+ // Return the user's snowflake
+ return user.userId;
+}
+
+export async function finishVerification(
+ channelId: string,
+ verifierId: string,
+ info: {
+ page: number,
+ find: {
+ reason: number,
+ where: number
+ },
+ length: number,
+ reasoning: number,
+ life: number,
+ food: number,
+ roles: {
+ vegan: boolean,
+ activist: boolean,
+ trusted: boolean,
+ vegCurious: boolean,
+ convinced: boolean
+ } },
+) {
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ // TODO potentially add an incomplete tracker?
+ await prisma.verify.update({
+ where: {
+ id: channelId,
+ },
+ data: {
+ verifier: {
+ connect: {
+ id: verifierId,
+ },
+ },
+ finishTime: new Date(),
+ // Roles
+ vegan: info.roles.vegan,
+ activist: info.roles.activist,
+ trusted: info.roles.trusted,
+ vegCurious: info.roles.vegCurious,
+ convinced: info.roles.convinced,
+ // Statistics
+ reason: info.find.reason,
+ where: info.find.where,
+ length: info.length,
+ reasoning: info.reasoning,
+ life: info.life,
+ food: info.food,
+ },
+ });
+
+ // Close database connection
+ await prisma.$disconnect();
+}
+
+// Checks if verification was complete
+export async function checkFinish(channelId: string) {
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ // Get the snowflake of the user verifying
+ const finish = await prisma.verify.findUnique({
+ where: {
+ id: channelId,
+ },
+ select: {
+ finishTime: true,
+ },
+ });
+
+ // Close database connection
+ await prisma.$disconnect();
+
+ // Checks if query returned is null
+ if (finish === null) {
+ return false;
+ }
+
+ // Return if a finish time has been set meaning verification is complete
+ return finish.finishTime !== null;
+}
+
+// Counts how many times the user has not had a verifier join their VC before leaving
+export async function countIncomplete(userId: string) {
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ // Count how many times the user has not completed a verification
+ const incompleteCount = await prisma.verify.count({
+ where: {
+ userId,
+ finishTime: null,
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+
+ return incompleteCount;
+}
+
+// Gets the amount of time left on the block
+export async function blockTime(userId: string) {
+ // Initialises Prisma Client
+ const prisma = new PrismaClient();
+
+ // Count how many times the user has not completed a verification
+ const verification = await prisma.verify.findFirst({
+ where: {
+ userId,
+ },
+ orderBy: {
+ id: 'desc',
+ },
+ });
+
+ // Close the database connection
+ await prisma.$disconnect();
+
+ if (verification === null) {
+ return 0;
+ }
+
+ // If user finished verification
+ if (verification.finishTime !== null) {
+ // Activist role
+ if (verification.activist) {
+ return 0;
+ }
+ const timeOff = new Date().getTime() - verification.finishTime.getTime();
+ return ((verification.vegan || verification.convinced) ? 604800000 : 1814400000) - timeOff;
+ }
+
+ // Timeouts
+ const count = await countIncomplete(verification.userId) % (leaveBan + 1);
+ const timeOff = new Date().getTime() - verification.joinTime.getTime();
+ // Creates the length of the time for the ban
+ return (fibonacci(count) * 3600_000) - timeOff;
+}
diff --git a/src/utils/dbExistingUser.ts b/src/utils/dbExistingUser.ts
deleted file mode 100644
index 14a5892..0000000
--- a/src/utils/dbExistingUser.ts
+++ /dev/null
@@ -1,87 +0,0 @@
-// SPDX-License-Identifier: GPL-3.0-or-later
-/*
- Animal Rights Advocates Discord Bot
- Copyright (C) 2022 Anthony Berg
-
- This program is free software: you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation, either version 3 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program. If not, see .
-*/
-
-import type { GuildMember } from 'discord.js';
-import { PrismaClient } from '@prisma/client';
-import IDs from './ids';
-
-// Checks if the user exists on the database
-export async function userExists(user: GuildMember) {
- // Initialises Prisma Client
- const prisma = new PrismaClient();
-
- // Counts if the user is on the database by their snowflake
- const userQuery = await prisma.user.count({
- where: {
- id: user.id,
- },
- });
-
- // Close the database connection
- await prisma.$disconnect();
-
- // If the user is found on the database, then return true, otherwise, false.
- return userQuery > 0;
-}
-
-// Adds the user to the database if they were already on the server before the bot/database
-export async function addExistingUser(user: GuildMember) {
- // Initialises Prisma Client
- const prisma = new PrismaClient();
-
- // Counts if the user is on the database by their snowflake
- const userQuery = await prisma.user.count({
- where: {
- id: user.id,
- },
- });
-
- // If the user is already in the database
- if (userQuery > 0) {
- return;
- }
-
- // Checks what roles the user has
- const hasVegan = user.roles.cache.has(IDs.roles.vegan.vegan);
- const hasActivist = user.roles.cache.has(IDs.roles.vegan.activist);
- const hasPlus = user.roles.cache.has(IDs.roles.vegan.plus);
- const hasNotVegan = user.roles.cache.has(IDs.roles.nonvegan.nonvegan);
- const hasVegCurious = user.roles.cache.has(IDs.roles.nonvegan.vegCurious);
- const hasConvinced = user.roles.cache.has(IDs.roles.nonvegan.convinced);
- const hasTrusted = user.roles.cache.has(IDs.roles.trusted);
- const hasMuted = user.roles.cache.has(IDs.roles.restrictions.muted);
-
- // Create the user in the database
- await prisma.user.create({
- data: {
- id: user.id,
- vegan: hasVegan,
- trusted: hasTrusted,
- activist: hasActivist,
- plus: hasPlus,
- notVegan: hasNotVegan,
- vegCurious: hasVegCurious,
- convinced: hasConvinced,
- muted: hasMuted,
- },
- });
-
- // Close the database connection
- await prisma.$disconnect();
-}
diff --git a/src/utils/devIDs.ts b/src/utils/devIDs.ts
index b5fb74b..72857b7 100644
--- a/src/utils/devIDs.ts
+++ b/src/utils/devIDs.ts
@@ -60,15 +60,28 @@ const devIDs = {
channels: {
information: {
news: '999431676058927247',
+ conduct: '999431676058927248',
+ roles: '999431676058927250',
},
staff: {
coordinators: '999431676058927254',
standup: '999431676289622183',
verifiers: '999431677006860411',
},
+ dietSupport: {
+ info: '999431677006860417',
+ introduction: '999431677325615184',
+ main: '999431677325615185',
+ },
nonVegan: {
general: '999431677325615189',
},
+ vegan: {
+ general: '999431677535338575',
+ },
+ activism: {
+ activism: '999431678214807604',
+ },
diversity: {
women: '999431679053660187',
lgbtqia: '999431679053660188',
diff --git a/src/utils/formatter.ts b/src/utils/formatter.ts
new file mode 100644
index 0000000..5dc0664
--- /dev/null
+++ b/src/utils/formatter.ts
@@ -0,0 +1,34 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+import type { Snowflake } from 'discord-api-types/globals';
+
+export function rolesToString(roles: Snowflake[]) {
+ let output = '';
+
+ roles.forEach((role) => {
+ output += `<@&${role}>`;
+ });
+
+ if (output.length === 0) {
+ output = 'None';
+ }
+
+ return output;
+}
diff --git a/src/utils/ids.ts b/src/utils/ids.ts
index c07074b..6d38d25 100644
--- a/src/utils/ids.ts
+++ b/src/utils/ids.ts
@@ -52,23 +52,39 @@ let IDs = {
moderator: '826157475815489598',
trialModerator: '982074555596152904',
verifier: '871802735031373856',
+ trialVerifier: '982635638010572850',
},
stageHost: '854893757593419786',
patron: '765370219207852055',
patreon: '993848684640997406',
verifyingAsVegan: '854725899576279060',
+ verifyBlock: '1032765019269640203',
},
channels: {
information: {
news: '866000393259319306',
+ conduct: '990728521531920385',
+ roles: '990761562199457813',
},
staff: {
coordinators: '1006240682505142354',
standup: '996009201237233684',
+ verifiers: '873215538627756072',
+ },
+ dietSupport: {
+ info: '993891104346873888',
+ introduction: '993272252743286874',
+ main: '822665615612837918',
},
nonVegan: {
general: '798967615636504657',
},
+ vegan: {
+ general: '787738272616808509',
+ },
+ activism: {
+ activism: '730907954877956179',
+ },
diversity: {
women: '938808963544285324',
lgbtqia: '956224226556272670',
@@ -77,6 +93,7 @@ let IDs = {
},
},
categories: {
+ verification: '797505409073676299',
diversity: '933078380394459146',
},
};
diff --git a/src/utils/mathsSeries.ts b/src/utils/mathsSeries.ts
new file mode 100644
index 0000000..2a99459
--- /dev/null
+++ b/src/utils/mathsSeries.ts
@@ -0,0 +1,34 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+// Created because Stove loves Fibonacci sequences
+// A fibonacci sequence where n = 0 => 1
+export function fibonacci(position: number) {
+ let previous = 0;
+ let next = 1;
+ let tempNext;
+
+ for (let i = 0; i < position; i += 1) {
+ tempNext = next + previous;
+ previous = next;
+ next = tempNext;
+ }
+
+ return next;
+}
diff --git a/src/utils/verificationConfig.ts b/src/utils/verificationConfig.ts
new file mode 100644
index 0000000..c47e22e
--- /dev/null
+++ b/src/utils/verificationConfig.ts
@@ -0,0 +1,141 @@
+// SPDX-License-Identifier: GPL-3.0-or-later
+/*
+ Animal Rights Advocates Discord Bot
+ Copyright (C) 2022 Anthony Berg
+
+ This program is free software: you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation, either version 3 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see .
+*/
+
+// The maximum amount of verification VCs there can be
+export const maxVCs = 10;
+
+// The maximum amount of leaving bans before time resets
+export const leaveBan = 8;
+
+export const questionInfo = [
+ {
+ question: 'Welcome to Animal Rights Advocates! How did you find the server?',
+ buttons: [
+ 'Search',
+ 'Friend',
+ 'YouTube',
+ 'Another Server',
+ 'Vegan Org',
+ ],
+ },
+ {
+ question: 'How long have you been vegan?',
+ buttons: [
+ '<1 month',
+ '1-2 months',
+ '3-6 months',
+ '6 months - 1 year',
+ '1-2 years',
+ '2+ years',
+ ],
+ },
+ {
+ question: 'Ask the user why they went vegan and to define veganism.\n'
+ + 'Do they cite ethical concerns and abstinence from at least meat, dairy, eggs, leather, and fur?',
+ buttons: [
+ 'Yes',
+ 'Yes with prompting',
+ 'No',
+ ],
+ },
+ {
+ question: 'Ask the user about their life as a vegan, including things like watching documentaries or social media content and interactions with family and friends. What are their stories like?',
+ buttons: [
+ 'Believable',
+ 'Unbelievable',
+ 'Short',
+ ],
+ },
+ {
+ question: 'Ask the user about food and nutrition. Do they seem to know how to live as a vegan?',
+ buttons: [
+ 'Dietitian / Chef',
+ 'Acceptable',
+ 'Salads / Smoothies',
+ 'No clue',
+ ],
+ },
+ {
+ question: 'Do you think this user is definitely vegan?',
+ buttons: [
+ 'Yes',
+ 'No',
+ ],
+ },
+ {
+ question: 'Offer to ask questions for Activist. Do you think they should get it?',
+ buttons: [
+ 'Yes',
+ 'No',
+ ],
+ },
+ {
+ question: 'Do some activism, asking Activist questions. Now which role should they get?',
+ buttons: [
+ 'Vegan',
+ 'Convinced',
+ 'Non-vegan',
+ ],
+ },
+ {
+ question: 'Should this user get Veg Curious?',
+ buttons: [
+ 'Yes',
+ 'No',
+ ],
+ },
+];
+
+export const serverFind = [
+ // From a friend
+ {
+ question: 'Ask for username and indicate',
+ buttons: [
+ 'Vegan',
+ 'Non-Vegan',
+ 'Unknown',
+ ],
+ },
+ // From a video
+ {
+ question: 'Ask what video',
+ buttons: [
+ 'Troll video',
+ 'Our content',
+ 'Other',
+ ],
+ },
+ // From another server
+ {
+ question: 'Ask which server',
+ buttons: [
+ 'Vegan',
+ 'Debate',
+ 'Other',
+ ],
+ },
+ // From a vegan organisation
+ {
+ question: 'Ask which one',
+ buttons: [
+ 'Vegan Hacktivists',
+ 'Other',
+ ],
+ },
+];
diff --git a/tsconfig.json b/tsconfig.json
index e2256ed..659c12b 100644
--- a/tsconfig.json
+++ b/tsconfig.json
@@ -12,7 +12,7 @@
// "disableReferencedProjectLoad": true, /* Reduce the number of projects loaded automatically by TypeScript. */
/* Language and Environment */
- "target": "es2016", /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */
+ "target": "es2021", /* Set the JavaScript language version for emitted JavaScript and include compatible library declarations. */
// "lib": [], /* Specify a set of bundled library declaration files that describe the target runtime environment. */
// "jsx": "preserve", /* Specify what JSX code is generated. */
// "experimentalDecorators": true, /* Enable experimental support for TC39 stage 2 draft decorators. */
@@ -101,7 +101,7 @@
/* Completeness */
// "skipDefaultLibCheck": true, /* Skip type checking .d.ts files that are included with TypeScript. */
- "skipLibCheck": true /* Skip type checking all .d.ts files. */
+ // "skipLibCheck": true /* Skip type checking all .d.ts files. */
},
"include": ["src"]
}