From e2261b63e9053fb5116dd0ef393f464bf16da190 Mon Sep 17 00:00:00 2001
From: Balazs Nadasdi <efertone@pm.me>
Date: Thu, 22 Jun 2023 08:56:40 +0200
Subject: [PATCH 01/17] fix: clear queue endpoint error with redis script
 (#11037)

Error message:
```
ReplyError: ERR value is not an integer or out of range script: 720d973b3877f92b4fb3285ced83c97cdd204979, on @user_script:209.
```

The whole error can be tracked back to one of the arguments, which is
`Infinity` in the codebase, but it has to be a number.

The documentation in bullmq says `0` is unlimited[^1], and bullmq tries to
parse the argument with `tonumber` which returns with `-9223372036854775808` if
the argument is `"Infinity"` which is out of bound.

```
127.0.0.1:6379> eval 'return tonumber(ARGV[3])' '2' 'slippy.xyz:queue:inbox:inbox:delayed' 'slippy.xyz:queue:inbox:inbox:events' 'slippy.xyz:queue:inbox:inbox:' '1687183763944' Infinity 'delayed'
(integer) -9223372036854775808
127.0.0.1:6379>
```

[^1]: https://github.com/taskforcesh/bullmq/blob/master/src/commands/cleanJobsInSet-2.lua#L10

Signed-off-by: Efertone <efertone@pm.me>
---
 packages/backend/src/core/QueueService.ts | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/packages/backend/src/core/QueueService.ts b/packages/backend/src/core/QueueService.ts
index 2ae8a2b754..5b7359074e 100644
--- a/packages/backend/src/core/QueueService.ts
+++ b/packages/backend/src/core/QueueService.ts
@@ -400,11 +400,11 @@ export class QueueService {
 		this.deliverQueue.once('cleaned', (jobs, status) => {
 			//deliverLogger.succ(`Cleaned ${jobs.length} ${status} jobs`);
 		});
-		this.deliverQueue.clean(0, Infinity, 'delayed');
+		this.deliverQueue.clean(0, 0, 'delayed');
 
 		this.inboxQueue.once('cleaned', (jobs, status) => {
 			//inboxLogger.succ(`Cleaned ${jobs.length} ${status} jobs`);
 		});
-		this.inboxQueue.clean(0, Infinity, 'delayed');
+		this.inboxQueue.clean(0, 0, 'delayed');
 	}
 }

From e8c5117b2dfc60641c26ff972917c8cd94731040 Mon Sep 17 00:00:00 2001
From: Caipira <caipira@libnare.net>
Date: Fri, 23 Jun 2023 16:30:47 +0900
Subject: [PATCH 02/17] fix(backend): Resolve missing parseObjectId in
 IdService (#11039)

---
 packages/backend/src/core/IdService.ts | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/packages/backend/src/core/IdService.ts b/packages/backend/src/core/IdService.ts
index 8aa6ccfc4e..60098bc81c 100644
--- a/packages/backend/src/core/IdService.ts
+++ b/packages/backend/src/core/IdService.ts
@@ -5,7 +5,7 @@ import type { Config } from '@/config.js';
 import { genAid, parseAid } from '@/misc/id/aid.js';
 import { genMeid, parseMeid } from '@/misc/id/meid.js';
 import { genMeidg, parseMeidg } from '@/misc/id/meidg.js';
-import { genObjectId } from '@/misc/id/object-id.js';
+import { genObjectId, parseObjectId } from '@/misc/id/object-id.js';
 import { bindThis } from '@/decorators.js';
 import { parseUlid } from '@/misc/id/ulid.js';
 
@@ -38,7 +38,7 @@ export class IdService {
 	public parse(id: string): { date: Date; } {
 		switch (this.method) {
 			case 'aid': return parseAid(id);
-			case 'objectid':
+			case 'objectid': return parseObjectId(id);
 			case 'meid': return parseMeid(id);
 			case 'meidg': return parseMeidg(id);
 			case 'ulid': return parseUlid(id);

From 33a2c0b59eea01699741ffb06ac31b82bcd1aefd Mon Sep 17 00:00:00 2001
From: Yuriha <121590760+yuriha-chan@users.noreply.github.com>
Date: Sat, 24 Jun 2023 07:51:44 +0900
Subject: [PATCH 03/17] Make role tag clickable on user pages (#11019)

---
 packages/frontend/src/pages/user/home.vue | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/packages/frontend/src/pages/user/home.vue b/packages/frontend/src/pages/user/home.vue
index 2e69eb367b..23588763bc 100644
--- a/packages/frontend/src/pages/user/home.vue
+++ b/packages/frontend/src/pages/user/home.vue
@@ -44,8 +44,10 @@
 					</div>
 					<div v-if="user.roles.length > 0" class="roles">
 						<span v-for="role in user.roles" :key="role.id" v-tooltip="role.description" class="role" :style="{ '--color': role.color }">
-							<img v-if="role.iconUrl" style="height: 1.3em; vertical-align: -22%;" :src="role.iconUrl"/>
-							{{ role.name }}
+							<MkA v-adaptive-bg :to="`/roles/${role.id}`">
+								<img v-if="role.iconUrl" style="height: 1.3em; vertical-align: -22%;" :src="role.iconUrl"/>
+								{{ role.name }}
+							</MkA>
 						</span>
 					</div>
 					<div v-if="iAmModerator" class="moderationNote">

From 3fe1c862f66b118b81c7d66d8627a1dfa13372dd Mon Sep 17 00:00:00 2001
From: syuilo <Syuilotan@yahoo.co.jp>
Date: Sat, 24 Jun 2023 12:46:30 +0900
Subject: [PATCH 04/17] update misskey-js version

---
 packages/frontend/tsconfig.json  | 6 +++---
 packages/misskey-js/package.json | 2 +-
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/packages/frontend/tsconfig.json b/packages/frontend/tsconfig.json
index 514b304246..e02acb6c5a 100644
--- a/packages/frontend/tsconfig.json
+++ b/packages/frontend/tsconfig.json
@@ -23,12 +23,12 @@
 		"useDefineForClassFields": true,
 		"baseUrl": ".",
 		"paths": {
-			"@/*": ["./src/*"],
+			"@/*": ["./src/*"]
 		},
 		"typeRoots": [
 			"node_modules/@types",
 			"node_modules/@vue-macros",
-			"@types",
+			"@types"
 		],
 		"types": [
 			"vite/client",
@@ -47,6 +47,6 @@
 		"./**/*.vue"
 	],
 	"exclude": [
-		".storybook/**/*",
+		".storybook/**/*"
 	]
 }
diff --git a/packages/misskey-js/package.json b/packages/misskey-js/package.json
index 23836b05f5..b0a7e15051 100644
--- a/packages/misskey-js/package.json
+++ b/packages/misskey-js/package.json
@@ -1,6 +1,6 @@
 {
 	"name": "misskey-js",
-	"version": "0.0.15",
+	"version": "0.0.16 ",
 	"description": "Misskey SDK for JavaScript",
 	"main": "./built/index.js",
 	"types": "./built/index.d.ts",

From dc27ba6f036c15ff94aaa76b3a6928e97c934fe7 Mon Sep 17 00:00:00 2001
From: syuilo <Syuilotan@yahoo.co.jp>
Date: Sat, 24 Jun 2023 12:58:26 +0900
Subject: [PATCH 05/17] enhance(frontend): improve ux of deck scroll

Resolve #11007
---
 packages/frontend/src/ui/deck.vue        | 17 +++++++++--------
 packages/frontend/src/ui/deck/column.vue |  5 +++++
 2 files changed, 14 insertions(+), 8 deletions(-)

diff --git a/packages/frontend/src/ui/deck.vue b/packages/frontend/src/ui/deck.vue
index bd5d5beb84..988fda1c2f 100644
--- a/packages/frontend/src/ui/deck.vue
+++ b/packages/frontend/src/ui/deck.vue
@@ -4,12 +4,13 @@
 
 	<div :class="$style.main">
 		<XStatusBars/>
-		<div ref="columnsEl" :class="[$style.sections, { [$style.center]: deckStore.reactiveState.columnAlign.value === 'center', [$style.snapScroll]: snapScroll }]" @contextmenu.self.prevent="onContextmenu">
+		<div ref="columnsEl" :class="[$style.sections, { [$style.center]: deckStore.reactiveState.columnAlign.value === 'center', [$style.snapScroll]: snapScroll }]" @contextmenu.self.prevent="onContextmenu" @wheel.self="onWheel">
 			<!-- sectionを利用しているのは、deck.vue側でcolumnに対してfirst-of-typeを効かせるため -->
 			<section
 				v-for="ids in layout"
 				:class="$style.section"
 				:style="columns.filter(c => ids.includes(c.id)).some(c => c.flexible) ? { flex: 1, minWidth: '350px' } : { width: Math.max(...columns.filter(c => ids.includes(c.id)).map(c => c.width)) + 'px' }"
+				@wheel.self="onWheel"
 			>
 				<component
 					:is="columnComponents[columns.find(c => c.id === id)!.type] ?? XTlColumn"
@@ -19,6 +20,7 @@
 					:class="$style.column"
 					:column="columns.find(c => c.id === id)"
 					:isStacked="ids.length > 1"
+					@headerWheel="onWheel"
 				/>
 			</section>
 			<div v-if="layout.length === 0" class="_panel" :class="$style.onboarding">
@@ -196,15 +198,14 @@ const onContextmenu = (ev) => {
 	}], ev);
 };
 
-document.documentElement.style.overflowY = 'hidden';
-document.documentElement.style.scrollBehavior = 'auto';
-window.addEventListener('wheel', (ev) => {
-	if (ev.target === columnsEl && ev.deltaX === 0) {
-		columnsEl.scrollLeft += ev.deltaY;
-	} else if (getScrollContainer(ev.target as HTMLElement) == null && ev.deltaX === 0) {
+function onWheel(ev: WheelEvent) {
+	if (ev.deltaX === 0) {
 		columnsEl.scrollLeft += ev.deltaY;
 	}
-});
+}
+
+document.documentElement.style.overflowY = 'hidden';
+document.documentElement.style.scrollBehavior = 'auto';
 
 loadDeck();
 
diff --git a/packages/frontend/src/ui/deck/column.vue b/packages/frontend/src/ui/deck/column.vue
index c8d6744a37..f6c5c8de46 100644
--- a/packages/frontend/src/ui/deck/column.vue
+++ b/packages/frontend/src/ui/deck/column.vue
@@ -12,6 +12,7 @@
 		@dragstart="onDragstart"
 		@dragend="onDragend"
 		@contextmenu.prevent.stop="onContextmenu"
+		@wheel="emit('headerWheel', $event)"
 	>
 		<svg viewBox="0 0 256 128" :class="$style.tabShape">
 			<g transform="matrix(6.2431,0,0,6.2431,-677.417,-29.3839)">
@@ -56,6 +57,10 @@ const props = withDefaults(defineProps<{
 	naked: false,
 });
 
+const emit = defineEmits<{
+	(ev: 'headerWheel', ctx: WheelEvent): void;
+}>();
+
 let body = $shallowRef<HTMLDivElement | null>();
 
 let dragging = $ref(false);

From 60cc7f62e619d097099183c40a5c816e4ba50fe5 Mon Sep 17 00:00:00 2001
From: syuilo <Syuilotan@yahoo.co.jp>
Date: Sat, 24 Jun 2023 13:11:53 +0900
Subject: [PATCH 06/17] update deps

---
 package.json                                  |    8 +-
 packages/backend/package.json                 |   58 +-
 .../backend/src/server/web/views/base.pug     |    2 +-
 packages/frontend/package.json                |   44 +-
 packages/misskey-js/package.json              |   16 +-
 packages/sw/package.json                      |    6 +-
 pnpm-lock.yaml                                | 2527 +++++++----------
 7 files changed, 1036 insertions(+), 1625 deletions(-)

diff --git a/package.json b/package.json
index dd0c1d57e7..6e28b8cf54 100644
--- a/package.json
+++ b/package.json
@@ -56,11 +56,11 @@
 	"devDependencies": {
 		"@types/gulp": "4.0.10",
 		"@types/gulp-rename": "2.0.1",
-		"@typescript-eslint/eslint-plugin": "5.59.8",
-		"@typescript-eslint/parser": "5.59.8",
+		"@typescript-eslint/eslint-plugin": "5.60.0",
+		"@typescript-eslint/parser": "5.60.0",
 		"cross-env": "7.0.3",
-		"cypress": "12.13.0",
-		"eslint": "8.41.0",
+		"cypress": "12.15.0",
+		"eslint": "8.43.0",
 		"start-server-and-test": "2.0.0"
 	},
 	"optionalDependencies": {
diff --git a/packages/backend/package.json b/packages/backend/package.json
index 56ecbc2eaf..c5b6278b69 100644
--- a/packages/backend/package.json
+++ b/packages/backend/package.json
@@ -54,31 +54,31 @@
 		"@aws-sdk/client-s3": "3.321.1",
 		"@aws-sdk/lib-storage": "3.321.1",
 		"@aws-sdk/node-http-handler": "3.321.1",
-		"@bull-board/api": "5.2.0",
-		"@bull-board/fastify": "5.2.0",
-		"@bull-board/ui": "5.2.0",
+		"@bull-board/api": "5.5.3",
+		"@bull-board/fastify": "5.5.3",
+		"@bull-board/ui": "5.5.3",
 		"@discordapp/twemoji": "14.1.2",
-		"@fastify/accepts": "4.1.0",
+		"@fastify/accepts": "4.2.0",
 		"@fastify/cookie": "8.3.0",
 		"@fastify/cors": "8.3.0",
-		"@fastify/http-proxy": "9.1.0",
-		"@fastify/multipart": "7.6.0",
+		"@fastify/http-proxy": "9.2.1",
+		"@fastify/multipart": "7.7.0",
 		"@fastify/static": "6.10.2",
 		"@fastify/view": "7.4.1",
-		"@nestjs/common": "9.4.2",
-		"@nestjs/core": "9.4.2",
-		"@nestjs/testing": "9.4.2",
+		"@nestjs/common": "10.0.3",
+		"@nestjs/core": "10.0.3",
+		"@nestjs/testing": "10.0.3",
 		"@peertube/http-signature": "1.7.0",
-		"@sinonjs/fake-timers": "10.2.0",
+		"@sinonjs/fake-timers": "10.3.0",
 		"@swc/cli": "0.1.62",
-		"@swc/core": "1.3.61",
+		"@swc/core": "1.3.66",
 		"accepts": "1.3.8",
 		"ajv": "8.12.0",
 		"archiver": "5.3.1",
 		"autwh": "0.1.0",
 		"bcryptjs": "2.4.3",
 		"blurhash": "2.0.5",
-		"bullmq": "3.15.0",
+		"bullmq": "4.1.0",
 		"cacheable-lookup": "6.1.0",
 		"cbor": "9.0.0",
 		"chalk": "5.2.0",
@@ -90,9 +90,9 @@
 		"date-fns": "2.30.0",
 		"deep-email-validator": "0.1.21",
 		"escape-regexp": "0.0.1",
-		"fastify": "4.17.0",
+		"fastify": "4.18.0",
 		"feed": "4.2.2",
-		"file-type": "18.4.0",
+		"file-type": "18.5.0",
 		"fluent-ffmpeg": "2.1.2",
 		"form-data": "4.0.0",
 		"got": "12.6.0",
@@ -106,7 +106,7 @@
 		"json5": "2.2.3",
 		"jsonld": "8.2.0",
 		"jsrsasign": "10.8.6",
-		"meilisearch": "0.32.5",
+		"meilisearch": "0.33.0",
 		"mfm-js": "0.23.3",
 		"mime-types": "2.1.35",
 		"misskey-js": "workspace:*",
@@ -129,7 +129,7 @@
 		"qrcode": "1.5.3",
 		"random-seed": "0.3.0",
 		"ratelimiter": "3.4.1",
-		"re2": "1.19.0",
+		"re2": "1.19.1",
 		"redis-lock": "0.1.4",
 		"reflect-metadata": "0.1.13",
 		"rename": "1.0.4",
@@ -137,28 +137,28 @@
 		"rss-parser": "3.13.0",
 		"rxjs": "7.8.1",
 		"s-age": "1.1.2",
-		"sanitize-html": "2.10.0",
+		"sanitize-html": "2.11.0",
 		"seedrandom": "3.0.5",
-		"semver": "7.5.1",
+		"semver": "7.5.3",
 		"sharp": "0.32.1",
 		"sharp-read-bmp": "github:misskey-dev/sharp-read-bmp",
 		"slacc": "0.0.9",
 		"strict-event-emitter-types": "2.0.0",
 		"stringz": "2.1.0",
 		"summaly": "github:misskey-dev/summaly",
-		"systeminformation": "5.17.16",
+		"systeminformation": "5.18.4",
 		"tinycolor2": "1.6.0",
 		"tmp": "0.2.1",
 		"tsc-alias": "1.8.6",
 		"tsconfig-paths": "4.2.0",
 		"twemoji-parser": "14.0.0",
-		"typeorm": "0.3.16",
+		"typeorm": "0.3.17",
 		"typescript": "5.1.3",
 		"ulid": "2.3.0",
 		"unzipper": "0.10.14",
 		"uuid": "9.0.0",
 		"vary": "1.1.2",
-		"web-push": "3.6.1",
+		"web-push": "3.6.3",
 		"ws": "8.13.0",
 		"xev": "3.0.2"
 	},
@@ -176,14 +176,14 @@
 		"@types/jest": "29.5.2",
 		"@types/js-yaml": "4.0.5",
 		"@types/jsdom": "21.1.1",
-		"@types/jsonld": "1.5.8",
+		"@types/jsonld": "1.5.9",
 		"@types/jsrsasign": "10.5.8",
 		"@types/mime-types": "2.1.1",
-		"@types/node": "20.2.5",
+		"@types/node": "20.3.1",
 		"@types/node-fetch": "3.0.3",
 		"@types/nodemailer": "6.4.8",
 		"@types/oauth": "0.9.1",
-		"@types/pg": "8.10.1",
+		"@types/pg": "8.10.2",
 		"@types/pug": "2.0.6",
 		"@types/punycode": "2.1.0",
 		"@types/qrcode": "1.5.0",
@@ -198,16 +198,16 @@
 		"@types/tinycolor2": "1.4.3",
 		"@types/tmp": "0.2.3",
 		"@types/unzipper": "0.10.6",
-		"@types/uuid": "9.0.1",
+		"@types/uuid": "9.0.2",
 		"@types/vary": "1.1.0",
 		"@types/web-push": "3.3.2",
 		"@types/websocket": "1.0.5",
-		"@types/ws": "8.5.4",
-		"@typescript-eslint/eslint-plugin": "5.59.8",
-		"@typescript-eslint/parser": "5.59.8",
+		"@types/ws": "8.5.5",
+		"@typescript-eslint/eslint-plugin": "5.60.0",
+		"@typescript-eslint/parser": "5.60.0",
 		"aws-sdk-client-mock": "2.1.1",
 		"cross-env": "7.0.3",
-		"eslint": "8.41.0",
+		"eslint": "8.43.0",
 		"eslint-plugin-import": "2.27.5",
 		"execa": "6.1.0",
 		"jest": "29.5.0",
diff --git a/packages/backend/src/server/web/views/base.pug b/packages/backend/src/server/web/views/base.pug
index 1216fc73f7..74e7ae2bca 100644
--- a/packages/backend/src/server/web/views/base.pug
+++ b/packages/backend/src/server/web/views/base.pug
@@ -35,7 +35,7 @@ html
 		link(rel='prefetch' href=infoImageUrl)
 		link(rel='prefetch' href=notFoundImageUrl)
 		//- https://github.com/misskey-dev/misskey/issues/9842
-		link(rel='stylesheet' href='/assets/tabler-icons/tabler-icons.min.css?v2.21.0')
+		link(rel='stylesheet' href='/assets/tabler-icons/tabler-icons.min.css?v2.22.0')
 		link(rel='modulepreload' href=`/vite/${clientEntry.file}`)
 
 		if !config.clientManifestExists
diff --git a/packages/frontend/package.json b/packages/frontend/package.json
index 506d187901..398d6421a6 100644
--- a/packages/frontend/package.json
+++ b/packages/frontend/package.json
@@ -20,9 +20,9 @@
 		"@rollup/plugin-replace": "5.0.2",
 		"@rollup/pluginutils": "5.0.2",
 		"@syuilo/aiscript": "0.13.3",
-		"@tabler/icons-webfont": "2.21.0",
+		"@tabler/icons-webfont": "2.22.0",
 		"@vitejs/plugin-vue": "4.2.3",
-		"@vue-macros/reactivity-transform": "0.3.9",
+		"@vue-macros/reactivity-transform": "0.3.10",
 		"@vue/compiler-sfc": "3.3.4",
 		"astring": "1.8.6",
 		"autosize": "6.0.1",
@@ -35,14 +35,14 @@
 		"chartjs-chart-matrix": "2.0.1",
 		"chartjs-plugin-gradient": "0.6.1",
 		"chartjs-plugin-zoom": "2.0.1",
-		"chromatic": "6.18.0",
+		"chromatic": "6.19.9",
 		"compare-versions": "5.0.3",
-		"cropperjs": "2.0.0-beta.2",
+		"cropperjs": "2.0.0-beta.3",
 		"date-fns": "2.30.0",
 		"escape-regexp": "0.0.1",
 		"estree-walker": "^3.0.3",
 		"eventemitter3": "5.0.1",
-		"gsap": "3.11.5",
+		"gsap": "3.12.1",
 		"idb-keyval": "6.2.1",
 		"insert-text-at-cursor": "0.3.0",
 		"is-file-animated": "1.0.2",
@@ -55,10 +55,10 @@
 		"punycode": "2.3.0",
 		"querystring": "0.2.1",
 		"rndstr": "1.0.0",
-		"rollup": "3.23.0",
+		"rollup": "3.25.1",
 		"s-age": "1.1.2",
-		"sanitize-html": "2.10.0",
-		"sass": "1.62.1",
+		"sanitize-html": "2.11.0",
+		"sass": "1.63.6",
 		"seedrandom": "3.0.5",
 		"strict-event-emitter-types": "2.0.0",
 		"syuilo-password-strength": "0.0.1",
@@ -104,31 +104,31 @@
 		"@types/gulp-rename": "2.0.2",
 		"@types/matter-js": "0.18.5",
 		"@types/micromatch": "4.0.2",
-		"@types/node": "20.2.5",
+		"@types/node": "20.3.1",
 		"@types/punycode": "2.1.0",
 		"@types/sanitize-html": "2.9.0",
 		"@types/seedrandom": "3.0.5",
 		"@types/testing-library__jest-dom": "^5.14.6",
 		"@types/throttle-debounce": "5.0.0",
 		"@types/tinycolor2": "1.4.3",
-		"@types/uuid": "9.0.1",
+		"@types/uuid": "9.0.2",
 		"@types/websocket": "1.0.5",
-		"@types/ws": "8.5.4",
-		"@typescript-eslint/eslint-plugin": "5.59.8",
-		"@typescript-eslint/parser": "5.59.8",
-		"@vitest/coverage-c8": "0.31.4",
+		"@types/ws": "8.5.5",
+		"@typescript-eslint/eslint-plugin": "5.60.0",
+		"@typescript-eslint/parser": "5.60.0",
+		"@vitest/coverage-c8": "0.32.2",
 		"@vue/runtime-core": "3.3.4",
-		"acorn": "^8.8.2",
+		"acorn": "8.9.0",
 		"chokidar-cli": "3.0.0",
 		"cross-env": "7.0.3",
-		"cypress": "12.13.0",
-		"eslint": "8.41.0",
+		"cypress": "12.15.0",
+		"eslint": "8.43.0",
 		"eslint-plugin-import": "2.27.5",
-		"eslint-plugin-vue": "9.14.1",
+		"eslint-plugin-vue": "9.15.0",
 		"fast-glob": "3.2.12",
 		"happy-dom": "9.20.3",
 		"micromatch": "3.1.10",
-		"msw": "1.2.1",
+		"msw": "1.2.2",
 		"msw-storybook-addon": "1.8.0",
 		"prettier": "2.8.8",
 		"react": "18.2.0",
@@ -138,9 +138,9 @@
 		"storybook-addon-misskey-theme": "github:misskey-dev/storybook-addon-misskey-theme",
 		"summaly": "github:misskey-dev/summaly",
 		"vite-plugin-turbosnap": "1.0.2",
-		"vitest": "0.31.4",
+		"vitest": "0.32.2",
 		"vitest-fetch-mock": "0.2.2",
-		"vue-eslint-parser": "9.3.0",
-		"vue-tsc": "1.6.5"
+		"vue-eslint-parser": "9.3.1",
+		"vue-tsc": "1.8.1"
 	}
 }
diff --git a/packages/misskey-js/package.json b/packages/misskey-js/package.json
index b0a7e15051..2f9aba864e 100644
--- a/packages/misskey-js/package.json
+++ b/packages/misskey-js/package.json
@@ -20,26 +20,26 @@
 		"url": "git+https://github.com/misskey-dev/misskey.js.git"
 	},
 	"devDependencies": {
-		"@microsoft/api-extractor": "7.34.7",
+		"@microsoft/api-extractor": "7.36.0",
 		"@swc/jest": "0.2.26",
-		"@types/jest": "29.5.1",
-		"@types/node": "18.16.3",
-		"@typescript-eslint/eslint-plugin": "5.59.5",
-		"@typescript-eslint/parser": "5.59.5",
-		"eslint": "8.40.0",
+		"@types/jest": "29.5.2",
+		"@types/node": "20.3.1",
+		"@typescript-eslint/eslint-plugin": "5.60.0",
+		"@typescript-eslint/parser": "5.60.0",
+		"eslint": "8.43.0",
 		"jest": "29.5.0",
 		"jest-fetch-mock": "3.0.3",
 		"jest-websocket-mock": "2.4.0",
 		"mock-socket": "9.2.1",
 		"tsd": "0.28.1",
-		"typescript": "5.0.4"
+		"typescript": "5.1.3"
 	},
 	"files": [
 		"built"
 	],
 	"dependencies": {
 		"@swc/cli": "0.1.62",
-		"@swc/core": "1.3.56",
+		"@swc/core": "1.3.66",
 		"eventemitter3": "5.0.1",
 		"reconnecting-websocket": "4.4.0"
 	}
diff --git a/packages/sw/package.json b/packages/sw/package.json
index 96c4bfe889..3dac9e22cf 100644
--- a/packages/sw/package.json
+++ b/packages/sw/package.json
@@ -14,10 +14,10 @@
 		"misskey-js": "workspace:*"
 	},
 	"devDependencies": {
-		"@typescript-eslint/parser": "5.59.5",
+		"@typescript-eslint/parser": "5.60.0",
 		"@typescript/lib-webworker": "npm:@types/serviceworker@0.0.67",
-		"eslint": "8.40.0",
+		"eslint": "8.43.0",
 		"eslint-plugin-import": "2.27.5",
-		"typescript": "5.0.4"
+		"typescript": "5.1.3"
 	}
 }
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index f48fac3f47..fcb058828b 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -48,20 +48,20 @@ importers:
         specifier: 2.0.1
         version: 2.0.1
       '@typescript-eslint/eslint-plugin':
-        specifier: 5.59.8
-        version: 5.59.8(@typescript-eslint/parser@5.59.8)(eslint@8.41.0)(typescript@5.1.3)
+        specifier: 5.60.0
+        version: 5.60.0(@typescript-eslint/parser@5.60.0)(eslint@8.43.0)(typescript@5.1.3)
       '@typescript-eslint/parser':
-        specifier: 5.59.8
-        version: 5.59.8(eslint@8.41.0)(typescript@5.1.3)
+        specifier: 5.60.0
+        version: 5.60.0(eslint@8.43.0)(typescript@5.1.3)
       cross-env:
         specifier: 7.0.3
         version: 7.0.3
       cypress:
-        specifier: 12.13.0
-        version: 12.13.0
+        specifier: 12.15.0
+        version: 12.15.0
       eslint:
-        specifier: 8.41.0
-        version: 8.41.0
+        specifier: 8.43.0
+        version: 8.43.0
       start-server-and-test:
         specifier: 2.0.0
         version: 2.0.0
@@ -78,20 +78,20 @@ importers:
         specifier: 3.321.1
         version: 3.321.1
       '@bull-board/api':
-        specifier: 5.2.0
-        version: 5.2.0(@bull-board/ui@5.2.0)
+        specifier: 5.5.3
+        version: 5.5.3(@bull-board/ui@5.5.3)
       '@bull-board/fastify':
-        specifier: 5.2.0
-        version: 5.2.0
+        specifier: 5.5.3
+        version: 5.5.3
       '@bull-board/ui':
-        specifier: 5.2.0
-        version: 5.2.0
+        specifier: 5.5.3
+        version: 5.5.3
       '@discordapp/twemoji':
         specifier: 14.1.2
         version: 14.1.2
       '@fastify/accepts':
-        specifier: 4.1.0
-        version: 4.1.0
+        specifier: 4.2.0
+        version: 4.2.0
       '@fastify/cookie':
         specifier: 8.3.0
         version: 8.3.0
@@ -99,11 +99,11 @@ importers:
         specifier: 8.3.0
         version: 8.3.0
       '@fastify/http-proxy':
-        specifier: 9.1.0
-        version: 9.1.0(bufferutil@4.0.7)(utf-8-validate@6.0.3)
+        specifier: 9.2.1
+        version: 9.2.1(bufferutil@4.0.7)(utf-8-validate@6.0.3)
       '@fastify/multipart':
-        specifier: 7.6.0
-        version: 7.6.0
+        specifier: 7.7.0
+        version: 7.7.0
       '@fastify/static':
         specifier: 6.10.2
         version: 6.10.2
@@ -111,26 +111,26 @@ importers:
         specifier: 7.4.1
         version: 7.4.1
       '@nestjs/common':
-        specifier: 9.4.2
-        version: 9.4.2(reflect-metadata@0.1.13)(rxjs@7.8.1)
+        specifier: 10.0.3
+        version: 10.0.3(reflect-metadata@0.1.13)(rxjs@7.8.1)
       '@nestjs/core':
-        specifier: 9.4.2
-        version: 9.4.2(@nestjs/common@9.4.2)(reflect-metadata@0.1.13)(rxjs@7.8.1)
+        specifier: 10.0.3
+        version: 10.0.3(@nestjs/common@10.0.3)(reflect-metadata@0.1.13)(rxjs@7.8.1)
       '@nestjs/testing':
-        specifier: 9.4.2
-        version: 9.4.2(@nestjs/common@9.4.2)(@nestjs/core@9.4.2)
+        specifier: 10.0.3
+        version: 10.0.3(@nestjs/common@10.0.3)(@nestjs/core@10.0.3)
       '@peertube/http-signature':
         specifier: 1.7.0
         version: 1.7.0
       '@sinonjs/fake-timers':
-        specifier: 10.2.0
-        version: 10.2.0
+        specifier: 10.3.0
+        version: 10.3.0
       '@swc/cli':
         specifier: 0.1.62
-        version: 0.1.62(@swc/core@1.3.61)(chokidar@3.5.3)
+        version: 0.1.62(@swc/core@1.3.66)(chokidar@3.5.3)
       '@swc/core':
-        specifier: 1.3.61
-        version: 1.3.61
+        specifier: 1.3.66
+        version: 1.3.66
       accepts:
         specifier: 1.3.8
         version: 1.3.8
@@ -150,8 +150,8 @@ importers:
         specifier: 2.0.5
         version: 2.0.5
       bullmq:
-        specifier: 3.15.0
-        version: 3.15.0
+        specifier: 4.1.0
+        version: 4.1.0
       cacheable-lookup:
         specifier: 6.1.0
         version: 6.1.0
@@ -186,14 +186,14 @@ importers:
         specifier: 0.0.1
         version: 0.0.1
       fastify:
-        specifier: 4.17.0
-        version: 4.17.0
+        specifier: 4.18.0
+        version: 4.18.0
       feed:
         specifier: 4.2.2
         version: 4.2.2
       file-type:
-        specifier: 18.4.0
-        version: 18.4.0
+        specifier: 18.5.0
+        version: 18.5.0
       fluent-ffmpeg:
         specifier: 2.1.2
         version: 2.1.2
@@ -234,8 +234,8 @@ importers:
         specifier: 10.8.6
         version: 10.8.6
       meilisearch:
-        specifier: 0.32.5
-        version: 0.32.5
+        specifier: 0.33.0
+        version: 0.33.0
       mfm-js:
         specifier: 0.23.3
         version: 0.23.3
@@ -303,8 +303,8 @@ importers:
         specifier: 3.4.1
         version: 3.4.1
       re2:
-        specifier: 1.19.0
-        version: 1.19.0
+        specifier: 1.19.1
+        version: 1.19.1
       redis-lock:
         specifier: 0.1.4
         version: 0.1.4
@@ -327,14 +327,14 @@ importers:
         specifier: 1.1.2
         version: 1.1.2
       sanitize-html:
-        specifier: 2.10.0
-        version: 2.10.0
+        specifier: 2.11.0
+        version: 2.11.0
       seedrandom:
         specifier: 3.0.5
         version: 3.0.5
       semver:
-        specifier: 7.5.1
-        version: 7.5.1
+        specifier: 7.5.3
+        version: 7.5.3
       sharp:
         specifier: 0.32.1
         version: 0.32.1
@@ -354,8 +354,8 @@ importers:
         specifier: github:misskey-dev/summaly
         version: github.com/misskey-dev/summaly/77dd5654bb82280b38c1f50e51a771c33f3df503
       systeminformation:
-        specifier: 5.17.16
-        version: 5.17.16
+        specifier: 5.18.4
+        version: 5.18.4
       tinycolor2:
         specifier: 1.6.0
         version: 1.6.0
@@ -372,8 +372,8 @@ importers:
         specifier: 14.0.0
         version: 14.0.0
       typeorm:
-        specifier: 0.3.16
-        version: 0.3.16(ioredis@5.3.2)(pg@8.11.0)
+        specifier: 0.3.17
+        version: 0.3.17(ioredis@5.3.2)(pg@8.11.0)
       typescript:
         specifier: 5.1.3
         version: 5.1.3
@@ -390,8 +390,8 @@ importers:
         specifier: 1.1.2
         version: 1.1.2
       web-push:
-        specifier: 3.6.1
-        version: 3.6.1
+        specifier: 3.6.3
+        version: 3.6.3
       ws:
         specifier: 8.13.0
         version: 8.13.0(bufferutil@4.0.7)(utf-8-validate@6.0.3)
@@ -486,7 +486,7 @@ importers:
         version: 29.5.0
       '@swc/jest':
         specifier: 0.2.26
-        version: 0.2.26(@swc/core@1.3.61)
+        version: 0.2.26(@swc/core@1.3.66)
       '@types/accepts':
         specifier: 1.3.5
         version: 1.3.5
@@ -521,8 +521,8 @@ importers:
         specifier: 21.1.1
         version: 21.1.1
       '@types/jsonld':
-        specifier: 1.5.8
-        version: 1.5.8
+        specifier: 1.5.9
+        version: 1.5.9
       '@types/jsrsasign':
         specifier: 10.5.8
         version: 10.5.8
@@ -530,8 +530,8 @@ importers:
         specifier: 2.1.1
         version: 2.1.1
       '@types/node':
-        specifier: 20.2.5
-        version: 20.2.5
+        specifier: 20.3.1
+        version: 20.3.1
       '@types/node-fetch':
         specifier: 3.0.3
         version: 3.0.3
@@ -542,8 +542,8 @@ importers:
         specifier: 0.9.1
         version: 0.9.1
       '@types/pg':
-        specifier: 8.10.1
-        version: 8.10.1
+        specifier: 8.10.2
+        version: 8.10.2
       '@types/pug':
         specifier: 2.0.6
         version: 2.0.6
@@ -587,8 +587,8 @@ importers:
         specifier: 0.10.6
         version: 0.10.6
       '@types/uuid':
-        specifier: 9.0.1
-        version: 9.0.1
+        specifier: 9.0.2
+        version: 9.0.2
       '@types/vary':
         specifier: 1.1.0
         version: 1.1.0
@@ -599,14 +599,14 @@ importers:
         specifier: 1.0.5
         version: 1.0.5
       '@types/ws':
-        specifier: 8.5.4
-        version: 8.5.4
+        specifier: 8.5.5
+        version: 8.5.5
       '@typescript-eslint/eslint-plugin':
-        specifier: 5.59.8
-        version: 5.59.8(@typescript-eslint/parser@5.59.8)(eslint@8.41.0)(typescript@5.1.3)
+        specifier: 5.60.0
+        version: 5.60.0(@typescript-eslint/parser@5.60.0)(eslint@8.43.0)(typescript@5.1.3)
       '@typescript-eslint/parser':
-        specifier: 5.59.8
-        version: 5.59.8(eslint@8.41.0)(typescript@5.1.3)
+        specifier: 5.60.0
+        version: 5.60.0(eslint@8.43.0)(typescript@5.1.3)
       aws-sdk-client-mock:
         specifier: 2.1.1
         version: 2.1.1
@@ -614,17 +614,17 @@ importers:
         specifier: 7.0.3
         version: 7.0.3
       eslint:
-        specifier: 8.41.0
-        version: 8.41.0
+        specifier: 8.43.0
+        version: 8.43.0
       eslint-plugin-import:
         specifier: 2.27.5
-        version: 2.27.5(@typescript-eslint/parser@5.59.8)(eslint@8.41.0)
+        version: 2.27.5(@typescript-eslint/parser@5.60.0)(eslint@8.43.0)
       execa:
         specifier: 6.1.0
         version: 6.1.0
       jest:
         specifier: 29.5.0
-        version: 29.5.0(@types/node@20.2.5)
+        version: 29.5.0(@types/node@20.3.1)
       jest-mock:
         specifier: 29.5.0
         version: 29.5.0
@@ -636,28 +636,28 @@ importers:
         version: 14.1.2
       '@rollup/plugin-alias':
         specifier: 5.0.0
-        version: 5.0.0(rollup@3.23.0)
+        version: 5.0.0(rollup@3.25.1)
       '@rollup/plugin-json':
         specifier: 6.0.0
-        version: 6.0.0(rollup@3.23.0)
+        version: 6.0.0(rollup@3.25.1)
       '@rollup/plugin-replace':
         specifier: 5.0.2
-        version: 5.0.2(rollup@3.23.0)
+        version: 5.0.2(rollup@3.25.1)
       '@rollup/pluginutils':
         specifier: 5.0.2
-        version: 5.0.2(rollup@3.23.0)
+        version: 5.0.2(rollup@3.25.1)
       '@syuilo/aiscript':
         specifier: 0.13.3
         version: 0.13.3
       '@tabler/icons-webfont':
-        specifier: 2.21.0
-        version: 2.21.0
+        specifier: 2.22.0
+        version: 2.22.0
       '@vitejs/plugin-vue':
         specifier: 4.2.3
         version: 4.2.3(vite@4.3.9)(vue@3.3.4)
       '@vue-macros/reactivity-transform':
-        specifier: 0.3.9
-        version: 0.3.9(rollup@3.23.0)(vue@3.3.4)
+        specifier: 0.3.10
+        version: 0.3.10(rollup@3.25.1)(vue@3.3.4)
       '@vue/compiler-sfc':
         specifier: 3.3.4
         version: 3.3.4
@@ -675,7 +675,7 @@ importers:
         version: github.com/misskey-dev/browser-image-resizer/0227e860621e55cbed0aabe6dc601096a7748c4a
       buraha:
         specifier: github:misskey-dev/buraha
-        version: github.com/misskey-dev/buraha/92b20c1ab15c5cb5a224cf3b1ecd4f6baca12b7c
+        version: github.com/misskey-dev/buraha/822d4be21126156c3e1827a771444b3fceb6be58
       canvas-confetti:
         specifier: 1.6.0
         version: 1.6.0
@@ -695,14 +695,14 @@ importers:
         specifier: 2.0.1
         version: 2.0.1(chart.js@4.3.0)
       chromatic:
-        specifier: 6.18.0
-        version: 6.18.0
+        specifier: 6.19.9
+        version: 6.19.9
       compare-versions:
         specifier: 5.0.3
         version: 5.0.3
       cropperjs:
-        specifier: 2.0.0-beta.2
-        version: 2.0.0-beta.2
+        specifier: 2.0.0-beta.3
+        version: 2.0.0-beta.3
       date-fns:
         specifier: 2.30.0
         version: 2.30.0
@@ -716,8 +716,8 @@ importers:
         specifier: 5.0.1
         version: 5.0.1
       gsap:
-        specifier: 3.11.5
-        version: 3.11.5
+        specifier: 3.12.1
+        version: 3.12.1
       idb-keyval:
         specifier: 6.2.1
         version: 6.2.1
@@ -755,17 +755,17 @@ importers:
         specifier: 1.0.0
         version: 1.0.0
       rollup:
-        specifier: 3.23.0
-        version: 3.23.0
+        specifier: 3.25.1
+        version: 3.25.1
       s-age:
         specifier: 1.1.2
         version: 1.1.2
       sanitize-html:
-        specifier: 2.10.0
-        version: 2.10.0
+        specifier: 2.11.0
+        version: 2.11.0
       sass:
-        specifier: 1.62.1
-        version: 1.62.1
+        specifier: 1.63.6
+        version: 1.63.6
       seedrandom:
         specifier: 3.0.5
         version: 3.0.5
@@ -807,7 +807,7 @@ importers:
         version: 1.8.0
       vite:
         specifier: 4.3.9
-        version: 4.3.9(@types/node@20.2.5)(sass@1.62.1)
+        version: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
       vue:
         specifier: 3.3.4
         version: 3.3.4
@@ -897,8 +897,8 @@ importers:
         specifier: 4.0.2
         version: 4.0.2
       '@types/node':
-        specifier: 20.2.5
-        version: 20.2.5
+        specifier: 20.3.1
+        version: 20.3.1
       '@types/punycode':
         specifier: 2.1.0
         version: 2.1.0
@@ -918,29 +918,29 @@ importers:
         specifier: 1.4.3
         version: 1.4.3
       '@types/uuid':
-        specifier: 9.0.1
-        version: 9.0.1
+        specifier: 9.0.2
+        version: 9.0.2
       '@types/websocket':
         specifier: 1.0.5
         version: 1.0.5
       '@types/ws':
-        specifier: 8.5.4
-        version: 8.5.4
+        specifier: 8.5.5
+        version: 8.5.5
       '@typescript-eslint/eslint-plugin':
-        specifier: 5.59.8
-        version: 5.59.8(@typescript-eslint/parser@5.59.8)(eslint@8.41.0)(typescript@5.1.3)
+        specifier: 5.60.0
+        version: 5.60.0(@typescript-eslint/parser@5.60.0)(eslint@8.43.0)(typescript@5.1.3)
       '@typescript-eslint/parser':
-        specifier: 5.59.8
-        version: 5.59.8(eslint@8.41.0)(typescript@5.1.3)
+        specifier: 5.60.0
+        version: 5.60.0(eslint@8.43.0)(typescript@5.1.3)
       '@vitest/coverage-c8':
-        specifier: 0.31.4
-        version: 0.31.4(vitest@0.31.4)
+        specifier: 0.32.2
+        version: 0.32.2(vitest@0.32.2)
       '@vue/runtime-core':
         specifier: 3.3.4
         version: 3.3.4
       acorn:
-        specifier: ^8.8.2
-        version: 8.8.2
+        specifier: 8.9.0
+        version: 8.9.0
       chokidar-cli:
         specifier: 3.0.0
         version: 3.0.0
@@ -948,17 +948,17 @@ importers:
         specifier: 7.0.3
         version: 7.0.3
       cypress:
-        specifier: 12.13.0
-        version: 12.13.0
+        specifier: 12.15.0
+        version: 12.15.0
       eslint:
-        specifier: 8.41.0
-        version: 8.41.0
+        specifier: 8.43.0
+        version: 8.43.0
       eslint-plugin-import:
         specifier: 2.27.5
-        version: 2.27.5(@typescript-eslint/parser@5.59.8)(eslint@8.41.0)
+        version: 2.27.5(@typescript-eslint/parser@5.60.0)(eslint@8.43.0)
       eslint-plugin-vue:
-        specifier: 9.14.1
-        version: 9.14.1(eslint@8.41.0)
+        specifier: 9.15.0
+        version: 9.15.0(eslint@8.43.0)
       fast-glob:
         specifier: 3.2.12
         version: 3.2.12
@@ -969,11 +969,11 @@ importers:
         specifier: 3.1.10
         version: 3.1.10
       msw:
-        specifier: 1.2.1
-        version: 1.2.1(typescript@5.1.3)
+        specifier: 1.2.2
+        version: 1.2.2(typescript@5.1.3)
       msw-storybook-addon:
         specifier: 1.8.0
-        version: 1.8.0(msw@1.2.1)
+        version: 1.8.0(msw@1.2.2)
       prettier:
         specifier: 2.8.8
         version: 2.8.8
@@ -999,26 +999,26 @@ importers:
         specifier: 1.0.2
         version: 1.0.2
       vitest:
-        specifier: 0.31.4
-        version: 0.31.4(happy-dom@9.20.3)(sass@1.62.1)
+        specifier: 0.32.2
+        version: 0.32.2(happy-dom@9.20.3)(sass@1.63.6)
       vitest-fetch-mock:
         specifier: 0.2.2
-        version: 0.2.2(vitest@0.31.4)
+        version: 0.2.2(vitest@0.32.2)
       vue-eslint-parser:
-        specifier: 9.3.0
-        version: 9.3.0(eslint@8.41.0)
+        specifier: 9.3.1
+        version: 9.3.1(eslint@8.43.0)
       vue-tsc:
-        specifier: 1.6.5
-        version: 1.6.5(typescript@5.1.3)
+        specifier: 1.8.1
+        version: 1.8.1(typescript@5.1.3)
 
   packages/misskey-js:
     dependencies:
       '@swc/cli':
         specifier: 0.1.62
-        version: 0.1.62(@swc/core@1.3.61)(chokidar@3.5.3)
+        version: 0.1.62(@swc/core@1.3.66)(chokidar@3.5.3)
       '@swc/core':
-        specifier: 1.3.56
-        version: 1.3.56
+        specifier: 1.3.66
+        version: 1.3.66
       eventemitter3:
         specifier: 5.0.1
         version: 5.0.1
@@ -1027,29 +1027,29 @@ importers:
         version: 4.4.0
     devDependencies:
       '@microsoft/api-extractor':
-        specifier: 7.34.7
-        version: 7.34.7(@types/node@18.16.3)
+        specifier: 7.36.0
+        version: 7.36.0(@types/node@20.3.1)
       '@swc/jest':
         specifier: 0.2.26
-        version: 0.2.26(@swc/core@1.3.56)
+        version: 0.2.26(@swc/core@1.3.66)
       '@types/jest':
-        specifier: 29.5.1
-        version: 29.5.1
+        specifier: 29.5.2
+        version: 29.5.2
       '@types/node':
-        specifier: 18.16.3
-        version: 18.16.3
+        specifier: 20.3.1
+        version: 20.3.1
       '@typescript-eslint/eslint-plugin':
-        specifier: 5.59.5
-        version: 5.59.5(@typescript-eslint/parser@5.59.5)(eslint@8.40.0)(typescript@5.0.4)
+        specifier: 5.60.0
+        version: 5.60.0(@typescript-eslint/parser@5.60.0)(eslint@8.43.0)(typescript@5.1.3)
       '@typescript-eslint/parser':
-        specifier: 5.59.5
-        version: 5.59.5(eslint@8.40.0)(typescript@5.0.4)
+        specifier: 5.60.0
+        version: 5.60.0(eslint@8.43.0)(typescript@5.1.3)
       eslint:
-        specifier: 8.40.0
-        version: 8.40.0
+        specifier: 8.43.0
+        version: 8.43.0
       jest:
         specifier: 29.5.0
-        version: 29.5.0(@types/node@18.16.3)
+        version: 29.5.0(@types/node@20.3.1)
       jest-fetch-mock:
         specifier: 3.0.3
         version: 3.0.3
@@ -1063,8 +1063,8 @@ importers:
         specifier: 0.28.1
         version: 0.28.1
       typescript:
-        specifier: 5.0.4
-        version: 5.0.4
+        specifier: 5.1.3
+        version: 5.1.3
 
   packages/sw:
     dependencies:
@@ -1079,20 +1079,20 @@ importers:
         version: link:../misskey-js
     devDependencies:
       '@typescript-eslint/parser':
-        specifier: 5.59.5
-        version: 5.59.5(eslint@8.40.0)(typescript@5.0.4)
+        specifier: 5.60.0
+        version: 5.60.0(eslint@8.43.0)(typescript@5.1.3)
       '@typescript/lib-webworker':
         specifier: npm:@types/serviceworker@0.0.67
         version: /@types/serviceworker@0.0.67
       eslint:
-        specifier: 8.40.0
-        version: 8.40.0
+        specifier: 8.43.0
+        version: 8.43.0
       eslint-plugin-import:
         specifier: 2.27.5
-        version: 2.27.5(@typescript-eslint/parser@5.59.5)(eslint@8.40.0)
+        version: 2.27.5(@typescript-eslint/parser@5.60.0)(eslint@8.43.0)
       typescript:
-        specifier: 5.0.4
-        version: 5.0.4
+        specifier: 5.1.3
+        version: 5.1.3
 
 packages:
 
@@ -1108,12 +1108,6 @@ packages:
       '@jridgewell/trace-mapping': 0.3.17
     dev: true
 
-  /@arcanis/slice-ansi@1.1.1:
-    resolution: {integrity: sha512-xguP2WR2Dv0gQ7Ykbdb7BNCnPnIPB94uTi0Z2NvkRBEnhbwjOQ7QyQKJXrVQg4qDpiD9hA5l5cCwy/z2OXgc3w==}
-    dependencies:
-      grapheme-splitter: 1.0.4
-    dev: false
-
   /@aw-web-design/x-default-browser@1.4.88:
     resolution: {integrity: sha512-AkEmF0wcwYC2QkhK703Y83fxWARttIWXDmQN8+cof8FmFZ5BRhnNXGymeb1S73bOCLfWjYELxtujL56idCN/XA==}
     hasBin: true
@@ -1302,7 +1296,7 @@ packages:
       '@aws-sdk/util-user-agent-browser': 3.310.0
       '@aws-sdk/util-user-agent-node': 3.310.0
       '@aws-sdk/util-utf8': 3.310.0
-      tslib: 2.5.2
+      tslib: 2.5.3
     transitivePeerDependencies:
       - aws-crt
     dev: false
@@ -1342,7 +1336,7 @@ packages:
       '@aws-sdk/util-user-agent-browser': 3.310.0
       '@aws-sdk/util-user-agent-node': 3.310.0
       '@aws-sdk/util-utf8': 3.310.0
-      tslib: 2.5.2
+      tslib: 2.5.3
     transitivePeerDependencies:
       - aws-crt
     dev: false
@@ -1495,7 +1489,7 @@ packages:
       '@aws-crypto/crc32': 3.0.0
       '@aws-sdk/types': 3.310.0
       '@aws-sdk/util-hex-encoding': 3.310.0
-      tslib: 2.5.2
+      tslib: 2.5.3
     dev: false
 
   /@aws-sdk/eventstream-serde-browser@3.310.0:
@@ -1885,7 +1879,7 @@ packages:
       '@aws-sdk/property-provider': 3.310.0
       '@aws-sdk/shared-ini-file-loader': 3.310.0
       '@aws-sdk/types': 3.310.0
-      tslib: 2.5.2
+      tslib: 2.5.3
     transitivePeerDependencies:
       - aws-crt
     dev: false
@@ -2092,6 +2086,7 @@ packages:
     engines: {node: '>=6.9.0'}
     dependencies:
       '@babel/highlight': 7.18.6
+    dev: true
 
   /@babel/compat-data@7.22.3:
     resolution: {integrity: sha512-aNtko9OPOwVESUFp3MZfD8Uzxl7JzSeJpd7npIoxCasU37PFbAQRpKglkaKwlHOyeJdrREpo8TW8ldrkYWwvIQ==}
@@ -2152,6 +2147,7 @@ packages:
       '@jridgewell/gen-mapping': 0.3.2
       '@jridgewell/trace-mapping': 0.3.17
       jsesc: 2.5.2
+    dev: true
 
   /@babel/generator@7.22.3:
     resolution: {integrity: sha512-C17MW4wlk//ES/CJDL51kPNwl+qiBQyN7b9SKyVp11BLGFeSPoVaHrv+MNt8jwQFhQWowW88z1eeBx3pFz9v8A==}
@@ -2161,6 +2157,7 @@ packages:
       '@jridgewell/gen-mapping': 0.3.2
       '@jridgewell/trace-mapping': 0.3.17
       jsesc: 2.5.2
+    dev: true
 
   /@babel/helper-annotate-as-pure@7.18.6:
     resolution: {integrity: sha512-duORpUiYrEpzKIop6iNbjnwKLAKnJ47csTyRACyEmWj0QdUrm5aqNJGHSSEQSUAvNW0ojX0dOmK9dZduvkfeXA==}
@@ -2300,6 +2297,7 @@ packages:
   /@babel/helper-environment-visitor@7.22.1:
     resolution: {integrity: sha512-Z2tgopurB/kTbidvzeBrc2To3PUP/9i5MUe+fU6QJCQDyPwSH2oRapkLw3KGECDYSjhQZCNxEvNvZlLw8JjGwA==}
     engines: {node: '>=6.9.0'}
+    dev: true
 
   /@babel/helper-explode-assignable-expression@7.18.6:
     resolution: {integrity: sha512-eyAYAsQmB80jNfg4baAtLeWAQHfHFiR483rzFK+BhETlGZaQC9bsfrugfXDCbRHLQbIA7U5NxhhOxN7p/dWIcg==}
@@ -2314,12 +2312,14 @@ packages:
     dependencies:
       '@babel/template': 7.21.9
       '@babel/types': 7.22.4
+    dev: true
 
   /@babel/helper-hoist-variables@7.18.6:
     resolution: {integrity: sha512-UlJQPkFqFULIcyW5sbzgbkxn2FKRgwWiRexcuaR8RNJRy8+LLveqPjwZV/bwrLZCN0eUHD/x8D0heK1ozuoo6Q==}
     engines: {node: '>=6.9.0'}
     dependencies:
       '@babel/types': 7.22.4
+    dev: true
 
   /@babel/helper-member-expression-to-functions@7.21.0:
     resolution: {integrity: sha512-Muu8cdZwNN6mRRNG6lAYErJ5X3bRevgYR2O8wN0yn7jJSnGDu6eG59RfT29JHxGUovyfrh6Pj0XzmR7drNVL3Q==}
@@ -2426,6 +2426,7 @@ packages:
     engines: {node: '>=6.9.0'}
     dependencies:
       '@babel/types': 7.22.4
+    dev: true
 
   /@babel/helper-string-parser@7.21.5:
     resolution: {integrity: sha512-5pTUx3hAJaZIdW99sJ6ZUUgWq/Y+Hja7TowEnLNMm1VivRgZQL3vpBY3qUACVsvw+yQU6+YgfBVmcbLaZtrA1w==}
@@ -2470,6 +2471,7 @@ packages:
       '@babel/helper-validator-identifier': 7.19.1
       chalk: 2.4.2
       js-tokens: 4.0.0
+    dev: true
 
   /@babel/parser@7.21.8:
     resolution: {integrity: sha512-6zavDGdzG3gUqAdWvlLFfk+36RilI+Pwyuuh7HItyeScCWP3k6i8vKclAQ0bM/0y/Kz/xiwvxhMv9MgTJP5gmA==}
@@ -2484,6 +2486,7 @@ packages:
     hasBin: true
     dependencies:
       '@babel/types': 7.22.4
+    dev: true
 
   /@babel/parser@7.22.4:
     resolution: {integrity: sha512-VLLsx06XkEYqBtE5YGPwfSGwfrjnyPP5oiGty3S8pQLFDFLaS8VwWSIxkTXpcvr5zeYLE6+MBNl2npl/YnfofA==}
@@ -4292,6 +4295,7 @@ packages:
       '@babel/code-frame': 7.21.4
       '@babel/parser': 7.22.4
       '@babel/types': 7.22.4
+    dev: true
 
   /@babel/traverse@7.21.3:
     resolution: {integrity: sha512-XLyopNeaTancVitYZe2MlUEvgKb6YVVPXzofHgqHijCImG33b/uTurMS488ht/Hbsb2XK3U2BnSTxKVNGV3nGQ==}
@@ -4309,6 +4313,7 @@ packages:
       globals: 11.12.0
     transitivePeerDependencies:
       - supports-color
+    dev: true
 
   /@babel/traverse@7.22.4:
     resolution: {integrity: sha512-Tn1pDsjIcI+JcLKq1AVlZEr4226gpuAQTsLMorsYg9tuS/kG7nuwwJ4AB8jfQuEgb/COBwR/DqJxmoiYFu5/rQ==}
@@ -4335,6 +4340,7 @@ packages:
       '@babel/helper-string-parser': 7.21.5
       '@babel/helper-validator-identifier': 7.19.1
       to-fast-properties: 2.0.0
+    dev: true
 
   /@babel/types@7.22.4:
     resolution: {integrity: sha512-Tx9x3UBHTTsMSW85WB2kphxYQVvrZ/t1FxD88IpSgIjiUJlCm9z+xWIDwyo1vffTwSqteqyznB8ZE9vYYk16zA==}
@@ -4352,29 +4358,29 @@ packages:
     resolution: {integrity: sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw==}
     dev: true
 
-  /@bull-board/api@5.2.0(@bull-board/ui@5.2.0):
-    resolution: {integrity: sha512-1HGF2EF/4zI3+Cj414nQzwFprLXOJTlVdqXUf5UEBS4HtYafWv93mGIwkrD8S4Bpz4VSvM87adF6tQPJ7Ewt+w==}
+  /@bull-board/api@5.5.3(@bull-board/ui@5.5.3):
+    resolution: {integrity: sha512-v3q0NmXPIkXwN4UKbrbbh/uQ+r9P00hN0f6QD3dmNBE/AYG2QD3MO4i4gxvrsjvEL7uKatXWwgAfVwKIXJAgAQ==}
     peerDependencies:
-      '@bull-board/ui': 5.2.0
+      '@bull-board/ui': 5.5.3
     dependencies:
-      '@bull-board/ui': 5.2.0
+      '@bull-board/ui': 5.5.3
       redis-info: 3.1.0
     dev: false
 
-  /@bull-board/fastify@5.2.0:
-    resolution: {integrity: sha512-tvvgCAxFoiogqmAhxUiAOV/rXBVXlmg7JO3jkePA778O/YSiE7nrwwjiiLbLNuIYLZfdoYnRK4bIDmLeg1nK2A==}
+  /@bull-board/fastify@5.5.3:
+    resolution: {integrity: sha512-2uGepa/6HO40YNWyMMc8yWOTzD/p5ftCATlra/z7tfx97nE2lxuX/57ukjf7QmNtCBf14WRRKSllRT4w9YSmCA==}
     dependencies:
-      '@bull-board/api': 5.2.0(@bull-board/ui@5.2.0)
-      '@bull-board/ui': 5.2.0
+      '@bull-board/api': 5.5.3(@bull-board/ui@5.5.3)
+      '@bull-board/ui': 5.5.3
       '@fastify/static': 6.10.2
       '@fastify/view': 7.4.1
       ejs: 3.1.8
     dev: false
 
-  /@bull-board/ui@5.2.0:
-    resolution: {integrity: sha512-f2sgs7AjOVch7tFhbmlVCkhZjJWboxwNxWEfAsIUd1WidUC+Ef5J02tpQvu7apzRtu5zcn8IiJtI5HFO6oKaCA==}
+  /@bull-board/ui@5.5.3:
+    resolution: {integrity: sha512-Ow373Jtjm249shNi8gdQMawe+lcTrqh6ZGe7duD1+mJqBDDdqtrjWre4/aQenDBK1eFSIXtGYUfvs0UKkNQMYQ==}
     dependencies:
-      '@bull-board/api': 5.2.0(@bull-board/ui@5.2.0)
+      '@bull-board/api': 5.5.3(@bull-board/ui@5.5.3)
     dev: false
 
   /@canvas/image-data@1.0.0:
@@ -4392,92 +4398,92 @@ packages:
     dev: true
     optional: true
 
-  /@cropper/element-canvas@2.0.0-beta.2:
-    resolution: {integrity: sha512-LZcnMwv7M3ZxUKX9YrYGxqbf8YsYfeIUFREaB/IkKsm7E7ASaDrrjdc996QYMjdjUNcWdJjxhsoucPNEvl/DXA==}
+  /@cropper/element-canvas@2.0.0-beta.3:
+    resolution: {integrity: sha512-G4KqpZHAqb2PNY63lt7MxSIXQhYrQUWImDmsQYrXSTVYC5yrMLlk5bT9oEaSTjQZnV4x5EaujFM+gx6lWh/5sg==}
     dependencies:
-      '@cropper/element': 2.0.0-beta.2
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/element': 2.0.0-beta.3
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
-  /@cropper/element-crosshair@2.0.0-beta.2:
-    resolution: {integrity: sha512-kBxZ2zZ7uR7XlQcnUbudq7562XwtTOqbGNYg5VWem/ukcAAKwYmPlapNlv7n228DSUGEz5FxKW8GSwLucJlQ0Q==}
+  /@cropper/element-crosshair@2.0.0-beta.3:
+    resolution: {integrity: sha512-SfrzZjO+x7ND/CgAclfwDQ9T/nTlZTKsLtM+dDXfjJQjuqreMaWaLD23isB1kh8H7iqjz1g+VE2ZsdiLB932ww==}
     dependencies:
-      '@cropper/element': 2.0.0-beta.2
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/element': 2.0.0-beta.3
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
-  /@cropper/element-grid@2.0.0-beta.2:
-    resolution: {integrity: sha512-rWMOjlj+eq9L2oxAthNYdGxbV3sYyV+tra6VAuooZl+RbdQZ9XCnG0Pitb/RfgPZb860ia0q8biE5zEq4Uc8fA==}
+  /@cropper/element-grid@2.0.0-beta.3:
+    resolution: {integrity: sha512-/U1/sNcJ9TKcUD7N+yHJqxRfZcW15XHz63LYMLaWQ7Cnnq2uYopopJUqtTiAdIoCh6mwoIWdYvLZ1Vhr6XKJBg==}
     dependencies:
-      '@cropper/element': 2.0.0-beta.2
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/element': 2.0.0-beta.3
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
-  /@cropper/element-handle@2.0.0-beta.2:
-    resolution: {integrity: sha512-IAFyqldnB57ZGzvf3VuE7Y9UAaq9IMmun15v17cAWX1q4ZCVqdFrugAWpRF+V5WgHBL2doxHUOQlfy7LznzRmg==}
+  /@cropper/element-handle@2.0.0-beta.3:
+    resolution: {integrity: sha512-bjxZfX0rqj4RsTBGxJ1WcxDya1/25dKe9j4+YRZFyASQUOPuUrqVOpWKQcGaQ0PeN+wfwLo3422vjaGSXNA+Pg==}
     dependencies:
-      '@cropper/element': 2.0.0-beta.2
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/element': 2.0.0-beta.3
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
-  /@cropper/element-image@2.0.0-beta.2:
-    resolution: {integrity: sha512-FgYb+GfcxdewH6VKgw6Ltws8fw3TSP8d0HMH/WZubBC2w/NNAvp92EonwgjDoTLEFFJKbj5P2aKTFY0aO70R0Q==}
+  /@cropper/element-image@2.0.0-beta.3:
+    resolution: {integrity: sha512-1VjqaJG+IxPDkvEUvnKAfR12zK8fx+C6+ZsC5T4986KLtpltmqccaYiupgGXX8CVHrVyaW5ncBvOXSTGowiC7Q==}
     dependencies:
-      '@cropper/element': 2.0.0-beta.2
-      '@cropper/element-canvas': 2.0.0-beta.2
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/element': 2.0.0-beta.3
+      '@cropper/element-canvas': 2.0.0-beta.3
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
-  /@cropper/element-selection@2.0.0-beta.2:
-    resolution: {integrity: sha512-O/fxpJe/WB5H+mELSVfp4tOAAa7yMVa+wn35DCRxaDPb/1Um55E7OT1G3puAL9Elm7NFA/CCMYuHohl9emE25A==}
+  /@cropper/element-selection@2.0.0-beta.3:
+    resolution: {integrity: sha512-FjcNwUaV5/KzQROoaoNZzOpeRe92PCd8PPTgfl4/b2rGgpYvGcjwpjei5HRsF+uaDJwR2f1MOK8L+3ZkAUw18Q==}
     dependencies:
-      '@cropper/element': 2.0.0-beta.2
-      '@cropper/element-canvas': 2.0.0-beta.2
-      '@cropper/element-image': 2.0.0-beta.2
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/element': 2.0.0-beta.3
+      '@cropper/element-canvas': 2.0.0-beta.3
+      '@cropper/element-image': 2.0.0-beta.3
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
-  /@cropper/element-shade@2.0.0-beta.2:
-    resolution: {integrity: sha512-aY5RP2ygteq51ZDU3+rAj+f+0hSgEf+vRAdJ1YO2bJ1n25TpOaz2klO5COdHxn3unLVjYK97khIZGs7ClbV0rQ==}
+  /@cropper/element-shade@2.0.0-beta.3:
+    resolution: {integrity: sha512-WCmGYbmewIF49GUeJyXCXZUBwmLsu7B+G22o5FObhtxoY8pF7mp1SclIZdJU5KfvGFFOzXKHJg4yx1wO9IAfvQ==}
     dependencies:
-      '@cropper/element': 2.0.0-beta.2
-      '@cropper/element-canvas': 2.0.0-beta.2
-      '@cropper/element-selection': 2.0.0-beta.2
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/element': 2.0.0-beta.3
+      '@cropper/element-canvas': 2.0.0-beta.3
+      '@cropper/element-selection': 2.0.0-beta.3
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
-  /@cropper/element-viewer@2.0.0-beta.2:
-    resolution: {integrity: sha512-/2BhLFr2Ti5LnRvcIlLlR3NDSF3x9w9BvYukFbnCxoTLIbGvwM02YQV2Qx+al8C0mBoW0ab6uF5ykl6W8i9WkQ==}
+  /@cropper/element-viewer@2.0.0-beta.3:
+    resolution: {integrity: sha512-A2yh8ULbxuykJHVvcG3eI81VX2ug/IklDuOAzCP4yRMGSvGb9eK0BQDkOButoViwM2FtleCf2blXPuXjzD1OMA==}
     dependencies:
-      '@cropper/element': 2.0.0-beta.2
-      '@cropper/element-canvas': 2.0.0-beta.2
-      '@cropper/element-image': 2.0.0-beta.2
-      '@cropper/element-selection': 2.0.0-beta.2
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/element': 2.0.0-beta.3
+      '@cropper/element-canvas': 2.0.0-beta.3
+      '@cropper/element-image': 2.0.0-beta.3
+      '@cropper/element-selection': 2.0.0-beta.3
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
-  /@cropper/element@2.0.0-beta.2:
-    resolution: {integrity: sha512-i3wfelk5d4MLNgAcQpRa/jOaxWAcDLRAUkiHmU6CMl7xvOAD/4TFQGB3qSpzgx3NK4hUDLn80/gp7gM2nvrBWg==}
+  /@cropper/element@2.0.0-beta.3:
+    resolution: {integrity: sha512-Ta1QPx6uqO4WtlvWbQanKSdTi0NptfnSk4h93TSk/GTKYTUI6Qa1g5C+2ibdsomcD/bVTTY6cbuGMFfM8E8zQQ==}
     dependencies:
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
-  /@cropper/elements@2.0.0-beta.2:
-    resolution: {integrity: sha512-l08CmeOvLJ8XLJ95OQ+kSHSbf7+pHcsu3pvQYjustbrUj0H1vzBiWT8VygPjkCUMoVIfsBpYmBNpWVGJvjoy2Q==}
+  /@cropper/elements@2.0.0-beta.3:
+    resolution: {integrity: sha512-oHRnhrFN/S2vadX1/ogaoZQuPUwUxYRoZ+BZjPUxr0kdX4SwumU0pMD2hxVMbveTl0zxFc0S3HdqXx8kcHGPtg==}
     dependencies:
-      '@cropper/element': 2.0.0-beta.2
-      '@cropper/element-canvas': 2.0.0-beta.2
-      '@cropper/element-crosshair': 2.0.0-beta.2
-      '@cropper/element-grid': 2.0.0-beta.2
-      '@cropper/element-handle': 2.0.0-beta.2
-      '@cropper/element-image': 2.0.0-beta.2
-      '@cropper/element-selection': 2.0.0-beta.2
-      '@cropper/element-shade': 2.0.0-beta.2
-      '@cropper/element-viewer': 2.0.0-beta.2
+      '@cropper/element': 2.0.0-beta.3
+      '@cropper/element-canvas': 2.0.0-beta.3
+      '@cropper/element-crosshair': 2.0.0-beta.3
+      '@cropper/element-grid': 2.0.0-beta.3
+      '@cropper/element-handle': 2.0.0-beta.3
+      '@cropper/element-image': 2.0.0-beta.3
+      '@cropper/element-selection': 2.0.0-beta.3
+      '@cropper/element-shade': 2.0.0-beta.3
+      '@cropper/element-viewer': 2.0.0-beta.3
     dev: false
 
-  /@cropper/utils@2.0.0-beta.2:
-    resolution: {integrity: sha512-RJu5IWzH6vcygwLsx9KEqzwjnEqApPkSFViMzxCRbe0IuAXt2ZlSUmYKgLFZY+YJIdaZ+/P7PwiUcZ7GYH3Msw==}
+  /@cropper/utils@2.0.0-beta.3:
+    resolution: {integrity: sha512-3oBwFN2DZiqfKzkB+fpAa+LV2izRUpbH0MS427p8rgMb7EEOP/UFaKeq/P/Ovs3dhLbiA48aLiV6GmX9piEmlw==}
     dev: false
 
   /@cypress/request@2.88.11:
@@ -4536,6 +4542,7 @@ packages:
   /@discoveryjs/json-ext@0.5.7:
     resolution: {integrity: sha512-dBVuXR082gk3jsFp7Rd/JI4kytwGHecnCoTtXFb7DB6CNHp4rg5k1bhg0nWdLGLnOV71lmDzGQaLMy8iPLY0pw==}
     engines: {node: '>=10.0.0'}
+    dev: true
 
   /@emotion/use-insertion-effect-with-fallbacks@1.0.0(react@18.2.0):
     resolution: {integrity: sha512-1eEgUGmkaljiBnRMTdksDV1W4kUnmwgp7X9G8B++9GYwl1lUdqSndSriIrTJ0N7LQaoauY9JJ2yhiOYK5+NI4A==}
@@ -4721,23 +4728,13 @@ packages:
     requiresBuild: true
     optional: true
 
-  /@eslint-community/eslint-utils@4.4.0(eslint@8.40.0):
+  /@eslint-community/eslint-utils@4.4.0(eslint@8.43.0):
     resolution: {integrity: sha512-1/sA4dwrzBAyeUoQ6oxahHKmrZvsnLCg4RfxW3ZFGGmQkSNQPFNLV9CUEFQP1x9EYXHTo5p6xdhZM1Ne9p/AfA==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
       eslint: ^6.0.0 || ^7.0.0 || >=8.0.0
     dependencies:
-      eslint: 8.40.0
-      eslint-visitor-keys: 3.4.1
-    dev: true
-
-  /@eslint-community/eslint-utils@4.4.0(eslint@8.41.0):
-    resolution: {integrity: sha512-1/sA4dwrzBAyeUoQ6oxahHKmrZvsnLCg4RfxW3ZFGGmQkSNQPFNLV9CUEFQP1x9EYXHTo5p6xdhZM1Ne9p/AfA==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    peerDependencies:
-      eslint: ^6.0.0 || ^7.0.0 || >=8.0.0
-    dependencies:
-      eslint: 8.41.0
+      eslint: 8.43.0
       eslint-visitor-keys: 3.4.1
     dev: true
 
@@ -4763,13 +4760,8 @@ packages:
       - supports-color
     dev: true
 
-  /@eslint/js@8.40.0:
-    resolution: {integrity: sha512-ElyB54bJIhXQYVKjDSvCkPO1iU1tSAeVQJbllWJq1XQSmmA4dgFk8CbiBGpiOPxleE48vDogxCtmMYku4HSVLA==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    dev: true
-
-  /@eslint/js@8.41.0:
-    resolution: {integrity: sha512-LxcyMGxwmTh2lY9FwHPGWOHmYFCZvbrFCBZL4FzSSsxsRPuhrYUg/49/0KDfW8tnIEaEHtfmn6+NPN+1DqaNmA==}
+  /@eslint/js@8.43.0:
+    resolution: {integrity: sha512-s2UHCoiXfxMvmfzqoN+vrQ84ahUSYde9qNO1MdxmoEhyHWsfmwOpFlwYV+ePJEVc7gFnATGUi376WowX1N7tFg==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     dev: true
 
@@ -4782,8 +4774,8 @@ packages:
     engines: {node: '>=14'}
     dev: false
 
-  /@fastify/accepts@4.1.0:
-    resolution: {integrity: sha512-oURKietAW2iXxtQCS8oaTSMHaJ0PQ7M+NymOr8RgX65fOi+xGWsZ9Fu6hep/9oyeOUD0PA07Ofg03g9f+GvHLg==}
+  /@fastify/accepts@4.2.0:
+    resolution: {integrity: sha512-nM2OsxJvdBZOcpMqtbolW7RMB2bn/L1PDZ03+zVlC+/JVdBEW+ufWEKmtsMVzelU5TwyTc/+X/CRr/98JfE9mQ==}
     dependencies:
       accepts: 1.3.8
       fastify-plugin: 4.5.0
@@ -4832,8 +4824,8 @@ packages:
       fast-json-stringify: 5.7.0
     dev: false
 
-  /@fastify/http-proxy@9.1.0(bufferutil@4.0.7)(utf-8-validate@6.0.3):
-    resolution: {integrity: sha512-vgHCTDKOqLB437zQJiLWFFnsrYfFZ6Lfwu/xXQoKqRUKIPDt+xG6LBRtf8s5MNqfFVoTE7kw1U/0qdRGDsMp4Q==}
+  /@fastify/http-proxy@9.2.1(bufferutil@4.0.7)(utf-8-validate@6.0.3):
+    resolution: {integrity: sha512-SSxcdrDQQA2PYYBCK+2I+w83QEbMt1s5bsKEERiMG1jcraQulTW3t/Wkje+RWJNNblDhABnhdKXUTbDuA/EIXA==}
     dependencies:
       '@fastify/reply-from': 9.0.1
       fastify-plugin: 4.5.0
@@ -4843,17 +4835,20 @@ packages:
       - utf-8-validate
     dev: false
 
-  /@fastify/multipart@7.6.0:
-    resolution: {integrity: sha512-mQoz0SMxk1WAYLYvQypoj3GYhCbmhnFl2LdleTzKQ4HgPfhVcMT014uln2wgzRh2y+gL74b/+j0mMVgvOKpqpQ==}
+  /@fastify/multipart@7.7.0:
+    resolution: {integrity: sha512-lE5v6+MVbLYmPL8yUHrvyezEOLQbZulEPL8itwGqPbNxL2pWdAN1HWEZ7f3VdwyR6wmQdOcpfZ0zdCU4BbWKzw==}
     dependencies:
       '@fastify/busboy': 1.1.0
       '@fastify/deepmerge': 1.3.0
       '@fastify/error': 3.2.0
+      '@fastify/swagger': 8.6.0
+      '@fastify/swagger-ui': 1.9.0
       end-of-stream: 1.4.4
       fastify-plugin: 4.5.0
-      hexoid: 1.0.0
       secure-json-parse: 2.7.0
       stream-wormhole: 1.1.0
+    transitivePeerDependencies:
+      - supports-color
     dev: false
 
   /@fastify/reply-from@9.0.1:
@@ -4865,7 +4860,7 @@ packages:
       fastify-plugin: 4.5.0
       pump: 3.0.0
       tiny-lru: 10.0.1
-      undici: 5.21.0
+      undici: 5.22.1
     dev: false
 
   /@fastify/send@2.0.1:
@@ -4890,6 +4885,28 @@ packages:
       readable-stream: 4.3.0
     dev: false
 
+  /@fastify/swagger-ui@1.9.0:
+    resolution: {integrity: sha512-7RTq2bI2cg4k6WsY69k8MZ8GnH6VUSbczJGnTotUKH+fOY9Cg3y8NEvPUREfwRzguI+3N+v8gp6H0UAohayldA==}
+    dependencies:
+      '@fastify/static': 6.10.2
+      fastify-plugin: 4.5.0
+      openapi-types: 12.1.3
+      rfdc: 1.3.0
+      yaml: 2.3.1
+    dev: false
+
+  /@fastify/swagger@8.6.0:
+    resolution: {integrity: sha512-PGde7ryn0nsX/BpSrjP4Ade8RK2M0uBIU4Iow3Qt3kWa/70p1fM7AW28kS3dKERnwT0VwrUdxU3ftrRI+DsNTw==}
+    dependencies:
+      fastify-plugin: 4.5.0
+      json-schema-resolver: 2.0.0
+      openapi-types: 12.1.3
+      rfdc: 1.3.0
+      yaml: 2.3.1
+    transitivePeerDependencies:
+      - supports-color
+    dev: false
+
   /@fastify/view@7.4.1:
     resolution: {integrity: sha512-ahmRmSbNVM8bIoz0BAFnY0jNigom+xbPQ9Q1ZjmNOtGVVT3nYXCxw2OMkTr9iXwrJ4Le3EtWDHlFkZ2fCQ2hJA==}
     dependencies:
@@ -4897,10 +4914,6 @@ packages:
       hashlru: 2.3.0
     dev: false
 
-  /@gar/promisify@1.1.3:
-    resolution: {integrity: sha512-k2Ty1JcVojjJFwrg/ThKi2ujJ7XNLYaFGNB/bWT9wGR+oSMJHMa5w+CUq6p/pVrKeNNgA7pCqEcjSnHVoqJQFw==}
-    dev: false
-
   /@hapi/hoek@9.3.0:
     resolution: {integrity: sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==}
     dev: true
@@ -4911,8 +4924,8 @@ packages:
       '@hapi/hoek': 9.3.0
     dev: true
 
-  /@humanwhocodes/config-array@0.11.8:
-    resolution: {integrity: sha512-UybHIJzJnR5Qc/MsD9Kr+RpO2h+/P1GhOwdiLPXK5TWk5sgTdu88bTD9UP+CKbPPh5Rni1u0GjAdYQLemG8g+g==}
+  /@humanwhocodes/config-array@0.11.10:
+    resolution: {integrity: sha512-KVVjQmNUepDVGXNuoRRdmmEjruj0KfiGSbS8LVc12LMsWDQzRXJ0qdhN8L8uUigKpfEHRhlaQFY0ib1tnUbNeQ==}
     engines: {node: '>=10.10.0'}
     dependencies:
       '@humanwhocodes/object-schema': 1.2.1
@@ -4935,6 +4948,18 @@ packages:
     resolution: {integrity: sha512-Sx1pU8EM64o2BrqNpEO1CNLtKQwyhuXuqyfH7oGKCk+1a33d2r5saW8zNwm3j6BTExtjrv2BxTgzzkMwts6vGg==}
     dev: false
 
+  /@isaacs/cliui@8.0.2:
+    resolution: {integrity: sha512-O8jcjabXaleOG9DQ0+ARXWZBTfnP4WNAqzuiJK7ll44AmxGKv/J2M4TPjxjY3znBCfvBXFzucm1twdyFybFqEA==}
+    engines: {node: '>=12'}
+    dependencies:
+      string-width: 5.1.2
+      string-width-cjs: /string-width@4.2.3
+      strip-ansi: 7.1.0
+      strip-ansi-cjs: /strip-ansi@6.0.1
+      wrap-ansi: 8.1.0
+      wrap-ansi-cjs: /wrap-ansi@7.0.0
+    dev: false
+
   /@istanbuljs/load-nyc-config@1.1.0:
     resolution: {integrity: sha512-VjeHSlIzpv/NyD3N0YuHfXOPDIixcA1q2ZV98wsMqcYlPmv2n3Yb2lYP9XMElnaFVXg5A7YLTeLu6V84uQDjmQ==}
     engines: {node: '>=8'}
@@ -4956,7 +4981,7 @@ packages:
     engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
     dependencies:
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       chalk: 4.1.2
       jest-message-util: 29.5.0
       jest-util: 29.5.0
@@ -4977,14 +5002,14 @@ packages:
       '@jest/test-result': 29.5.0
       '@jest/transform': 29.5.0
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       ansi-escapes: 4.3.2
       chalk: 4.1.2
       ci-info: 3.7.1
       exit: 0.1.2
       graceful-fs: 4.2.11
       jest-changed-files: 29.5.0
-      jest-config: 29.5.0(@types/node@20.2.5)
+      jest-config: 29.5.0(@types/node@20.3.1)
       jest-haste-map: 29.5.0
       jest-message-util: 29.5.0
       jest-regex-util: 29.4.3
@@ -5018,7 +5043,7 @@ packages:
     dependencies:
       '@jest/fake-timers': 29.5.0
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       jest-mock: 29.5.0
     dev: true
 
@@ -5044,8 +5069,8 @@ packages:
     engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
     dependencies:
       '@jest/types': 29.5.0
-      '@sinonjs/fake-timers': 10.2.0
-      '@types/node': 20.2.5
+      '@sinonjs/fake-timers': 10.3.0
+      '@types/node': 20.3.1
       jest-message-util: 29.5.0
       jest-mock: 29.5.0
       jest-util: 29.5.0
@@ -5078,7 +5103,7 @@ packages:
       '@jest/transform': 29.5.0
       '@jest/types': 29.5.0
       '@jridgewell/trace-mapping': 0.3.17
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       chalk: 4.1.2
       collect-v8-coverage: 1.0.1
       exit: 0.1.2
@@ -5172,7 +5197,7 @@ packages:
     dependencies:
       '@types/istanbul-lib-coverage': 2.0.4
       '@types/istanbul-reports': 3.0.1
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       '@types/yargs': 16.0.5
       chalk: 4.1.2
     dev: true
@@ -5184,7 +5209,7 @@ packages:
       '@jest/schemas': 29.4.3
       '@types/istanbul-lib-coverage': 2.0.4
       '@types/istanbul-reports': 3.0.1
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       '@types/yargs': 17.0.19
       chalk: 4.1.2
     dev: true
@@ -5203,7 +5228,7 @@ packages:
       magic-string: 0.27.0
       react-docgen-typescript: 2.2.2(typescript@5.1.3)
       typescript: 5.1.3
-      vite: 4.3.9(@types/node@20.2.5)(sass@1.62.1)
+      vite: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
     dev: true
 
   /@jridgewell/gen-mapping@0.3.2:
@@ -5267,7 +5292,7 @@ packages:
       nopt: 5.0.0
       npmlog: 5.0.1
       rimraf: 3.0.2
-      semver: 7.5.1
+      semver: 7.5.3
       tar: 6.1.13
     transitivePeerDependencies:
       - encoding
@@ -5285,32 +5310,32 @@ packages:
       react: 18.2.0
     dev: true
 
-  /@microsoft/api-extractor-model@7.26.7(@types/node@18.16.3):
-    resolution: {integrity: sha512-rx3Tq632VG3ddR74kPuPbv1qmUgO2IuCvn1z16hbNWNS5RhnTQqNPWIm7NVoi6lCh2E7uxzfmdnWXIXiJhM5IQ==}
+  /@microsoft/api-extractor-model@7.27.3(@types/node@20.3.1):
+    resolution: {integrity: sha512-fSFvw7otYHduOkyshjTbapKKgwF8bgquVHvgF8VgeKtMYvqXkoaj7W6VcM7PNY7E2bbblhUgC4XNdqZLD4SJGw==}
     dependencies:
       '@microsoft/tsdoc': 0.14.2
       '@microsoft/tsdoc-config': 0.16.2
-      '@rushstack/node-core-library': 3.58.0(@types/node@18.16.3)
+      '@rushstack/node-core-library': 3.59.4(@types/node@20.3.1)
     transitivePeerDependencies:
       - '@types/node'
     dev: true
 
-  /@microsoft/api-extractor@7.34.7(@types/node@18.16.3):
-    resolution: {integrity: sha512-8CrrYyOBWqc4XFviR1KSuHSlmJjlnC5CVpPkcFB8HXiLABUVaVWFTsOzJIwUU6z8mc4BZPZ8tSGAg/mwFDU31Q==}
+  /@microsoft/api-extractor@7.36.0(@types/node@20.3.1):
+    resolution: {integrity: sha512-P+kYgJFDXIr+UNzhRMhlpM/dderi6ab4lxn35vdhfAIMPtGCSXIJxrrtpTOQmQW8CZtmoZX06LYoUsKCc1zjow==}
     hasBin: true
     dependencies:
-      '@microsoft/api-extractor-model': 7.26.7(@types/node@18.16.3)
+      '@microsoft/api-extractor-model': 7.27.3(@types/node@20.3.1)
       '@microsoft/tsdoc': 0.14.2
       '@microsoft/tsdoc-config': 0.16.2
-      '@rushstack/node-core-library': 3.58.0(@types/node@18.16.3)
-      '@rushstack/rig-package': 0.3.18
-      '@rushstack/ts-command-line': 4.13.2
+      '@rushstack/node-core-library': 3.59.4(@types/node@20.3.1)
+      '@rushstack/rig-package': 0.4.0
+      '@rushstack/ts-command-line': 4.15.1
       colors: 1.2.5
       lodash: 4.17.21
       resolve: 1.22.1
       semver: 7.3.8
       source-map: 0.6.1
-      typescript: 4.8.4
+      typescript: 5.0.4
     transitivePeerDependencies:
       - '@types/node'
     dev: true
@@ -5422,17 +5447,14 @@ packages:
       tar-fs: 2.1.1
     dev: true
 
-  /@nestjs/common@9.4.2(reflect-metadata@0.1.13)(rxjs@7.8.1):
-    resolution: {integrity: sha512-sea+qZnbD5x3YWZDVQT/wbVJ2NiABaM1tyZTLuW9hpkcM2KFA96xKtK3VaCxyz49zoXIgSOefsyK7HuUMCe27Q==}
+  /@nestjs/common@10.0.3(reflect-metadata@0.1.13)(rxjs@7.8.1):
+    resolution: {integrity: sha512-Zv59rDQMuwyja8fvnQelG4AbEe7FEC2ZUXcUwE6Tw0aOHx5CaOBIU426FCYY9o3iqJX3xLCKVJ8NrLPg58xCZg==}
     peerDependencies:
-      cache-manager: <=5
       class-transformer: '*'
       class-validator: '*'
       reflect-metadata: ^0.1.12
       rxjs: ^7.1.0
     peerDependenciesMeta:
-      cache-manager:
-        optional: true
       class-transformer:
         optional: true
       class-validator:
@@ -5441,18 +5463,18 @@ packages:
       iterare: 1.2.1
       reflect-metadata: 0.1.13
       rxjs: 7.8.1
-      tslib: 2.5.2
+      tslib: 2.5.3
       uid: 2.0.2
     dev: false
 
-  /@nestjs/core@9.4.2(@nestjs/common@9.4.2)(reflect-metadata@0.1.13)(rxjs@7.8.1):
-    resolution: {integrity: sha512-S5K9GTpjBqEJtu5VxRsVaaGEBZ1bkY+Ht4+2hqZSKsI+rzcEB5hcvR+5KiMsMY1VGYvlZ99lxYz72p4h8B0mKw==}
+  /@nestjs/core@10.0.3(@nestjs/common@10.0.3)(reflect-metadata@0.1.13)(rxjs@7.8.1):
+    resolution: {integrity: sha512-LPZrUaGk9ZXXkOOoqNn2EwBN7bBV2+KKbNxkmJKZ/7wMO+qGE1hCLaYuwoPdwUEwmDMchFpUOydfMIeC1s/3bg==}
     requiresBuild: true
     peerDependencies:
-      '@nestjs/common': ^9.0.0
-      '@nestjs/microservices': ^9.0.0
-      '@nestjs/platform-express': ^9.0.0
-      '@nestjs/websockets': ^9.0.0
+      '@nestjs/common': ^10.0.0
+      '@nestjs/microservices': ^10.0.0
+      '@nestjs/platform-express': ^10.0.0
+      '@nestjs/websockets': ^10.0.0
       reflect-metadata: ^0.1.12
       rxjs: ^7.1.0
     peerDependenciesMeta:
@@ -5463,35 +5485,35 @@ packages:
       '@nestjs/websockets':
         optional: true
     dependencies:
-      '@nestjs/common': 9.4.2(reflect-metadata@0.1.13)(rxjs@7.8.1)
+      '@nestjs/common': 10.0.3(reflect-metadata@0.1.13)(rxjs@7.8.1)
       '@nuxtjs/opencollective': 0.3.2
       fast-safe-stringify: 2.1.1
       iterare: 1.2.1
       path-to-regexp: 3.2.0
       reflect-metadata: 0.1.13
       rxjs: 7.8.1
-      tslib: 2.5.2
+      tslib: 2.5.3
       uid: 2.0.2
     transitivePeerDependencies:
       - encoding
     dev: false
 
-  /@nestjs/testing@9.4.2(@nestjs/common@9.4.2)(@nestjs/core@9.4.2):
-    resolution: {integrity: sha512-4WZPJz85zLVZkhmWYq+Unr43MixISelg/TyuX1YFZYOeukIN+O6fRtAAPIKLqRQsiY0rE/h8FAEbYGWhNrRfSA==}
+  /@nestjs/testing@10.0.3(@nestjs/common@10.0.3)(@nestjs/core@10.0.3):
+    resolution: {integrity: sha512-Rhm+E7yr499DIOuYbqskdNVo/NJjLKDS7Wp6NWl37woef4u7eVsSKN8VUCXKxNlYUrSw2Nu2AekpLzvl169SXg==}
     peerDependencies:
-      '@nestjs/common': ^9.0.0
-      '@nestjs/core': ^9.0.0
-      '@nestjs/microservices': ^9.0.0
-      '@nestjs/platform-express': ^9.0.0
+      '@nestjs/common': ^10.0.0
+      '@nestjs/core': ^10.0.0
+      '@nestjs/microservices': ^10.0.0
+      '@nestjs/platform-express': ^10.0.0
     peerDependenciesMeta:
       '@nestjs/microservices':
         optional: true
       '@nestjs/platform-express':
         optional: true
     dependencies:
-      '@nestjs/common': 9.4.2(reflect-metadata@0.1.13)(rxjs@7.8.1)
-      '@nestjs/core': 9.4.2(@nestjs/common@9.4.2)(reflect-metadata@0.1.13)(rxjs@7.8.1)
-      tslib: 2.5.2
+      '@nestjs/common': 10.0.3(reflect-metadata@0.1.13)(rxjs@7.8.1)
+      '@nestjs/core': 10.0.3(@nestjs/common@10.0.3)(reflect-metadata@0.1.13)(rxjs@7.8.1)
+      tslib: 2.5.3
     dev: false
 
   /@nodelib/fs.scandir@2.1.5:
@@ -5512,21 +5534,11 @@ packages:
       '@nodelib/fs.scandir': 2.1.5
       fastq: 1.15.0
 
-  /@npmcli/fs@2.1.2:
-    resolution: {integrity: sha512-yOJKRvohFOaLqipNtwYB9WugyZKhC/DZC4VYPmpaCzDBrA8YpK3qHZ8/HGscMnE4GqbkLNuVcCnxkeQEdGt6LQ==}
-    engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0}
+  /@npmcli/fs@3.1.0:
+    resolution: {integrity: sha512-7kZUAaLscfgbwBQRbvdMYaZOWyMEcPTH/tJjnyAWJ/dvvs9Ef+CERx/qJb9GExJpl1qipaDGn7KqHnFGGixd0w==}
+    engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0}
     dependencies:
-      '@gar/promisify': 1.1.3
-      semver: 7.5.1
-    dev: false
-
-  /@npmcli/move-file@2.0.1:
-    resolution: {integrity: sha512-mJd2Z5TjYWq/ttPLLGqArdtnC74J6bOzg4rMDnN+p1xTacZ2yPRCk2y0oSWQtygLR9YVQXgOcONrwtnk3JupxQ==}
-    engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0}
-    deprecated: This functionality has been moved to @npmcli/fs
-    dependencies:
-      mkdirp: 1.0.4
-      rimraf: 3.0.2
+      semver: 7.5.3
     dev: false
 
   /@nsfw-filter/gif-frames@1.0.2:
@@ -5554,7 +5566,7 @@ packages:
     dependencies:
       chalk: 4.1.2
       consola: 2.15.3
-      node-fetch: 2.6.7
+      node-fetch: 2.6.11
     transitivePeerDependencies:
       - encoding
     dev: false
@@ -5572,6 +5584,13 @@ packages:
       sshpk: 1.17.0
     dev: false
 
+  /@pkgjs/parseargs@0.11.0:
+    resolution: {integrity: sha512-+1VkjdD0QBLPodGrJUeqarH8VAIvQODIbwh9XpP5Syisf7YoQgsJKPNFoqqLQlu+VQ/tVSshMR6loPMn8U+dPg==}
+    engines: {node: '>=14'}
+    requiresBuild: true
+    dev: false
+    optional: true
+
   /@redis/bloom@1.1.0(@redis/client@1.4.2):
     resolution: {integrity: sha512-9QovlxmpRtvxVbN0UBcv8WfdSMudNZZTFqCsnBszcQXqaZb/TVe30ScgGEO7u1EAIacTPAo7/oCYjYAxiHLanQ==}
     peerDependencies:
@@ -5621,7 +5640,7 @@ packages:
       '@redis/client': 1.4.2
     dev: true
 
-  /@rollup/plugin-alias@5.0.0(rollup@3.23.0):
+  /@rollup/plugin-alias@5.0.0(rollup@3.25.1):
     resolution: {integrity: sha512-l9hY5chSCjuFRPsnRm16twWBiSApl2uYFLsepQYwtBuAxNMQ/1dJqADld40P0Jkqm65GRTLy/AC6hnpVebtLsA==}
     engines: {node: '>=14.0.0'}
     peerDependencies:
@@ -5630,11 +5649,11 @@ packages:
       rollup:
         optional: true
     dependencies:
-      rollup: 3.23.0
+      rollup: 3.25.1
       slash: 4.0.0
     dev: false
 
-  /@rollup/plugin-json@6.0.0(rollup@3.23.0):
+  /@rollup/plugin-json@6.0.0(rollup@3.25.1):
     resolution: {integrity: sha512-i/4C5Jrdr1XUarRhVu27EEwjt4GObltD7c+MkCIpO2QIbojw8MUs+CCTqOphQi3Qtg1FLmYt+l+6YeoIf51J7w==}
     engines: {node: '>=14.0.0'}
     peerDependencies:
@@ -5643,11 +5662,11 @@ packages:
       rollup:
         optional: true
     dependencies:
-      '@rollup/pluginutils': 5.0.2(rollup@3.23.0)
-      rollup: 3.23.0
+      '@rollup/pluginutils': 5.0.2(rollup@3.25.1)
+      rollup: 3.25.1
     dev: false
 
-  /@rollup/plugin-replace@5.0.2(rollup@3.23.0):
+  /@rollup/plugin-replace@5.0.2(rollup@3.25.1):
     resolution: {integrity: sha512-M9YXNekv/C/iHHK+cvORzfRYfPbq0RDD8r0G+bMiTXjNGKulPnCT9O3Ss46WfhI6ZOCgApOP7xAdmCQJ+U2LAA==}
     engines: {node: '>=14.0.0'}
     peerDependencies:
@@ -5656,9 +5675,9 @@ packages:
       rollup:
         optional: true
     dependencies:
-      '@rollup/pluginutils': 5.0.2(rollup@3.23.0)
+      '@rollup/pluginutils': 5.0.2(rollup@3.25.1)
       magic-string: 0.27.0
-      rollup: 3.23.0
+      rollup: 3.25.1
     dev: false
 
   /@rollup/pluginutils@4.2.1:
@@ -5669,7 +5688,7 @@ packages:
       picomatch: 2.3.1
     dev: true
 
-  /@rollup/pluginutils@5.0.2(rollup@3.23.0):
+  /@rollup/pluginutils@5.0.2(rollup@3.25.1):
     resolution: {integrity: sha512-pTd9rIsP92h+B6wWwFbW8RkZv4hiR/xKsqre4SIuAOaOEQRxi0lqLke9k2/7WegC85GgUs9pjmOjCUi3In4vwA==}
     engines: {node: '>=14.0.0'}
     peerDependencies:
@@ -5681,18 +5700,18 @@ packages:
       '@types/estree': 1.0.1
       estree-walker: 2.0.2
       picomatch: 2.3.1
-      rollup: 3.23.0
+      rollup: 3.25.1
     dev: false
 
-  /@rushstack/node-core-library@3.58.0(@types/node@18.16.3):
-    resolution: {integrity: sha512-DHAZ3LTOEq2/EGURznpTJDnB3SNE2CKMDXuviQ6afhru6RykE3QoqXkeyjbpLb5ib5cpIRCPE/wykNe0xmQj3w==}
+  /@rushstack/node-core-library@3.59.4(@types/node@20.3.1):
+    resolution: {integrity: sha512-YAKJDC6Mz/KA1D7bvB88WaRX3knt/ZuLzkRu5G9QADGSjLtvTWzCNCytRF2PCSaaHOZaZsWul4F1KQdgFgUDqA==}
     peerDependencies:
       '@types/node': '*'
     peerDependenciesMeta:
       '@types/node':
         optional: true
     dependencies:
-      '@types/node': 18.16.3
+      '@types/node': 20.3.1
       colors: 1.2.5
       fs-extra: 7.0.1
       import-lazy: 4.0.0
@@ -5702,15 +5721,15 @@ packages:
       z-schema: 5.0.5
     dev: true
 
-  /@rushstack/rig-package@0.3.18:
-    resolution: {integrity: sha512-SGEwNTwNq9bI3pkdd01yCaH+gAsHqs0uxfGvtw9b0LJXH52qooWXnrFTRRLG1aL9pf+M2CARdrA9HLHJys3jiQ==}
+  /@rushstack/rig-package@0.4.0:
+    resolution: {integrity: sha512-FnM1TQLJYwSiurP6aYSnansprK5l8WUK8VG38CmAaZs29ZeL1msjK0AP1VS4ejD33G0kE/2cpsPsS9jDenBMxw==}
     dependencies:
       resolve: 1.22.1
       strip-json-comments: 3.1.1
     dev: true
 
-  /@rushstack/ts-command-line@4.13.2:
-    resolution: {integrity: sha512-bCU8qoL9HyWiciltfzg7GqdfODUeda/JpI0602kbN5YH22rzTxyqYvv7aRLENCM7XCQ1VRs7nMkEqgJUOU8Sag==}
+  /@rushstack/ts-command-line@4.15.1:
+    resolution: {integrity: sha512-EL4jxZe5fhb1uVL/P/wQO+Z8Rc8FMiWJ1G7VgnPDvdIt5GVjRfK7vwzder1CZQiX3x0PY6uxENYLNGTFd1InRQ==}
     dependencies:
       '@types/argparse': 1.0.38
       argparse: 1.0.10
@@ -5766,8 +5785,8 @@ packages:
     dependencies:
       type-detect: 4.0.8
 
-  /@sinonjs/fake-timers@10.2.0:
-    resolution: {integrity: sha512-OPwQlEdg40HAj5KNF8WW6q2KG4Z+cBCZb3m4ninfTZKaBmbIJodviQsDBoYMPHkOyJJMHnOJo5j2+LKDOhOACg==}
+  /@sinonjs/fake-timers@10.3.0:
+    resolution: {integrity: sha512-V4BG07kuYSUkTCSBHG8G8TNhM+F19jXFWnQtzj+we8DrkpSBCee9Z3Ms8yiGer/dlmhe35/Xdgyo3/0rQKg7YA==}
     dependencies:
       '@sinonjs/commons': 3.0.0
 
@@ -5789,51 +5808,6 @@ packages:
     resolution: {integrity: sha512-sXXKG+uL9IrKqViTtao2Ws6dy0znu9sOaP1di/jKGW1M6VssO8vlpXCQcpZ+jisQ1tTFAC5Jo/EOzFbggBagFQ==}
     dev: true
 
-  /@snyk/dep-graph@2.6.0:
-    resolution: {integrity: sha512-9NPk7cTvDNA90NyNQvh87LYKgkCoD67i+FGdRpwA0/CL59RRY7cG37RTFe++Y3ZALxpYK1sLNzU+yeB7vzVhqQ==}
-    engines: {node: '>=10'}
-    dependencies:
-      event-loop-spinner: 2.2.0
-      lodash.clone: 4.5.0
-      lodash.constant: 3.0.0
-      lodash.filter: 4.6.0
-      lodash.foreach: 4.5.0
-      lodash.isempty: 4.4.0
-      lodash.isequal: 4.5.0
-      lodash.isfunction: 3.0.9
-      lodash.isundefined: 3.0.1
-      lodash.map: 4.6.0
-      lodash.reduce: 4.6.0
-      lodash.size: 4.2.0
-      lodash.transform: 4.6.0
-      lodash.union: 4.6.0
-      lodash.values: 4.3.0
-      object-hash: 3.0.0
-      packageurl-js: 1.0.1
-      semver: 7.5.1
-      tslib: 2.5.2
-    dev: false
-
-  /@snyk/graphlib@2.1.9-patch.3:
-    resolution: {integrity: sha512-bBY9b9ulfLj0v2Eer0yFYa3syVeIxVKl2EpxSrsVeT4mjA0CltZyHsF0JjoaGXP27nItTdJS5uVsj1NA+3aE+Q==}
-    dependencies:
-      lodash.clone: 4.5.0
-      lodash.constant: 3.0.0
-      lodash.filter: 4.6.0
-      lodash.foreach: 4.5.0
-      lodash.has: 4.5.2
-      lodash.isempty: 4.4.0
-      lodash.isfunction: 3.0.9
-      lodash.isundefined: 3.0.1
-      lodash.keys: 4.2.0
-      lodash.map: 4.6.0
-      lodash.reduce: 4.6.0
-      lodash.size: 4.2.0
-      lodash.transform: 4.6.0
-      lodash.union: 4.6.0
-      lodash.values: 4.3.0
-    dev: false
-
   /@sqltools/formatter@1.2.5:
     resolution: {integrity: sha512-Uy0+khmZqUrUGm5dmMqVlnvufZRSK0FbYzVgp0UMstm+F5+W2/jnEEQyc9vo1ZR/E5ZI/B1WjjoTqBqwJL6Krw==}
     dev: false
@@ -6262,9 +6236,9 @@ packages:
       magic-string: 0.27.0
       remark-external-links: 8.0.0
       remark-slug: 6.1.0
-      rollup: 3.23.0
+      rollup: 3.25.1
       typescript: 5.1.3
-      vite: 4.3.9(@types/node@20.2.5)(sass@1.62.1)
+      vite: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
     transitivePeerDependencies:
       - supports-color
     dev: true
@@ -6313,6 +6287,7 @@ packages:
 
   /@storybook/channels@7.0.18:
     resolution: {integrity: sha512-rkA7ea0M3+dWS+71iHJdiZ5R2QuIdiVg0CgyLJHDagc1qej7pEVNhMWtppeq+X5Pwp9nkz8ZTQ7aCjTf6th0/A==}
+    dev: true
 
   /@storybook/channels@7.0.2:
     resolution: {integrity: sha512-qkI8mFy9c8mxN2f01etayKhCaauL6RAsxRzbX1/pKj6UqhHWqqUbtHwymrv4hG5qDYjV1e9pd7ae5eNF8Kui0g==}
@@ -6358,7 +6333,7 @@ packages:
       prompts: 2.4.2
       puppeteer-core: 2.1.1
       read-pkg-up: 7.0.1
-      semver: 7.5.1
+      semver: 7.5.3
       shelljs: 0.8.5
       simple-update-notifier: 1.1.0
       strip-json-comments: 3.1.1
@@ -6511,7 +6486,7 @@ packages:
       pretty-hrtime: 1.0.3
       prompts: 2.4.2
       read-pkg-up: 7.0.1
-      semver: 7.5.1
+      semver: 7.5.3
       serve-favicon: 2.5.0
       telejson: 7.0.4
       ts-dedent: 2.2.0
@@ -6548,11 +6523,13 @@ packages:
       ts-dedent: 2.2.0
     transitivePeerDependencies:
       - supports-color
+    dev: true
 
   /@storybook/csf@0.1.0:
     resolution: {integrity: sha512-uk+jMXCZ8t38jSTHk2o5btI+aV2Ksbvl6DoOv3r6VaCM1KZqeuMwtwywIQdflkA8/6q/dKT8z8L+g8hC4GC3VQ==}
     dependencies:
       type-fest: 2.19.0
+    dev: true
 
   /@storybook/docs-mdx@0.1.0:
     resolution: {integrity: sha512-JDaBR9lwVY4eSH5W8EGHrhODjygPd6QImRbwjAuJNEnY0Vw4ie3bPkeGfnacB3OBW6u/agqPv2aRlR46JcAQLg==}
@@ -6640,7 +6617,7 @@ packages:
       memoizerific: 1.11.3
       react: 18.2.0
       react-dom: 18.2.0(react@18.2.0)
-      semver: 7.5.1
+      semver: 7.5.3
       store2: 2.14.2
       telejson: 7.0.4
       ts-dedent: 2.2.0
@@ -6759,7 +6736,7 @@ packages:
       react: 18.2.0
       react-docgen: 6.0.0-alpha.3
       react-dom: 18.2.0(react@18.2.0)
-      vite: 4.3.9(@types/node@20.2.5)(sass@1.62.1)
+      vite: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
     transitivePeerDependencies:
       - '@preact/preset-vite'
       - supports-color
@@ -6882,6 +6859,7 @@ packages:
       '@types/babel__core': 7.20.0
       '@types/express': 4.17.17
       file-system-cache: 2.0.2
+    dev: true
 
   /@storybook/types@7.0.2:
     resolution: {integrity: sha512-0OCt/kAexa8MCcljxA+yZxGMn0n2U2Ync0KxotItqNbKBKVkaLQUls0+IXTWSCpC/QJvNZ049jxUHHanNi/96w==}
@@ -6916,7 +6894,7 @@ packages:
       magic-string: 0.27.0
       react: 18.2.0
       react-dom: 18.2.0(react@18.2.0)
-      vite: 4.3.9(@types/node@20.2.5)(sass@1.62.1)
+      vite: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
       vue-docgen-api: 4.64.1(vue@3.3.4)
     transitivePeerDependencies:
       - '@preact/preset-vite'
@@ -6948,7 +6926,7 @@ packages:
       - supports-color
     dev: true
 
-  /@swc/cli@0.1.62(@swc/core@1.3.61)(chokidar@3.5.3):
+  /@swc/cli@0.1.62(@swc/core@1.3.66)(chokidar@3.5.3):
     resolution: {integrity: sha512-kOFLjKY3XH1DWLfXL1/B5MizeNorHR8wHKEi92S/Zi9Md/AK17KSqR8MgyRJ6C1fhKHvbBCl8wboyKAFXStkYw==}
     engines: {node: '>= 12.13'}
     hasBin: true
@@ -6960,11 +6938,11 @@ packages:
         optional: true
     dependencies:
       '@mole-inc/bin-wrapper': 8.0.1
-      '@swc/core': 1.3.61
+      '@swc/core': 1.3.66
       chokidar: 3.5.3
       commander: 7.2.0
       fast-glob: 3.2.12
-      semver: 7.5.1
+      semver: 7.5.3
       slash: 3.0.0
       source-map: 0.7.4
     dev: false
@@ -6986,10 +6964,11 @@ packages:
     cpu: [arm64]
     os: [darwin]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-darwin-arm64@1.3.61:
-    resolution: {integrity: sha512-Ra1CZIYYyIp/Y64VcKyaLjIPUwT83JmGduvHu8vhUZOvWV4dWL4s5DrcxQVaQJjjb7Z2N/IUYYS55US1TGnxZw==}
+  /@swc/core-darwin-arm64@1.3.66:
+    resolution: {integrity: sha512-UijJsvuLy73vxeVYEy7urIHksXS+3BdvJ9s9AY+bRMSQW483NO7RLp8g4FdTyJbRaN0BH15SQnY0dcjQBkVuHw==}
     engines: {node: '>=10'}
     cpu: [arm64]
     os: [darwin]
@@ -7002,10 +6981,11 @@ packages:
     cpu: [x64]
     os: [darwin]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-darwin-x64@1.3.61:
-    resolution: {integrity: sha512-LUia75UByUFkYH1Ddw7IE0X9usNVGJ7aL6+cgOTju7P0dsU0f8h/OGc/GDfp1E4qnKxDCJE+GwDRLoi4SjIxpg==}
+  /@swc/core-darwin-x64@1.3.66:
+    resolution: {integrity: sha512-xGsHKvViQnwTNLF30Y/5OqWdnN6RsiyUI8awZXfz1sHcXCEaLe+v+WLQ+/E8sgw0YUkYVHzzfV/sAN2CezJK5Q==}
     engines: {node: '>=10'}
     cpu: [x64]
     os: [darwin]
@@ -7018,10 +6998,11 @@ packages:
     cpu: [arm]
     os: [linux]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-linux-arm-gnueabihf@1.3.61:
-    resolution: {integrity: sha512-aalPlicYxHAn2PxNlo3JFEZkMXzCtUwjP27AgMqnfV4cSz7Omo56OtC+413e/kGyCH86Er9gJRQQsxNKP8Qbsg==}
+  /@swc/core-linux-arm-gnueabihf@1.3.66:
+    resolution: {integrity: sha512-gNbLcSIV2pq90BkMSpzvK4xPXOl8GEF3YR4NaqF0CYSzQsVXXTTqMuX/r26xNYudBKzH0345S1MpoRk2qricnA==}
     engines: {node: '>=10'}
     cpu: [arm]
     os: [linux]
@@ -7034,10 +7015,11 @@ packages:
     cpu: [arm64]
     os: [linux]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-linux-arm64-gnu@1.3.61:
-    resolution: {integrity: sha512-9hGdsbQrYNPo1c7YzWF57yl17bsIuuEQi3I1fOFSv3puL3l5M/C/oCD0Bz6IdKh6mEDC5UNJE4LWtV1gFA995A==}
+  /@swc/core-linux-arm64-gnu@1.3.66:
+    resolution: {integrity: sha512-cJSQ0oplyWbJqy4rzVcnBYLAi6z1QT3QCcR7iAey0aAmCvfRBZJfXlyjggMjn4iosuadkauwCZR1xYNhBDRn7w==}
     engines: {node: '>=10'}
     cpu: [arm64]
     os: [linux]
@@ -7050,10 +7032,11 @@ packages:
     cpu: [arm64]
     os: [linux]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-linux-arm64-musl@1.3.61:
-    resolution: {integrity: sha512-mVmcNfFQRP4SYbGC08IPB3B9Xox+VpGIQqA3Qg7LMCcejLAQLi4Lfe8CDvvBPlQzXHso0Cv+BicJnQVKs8JLOA==}
+  /@swc/core-linux-arm64-musl@1.3.66:
+    resolution: {integrity: sha512-GDQZpcB9aGxG9PTA2shdIkoMZlGK5omJ8NR49uoBTtLBVYiGeXAwV0U1Uaw8kXEZj9i7wZDkvjzjSaNH3evRsg==}
     engines: {node: '>=10'}
     cpu: [arm64]
     os: [linux]
@@ -7066,10 +7049,11 @@ packages:
     cpu: [x64]
     os: [linux]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-linux-x64-gnu@1.3.61:
-    resolution: {integrity: sha512-ZkRHs7GEikN6JiVL1/stvq9BVHKrSKoRn9ulVK2hMr+mAGNOKm3Y06NSzOO+BWwMaFOgnO2dWlszCUICsQ0kpg==}
+  /@swc/core-linux-x64-gnu@1.3.66:
+    resolution: {integrity: sha512-lg8E4O/Pd9KfK0lajdinVMuGME8dSv7V9arhEpmlfGE2eXSDCWqDn5Htk5QVBstt9lt1lsRhWHJ/YYc2eQY30Q==}
     engines: {node: '>=10'}
     cpu: [x64]
     os: [linux]
@@ -7082,10 +7066,11 @@ packages:
     cpu: [x64]
     os: [linux]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-linux-x64-musl@1.3.61:
-    resolution: {integrity: sha512-zK7VqQ5JlK20+7fxI4AgvIUckeZyX0XIbliGXNMR3i+39SJq1vs9scYEmq8VnAfvNdMU5BG+DewbFJlMfCtkxQ==}
+  /@swc/core-linux-x64-musl@1.3.66:
+    resolution: {integrity: sha512-lo8ZcAO/zL2pZWH+LZIyge8u2MklaeuT6+FpVVpBFktMVdYXbaVtzpvWbgRFBZHvL3SRDF+u8jxjtkXhvGUpTw==}
     engines: {node: '>=10'}
     cpu: [x64]
     os: [linux]
@@ -7098,10 +7083,11 @@ packages:
     cpu: [arm64]
     os: [win32]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-win32-arm64-msvc@1.3.61:
-    resolution: {integrity: sha512-e9kVVPk5iVNhO41TvLvcExDHn5iATQ5/M4U7/CdcC7s0fK19TKSEUqkdoTLIJvHBFhgR7w3JJSErfnauO0xXoA==}
+  /@swc/core-win32-arm64-msvc@1.3.66:
+    resolution: {integrity: sha512-cQoVwBuJY5WkHbfpCOlndNwYr1ZThatRjQQvKy540NUIeAEk9Fa6ozlDBtU75UdaWKtUG6YQ/bWz+KTemheVxw==}
     engines: {node: '>=10'}
     cpu: [arm64]
     os: [win32]
@@ -7114,10 +7100,11 @@ packages:
     cpu: [ia32]
     os: [win32]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-win32-ia32-msvc@1.3.61:
-    resolution: {integrity: sha512-7cJULfa6HvKqvFh6M/f7mKiNRhE2AjgFUCZfdOuy5r8vbtpk+qBK94TXwaDjJYDUGKzDVZw/tJ1eN4Y9n9Ls/Q==}
+  /@swc/core-win32-ia32-msvc@1.3.66:
+    resolution: {integrity: sha512-y/FrAIINK4UBeUQQknGlWXEyjo+MBvjF7WkUf2KP7sNr9EHHy8+dXohAGd5Anz0eJrqOM1ZXR/GEjxRp7bGQ1Q==}
     engines: {node: '>=10'}
     cpu: [ia32]
     os: [win32]
@@ -7130,18 +7117,19 @@ packages:
     cpu: [x64]
     os: [win32]
     requiresBuild: true
+    dev: false
     optional: true
 
-  /@swc/core-win32-x64-msvc@1.3.61:
-    resolution: {integrity: sha512-Jx8S+21WcKF/wlhW+sYpystWUyymDTEsbBpOgBRpXZelakVcNBCIIYSZOKW/A9PwWTpu6S8yvbs9nUOzKiVPqA==}
+  /@swc/core-win32-x64-msvc@1.3.66:
+    resolution: {integrity: sha512-yI64ACzS14qFLrfyO12qW+f/UROTotzDeEbuyJAaPD2IZexoT1cICznI3sBmIfrSt33mVuW8eF5m3AG/NUImzw==}
     engines: {node: '>=10'}
     cpu: [x64]
     os: [win32]
     requiresBuild: true
     optional: true
 
-  /@swc/core@1.3.56:
-    resolution: {integrity: sha512-yz/EeXT+PMZucUNrYceRUaTfuNS4IIu5EDZSOlvCEvm4jAmZi7CYH1B/kvzEzoAOzr7zkQiDPNJftcQXLkjbjA==}
+  /@swc/core@1.3.66:
+    resolution: {integrity: sha512-Hpf91kH5ly7fHkWnApwryTQryT+TO4kMMPH3WyciUSQOWLE3UuQz1PtETHQQk7PZ/b1QF0qQurJrgfBr5bSKUA==}
     engines: {node: '>=10'}
     requiresBuild: true
     peerDependencies:
@@ -7150,57 +7138,25 @@ packages:
       '@swc/helpers':
         optional: true
     optionalDependencies:
-      '@swc/core-darwin-arm64': 1.3.56
-      '@swc/core-darwin-x64': 1.3.56
-      '@swc/core-linux-arm-gnueabihf': 1.3.56
-      '@swc/core-linux-arm64-gnu': 1.3.56
-      '@swc/core-linux-arm64-musl': 1.3.56
-      '@swc/core-linux-x64-gnu': 1.3.56
-      '@swc/core-linux-x64-musl': 1.3.56
-      '@swc/core-win32-arm64-msvc': 1.3.56
-      '@swc/core-win32-ia32-msvc': 1.3.56
-      '@swc/core-win32-x64-msvc': 1.3.56
+      '@swc/core-darwin-arm64': 1.3.66
+      '@swc/core-darwin-x64': 1.3.66
+      '@swc/core-linux-arm-gnueabihf': 1.3.66
+      '@swc/core-linux-arm64-gnu': 1.3.66
+      '@swc/core-linux-arm64-musl': 1.3.66
+      '@swc/core-linux-x64-gnu': 1.3.66
+      '@swc/core-linux-x64-musl': 1.3.66
+      '@swc/core-win32-arm64-msvc': 1.3.66
+      '@swc/core-win32-ia32-msvc': 1.3.66
+      '@swc/core-win32-x64-msvc': 1.3.66
 
-  /@swc/core@1.3.61:
-    resolution: {integrity: sha512-p58Ltdjo7Yy8CU3zK0cp4/eAgy5qkHs35znGedqVGPiA67cuYZM63DuTfmyrOntMRwQnaFkMLklDAPCizDdDng==}
-    engines: {node: '>=10'}
-    requiresBuild: true
-    peerDependencies:
-      '@swc/helpers': ^0.5.0
-    peerDependenciesMeta:
-      '@swc/helpers':
-        optional: true
-    optionalDependencies:
-      '@swc/core-darwin-arm64': 1.3.61
-      '@swc/core-darwin-x64': 1.3.61
-      '@swc/core-linux-arm-gnueabihf': 1.3.61
-      '@swc/core-linux-arm64-gnu': 1.3.61
-      '@swc/core-linux-arm64-musl': 1.3.61
-      '@swc/core-linux-x64-gnu': 1.3.61
-      '@swc/core-linux-x64-musl': 1.3.61
-      '@swc/core-win32-arm64-msvc': 1.3.61
-      '@swc/core-win32-ia32-msvc': 1.3.61
-      '@swc/core-win32-x64-msvc': 1.3.61
-
-  /@swc/jest@0.2.26(@swc/core@1.3.56):
+  /@swc/jest@0.2.26(@swc/core@1.3.66):
     resolution: {integrity: sha512-7lAi7q7ShTO3E5Gt1Xqf3pIhRbERxR1DUxvtVa9WKzIB+HGQ7wZP5sYx86zqnaEoKKGhmOoZ7gyW0IRu8Br5+A==}
     engines: {npm: '>= 7.0.0'}
     peerDependencies:
       '@swc/core': '*'
     dependencies:
       '@jest/create-cache-key-function': 27.5.1
-      '@swc/core': 1.3.56
-      jsonc-parser: 3.2.0
-    dev: true
-
-  /@swc/jest@0.2.26(@swc/core@1.3.61):
-    resolution: {integrity: sha512-7lAi7q7ShTO3E5Gt1Xqf3pIhRbERxR1DUxvtVa9WKzIB+HGQ7wZP5sYx86zqnaEoKKGhmOoZ7gyW0IRu8Br5+A==}
-    engines: {npm: '>= 7.0.0'}
-    peerDependencies:
-      '@swc/core': '*'
-    dependencies:
-      '@jest/create-cache-key-function': 27.5.1
-      '@swc/core': 1.3.61
+      '@swc/core': 1.3.66
       jsonc-parser: 3.2.0
     dev: true
 
@@ -7232,14 +7188,14 @@ packages:
     dependencies:
       defer-to-connect: 2.0.1
 
-  /@tabler/icons-webfont@2.21.0:
-    resolution: {integrity: sha512-WCa57zYBjD9NF3/g96WKePgKUkKKD95Y+mo27/fzXOGxuoP9lGRjd01UCeLTGVxdEPErwlCjHXSi8HoDX2jevg==}
+  /@tabler/icons-webfont@2.22.0:
+    resolution: {integrity: sha512-+hDYaRHL3OTdSqBV1Y1xejTp86lubMFon/jKu2eT7kpKnexyhmE/rh1DfF97IYpmQEazu3ip1/GFWL4BOU0vzQ==}
     dependencies:
-      '@tabler/icons': 2.21.0
+      '@tabler/icons': 2.22.0
     dev: false
 
-  /@tabler/icons@2.21.0:
-    resolution: {integrity: sha512-XKrTEHMX6XzCOwcOU8ZNA+Xqm51sI+0abn2jk1fyQUpWeFnGsOEiC+fpQ4EISc+v+U9jqgTSbh8bZ6JBuKU5sw==}
+  /@tabler/icons@2.22.0:
+    resolution: {integrity: sha512-lOsGHqRPIKNARMWHHFkUUJH78C8ptQmUcDnumFBUI4YLRKFouKa7uAZL3ZfuH0HjDpOhsnWqUYZ7FhMCLcGpAQ==}
     dev: false
 
   /@tensorflow/tfjs-backend-cpu@4.4.0(@tensorflow/tfjs-core@4.4.0):
@@ -7437,7 +7393,7 @@ packages:
   /@types/accepts@1.3.5:
     resolution: {integrity: sha512-jOdnI/3qTpHABjM5cx1Hc0sKsPoYCp+DP/GJRGtDlPd7fiV9oXGGIcjW/ZOxLIvjGz8MA+uMZI9metHlgqbgwQ==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/archiver@5.3.2:
@@ -7462,22 +7418,26 @@ packages:
       '@types/babel__generator': 7.6.4
       '@types/babel__template': 7.4.1
       '@types/babel__traverse': 7.20.0
+    dev: true
 
   /@types/babel__generator@7.6.4:
     resolution: {integrity: sha512-tFkciB9j2K755yrTALxD44McOrk+gfpIpvC3sxHjRawj6PfnQxrse4Clq5y/Rq+G3mrBurMax/lG8Qn2t9mSsg==}
     dependencies:
       '@babel/types': 7.22.4
+    dev: true
 
   /@types/babel__template@7.4.1:
     resolution: {integrity: sha512-azBFKemX6kMg5Io+/rdGT0dkGreboUVR0Cdm3fz9QJWpaQGJRQXl7C+6hOTCZcMll7KFyEQpgbYI2lHdsS4U7g==}
     dependencies:
       '@babel/parser': 7.22.4
       '@babel/types': 7.22.4
+    dev: true
 
   /@types/babel__traverse@7.20.0:
     resolution: {integrity: sha512-TBOjqAGf0hmaqRwpii5LLkJLg7c6OMm4nHLmpsUxwk9bBHtoTC6dAHdVWdGv4TBxj2CZOZY8Xfq8WmfoVi7n4Q==}
     dependencies:
       '@babel/types': 7.22.4
+    dev: true
 
   /@types/bcryptjs@2.4.2:
     resolution: {integrity: sha512-LiMQ6EOPob/4yUL66SZzu6Yh77cbzJFYll+ZfaPiPPFswtIlA/Fs1MzdKYA7JApHU49zQTbJGX3PDmCpIdDBRQ==}
@@ -7487,7 +7447,8 @@ packages:
     resolution: {integrity: sha512-ALYone6pm6QmwZoAgeyNksccT9Q4AWZQ6PvfwR37GT6r6FWUPguq6sUmNGSMV2Wr761oQoBxwGGa6DR5o1DC9g==}
     dependencies:
       '@types/connect': 3.4.35
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
+    dev: true
 
   /@types/braces@3.0.1:
     resolution: {integrity: sha512-+euflG6ygo4bn0JHtn4pYqcXwRtLvElQ7/nnjDu7iYG56H0+OhCd7d6Ug0IE3WcFpZozBKW2+80FUbv5QGk5AQ==}
@@ -7498,7 +7459,7 @@ packages:
     dependencies:
       '@types/http-cache-semantics': 4.0.1
       '@types/keyv': 3.1.4
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       '@types/responselike': 1.0.0
     dev: false
 
@@ -7531,7 +7492,8 @@ packages:
   /@types/connect@3.4.35:
     resolution: {integrity: sha512-cdeYyv4KWoEgpBISTxWvqYsVy444DOqehiF3fM3ne10AmJ62RSyNkUnxMJXHQWRQQX2eR94m5y1IZyDwBjV9FQ==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
+    dev: true
 
   /@types/content-disposition@0.5.5:
     resolution: {integrity: sha512-v6LCdKfK6BwcqMo+wYW05rLS12S0ZO0Fl4w1h4aaZMD7bqT3gVUns6FvLJKGZHQmYn3SX55JWGpziwJRwVgutA==}
@@ -7563,10 +7525,6 @@ packages:
     resolution: {integrity: sha512-ZmiaE3wglXVWBM9fyVC17aGPkLo/UgaOjEiI2FXQfyczrCefORPxIe+2dVmnmk3zkVIbizjrlQzmPGhSYGXG5g==}
     dev: true
 
-  /@types/emscripten@1.39.6:
-    resolution: {integrity: sha512-H90aoynNhhkQP6DRweEjJp5vfUVdIj7tdPLsu7pq89vODD/lcugKfZOsfgwpvM6XUewEp2N5dCg1Uf3Qe55Dcg==}
-    dev: false
-
   /@types/escape-regexp@0.0.1:
     resolution: {integrity: sha512-ogj/ZTIdeFkiuxDwawYuZSIgC6suFGgBeZPr6Xs5lHEcvIXTjXGtH+/n8f1XhZhespaUwJ5LIGRICPji972FLw==}
     dev: true
@@ -7595,9 +7553,10 @@ packages:
   /@types/express-serve-static-core@4.17.33:
     resolution: {integrity: sha512-TPBqmR/HRYI3eC2E5hmiivIzv+bidAfXofM+sbonAGvyDhySGw9/PQZFt2BLOrjUUR++4eJVpx6KnLQK1Fk9tA==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       '@types/qs': 6.9.7
       '@types/range-parser': 1.2.4
+    dev: true
 
   /@types/express@4.17.17:
     resolution: {integrity: sha512-Q4FmmuLGBG58btUnfS1c1r/NQdlp3DMfGDGig8WhfpA2YRUtEkxAjkZb0yvplJGYdF1fsQ81iMDcH24sSCNC/Q==}
@@ -7606,6 +7565,7 @@ packages:
       '@types/express-serve-static-core': 4.17.33
       '@types/qs': 6.9.7
       '@types/serve-static': 1.15.1
+    dev: true
 
   /@types/find-cache-dir@3.2.1:
     resolution: {integrity: sha512-frsJrz2t/CeGifcu/6uRo4b+SzAwT4NYCVPu1GN8IB9XTzrpPkGuV0tmh9mN+/L0PklAlsC3u5Fxt0ju00LXIw==}
@@ -7614,34 +7574,34 @@ packages:
   /@types/fluent-ffmpeg@2.1.21:
     resolution: {integrity: sha512-+n3dy/Tegt6n+YwGZUiGq6i8Jrnt8+MoyPiW1L6J5EWUl7GSt18a/VyReecfCsvTTNBXNMIKOMHDstiQM8nJLA==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/glob-stream@6.1.1:
     resolution: {integrity: sha512-AGOUTsTdbPkRS0qDeyeS+6KypmfVpbT5j23SN8UPG63qjKXNKjXn6V9wZUr8Fin0m9l8oGYaPK8b2WUMF8xI1A==}
     dependencies:
       '@types/glob': 8.1.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/glob@7.2.0:
     resolution: {integrity: sha512-ZUxbzKl0IfJILTS6t7ip5fQQM/J3TJYubDm3nMbgubNNYS62eXeUpoLUC8/7fJNiFYHTrGPQn7hspDUzIHX3UA==}
     dependencies:
       '@types/minimatch': 5.1.2
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/glob@8.1.0:
     resolution: {integrity: sha512-IO+MJPVhoqz+28h1qLAcBEH2+xHMK6MTyHJc7MTnnYb6wsoLR29POVGJ7LycmVXIqyy/4/2ShP5sUwTXuOwb/w==}
     dependencies:
       '@types/minimatch': 5.1.2
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/graceful-fs@4.1.6:
     resolution: {integrity: sha512-Sig0SNORX9fdW+bQuTEovKj3uHcUL6LQKbCrrqb1X7J6/ReAbhCXRAhc+SMejhLELFj2QcyuxmUooZ4bt5ReSw==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/gulp-rename@2.0.1:
@@ -7654,7 +7614,7 @@ packages:
   /@types/gulp-rename@2.0.2:
     resolution: {integrity: sha512-CQsXqTVtAXqrPd4IbrrlJEEzRkUR3RXsyZbrVoOVqjlchDDmnyRDatAUisjpQjjCg/wjJrSiNg8T1uAbJ/7Qqg==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       '@types/vinyl': 2.0.7
     dev: true
 
@@ -7691,13 +7651,6 @@ packages:
       '@types/istanbul-lib-report': 3.0.0
     dev: true
 
-  /@types/jest@29.5.1:
-    resolution: {integrity: sha512-tEuVcHrpaixS36w7hpsfLBLpjtMRJUE09/MHXn923LOVojDwyC14cWcfc0rDs0VEfUyYmt/+iX1kxxp+gZMcaQ==}
-    dependencies:
-      expect: 29.5.0
-      pretty-format: 29.5.0
-    dev: true
-
   /@types/jest@29.5.2:
     resolution: {integrity: sha512-mSoZVJF5YzGVCk+FsDxzDuH7s+SCkzrgKZzf0Z0T2WudhBUPoF6ktoTPC4R0ZoCPCV5xUvuU6ias5NvxcBcMMg==}
     dependencies:
@@ -7716,7 +7669,7 @@ packages:
   /@types/jsdom@21.1.1:
     resolution: {integrity: sha512-cZFuoVLtzKP3gmq9eNosUL1R50U+USkbLtUQ1bYVgl/lKp0FZM7Cq4aIHAL8oIvQ17uSHi7jXPtfDOdjPwBE7A==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       '@types/tough-cookie': 4.0.2
       parse5: 7.1.2
     dev: true
@@ -7729,8 +7682,8 @@ packages:
     resolution: {integrity: sha512-dRLjCWHYg4oaA77cxO64oO+7JwCwnIzkZPdrrC71jQmQtlhM556pwKo5bUzqvZndkVbeFLIIi+9TC40JNF5hNQ==}
     dev: true
 
-  /@types/jsonld@1.5.8:
-    resolution: {integrity: sha512-4l5t/jDnJpqZ+i7CLTTgPcT5BYXnAnwJupb07aAokPufCV0SjDHcwctUkSTuhIuSU9yHok+WOOngIGCtpL96gw==}
+  /@types/jsonld@1.5.9:
+    resolution: {integrity: sha512-K76ImkErPYL2wGPZpNFSKp6wE+h/APecZLJrU7UfDaGqt/f+D9Rrg1aR7VdRrQ6k5DUNRZ2vn9yACwmpOr9QcA==}
     dev: true
 
   /@types/jsrsasign@10.5.8:
@@ -7740,7 +7693,7 @@ packages:
   /@types/keyv@3.1.4:
     resolution: {integrity: sha512-BQ5aZNSCpj7D6K2ksrRCTmKRLEpnPvWDiLPfoGyhZ++8YtiK9d/3DBKPJgry359X/P1PfruyYwvnvwFjuEiEIg==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: false
 
   /@types/lodash@4.14.191:
@@ -7771,6 +7724,7 @@ packages:
 
   /@types/mime@3.0.1:
     resolution: {integrity: sha512-Y4XFY5VJAuw0FgAqPNd6NNoV44jbq9Bz2L7Rh/J6jLTiHBSBJa9fxqQIvkIld4GsoDOcCbvzOUAbLPsSKKg+uA==}
+    dev: true
 
   /@types/minimatch@5.1.2:
     resolution: {integrity: sha512-K0VQKziLUWkVKiRVrx4a40iPaxTUefQmjtkQofBkYRcoaaL/8rhwDWww9qWbrgicNOgnpIsMxyNIUM4+n6dUIA==}
@@ -7787,7 +7741,7 @@ packages:
   /@types/node-fetch@2.6.2:
     resolution: {integrity: sha512-DHqhlq5jeESLy19TYhLakJ07kNumXWjcDdxXsLUMJZ6ue8VZJj4kLPQVE/2mdHh3xZziNF1xppu5lwmS53HR+A==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       form-data: 3.0.1
 
   /@types/node-fetch@3.0.3:
@@ -7796,10 +7750,6 @@ packages:
       node-fetch: 3.3.1
     dev: true
 
-  /@types/node@13.13.52:
-    resolution: {integrity: sha512-s3nugnZumCC//n4moGGe6tkNMyYEdaDBitVjwPxXmR5lnMG5dHePinH2EdxkG3Rh1ghFHHixAG4NJhpJW1rthQ==}
-    dev: false
-
   /@types/node@14.18.36:
     resolution: {integrity: sha512-FXKWbsJ6a1hIrRxv+FoukuHnGTgEzKYGi7kilfMae96AL9UNkPFNWJEEYWzdRI9ooIkbr4AKldyuSTLql06vLQ==}
     dev: true
@@ -7811,17 +7761,13 @@ packages:
   /@types/node@18.11.18:
     resolution: {integrity: sha512-DHQpWGjyQKSHj3ebjFI/wRKcqQcdR+MoFBygntYOZytCqNfkd2ZC4ARDJ2DQqhjH5p85Nnd3jhUJIXrszFX/JA==}
 
-  /@types/node@18.16.3:
-    resolution: {integrity: sha512-OPs5WnnT1xkCBiuQrZA4+YAV4HEJejmHneyraIaxsbev5yCEr6KMwINNFP9wQeFIw8FWcoTqF3vQsa5CDaI+8Q==}
-    dev: true
-
-  /@types/node@20.2.5:
-    resolution: {integrity: sha512-JJulVEQXmiY9Px5axXHeYGLSjhkZEnD+MDPDGbCbIAbMslkKwmygtZFy1X6s/075Yo94sf8GuSlFfPzysQrWZQ==}
+  /@types/node@20.3.1:
+    resolution: {integrity: sha512-EhcH/wvidPy1WeML3TtYFGR83UzjxeWRen9V402T8aUGYsCHOmfoisV3ZSg03gAFIbLq8TnWOJ0f4cALtnSEUg==}
 
   /@types/nodemailer@6.4.8:
     resolution: {integrity: sha512-oVsJSCkqViCn8/pEu2hfjwVO+Gb3e+eTWjg3PcjeFKRItfKpKwHphQqbYmPQrlMk+op7pNNWPbsJIEthpFN/OQ==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/normalize-package-data@2.4.1:
@@ -7835,7 +7781,7 @@ packages:
   /@types/oauth@0.9.1:
     resolution: {integrity: sha512-a1iY62/a3yhZ7qH7cNUsxoI3U/0Fe9+RnuFrpTKr+0WVOzbKlSLojShCKe20aOD1Sppv+i8Zlq0pLDuTJnwS4A==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/offscreencanvas@2019.3.0:
@@ -7846,10 +7792,10 @@ packages:
     resolution: {integrity: sha512-PGcyveRIpL1XIqK8eBsmRBt76eFgtzuPiSTyKHZxnGemp2yzGzWpjYKAfK3wIMiU7eH+851yEpiuP8JZerTmWg==}
     dev: false
 
-  /@types/pg@8.10.1:
-    resolution: {integrity: sha512-AmEHA/XxMxemQom5iDwP62FYNkv+gDDnetRG7v2N2dPtju7UKI7FknUimcZo7SodKTHtckYPzaTqUEvUKbVJEA==}
+  /@types/pg@8.10.2:
+    resolution: {integrity: sha512-MKFs9P6nJ+LAeHLU3V0cODEOgyThJ3OAnmOlsZsxux6sfQs3HRXR5bBn7xG5DjckEFhTAxsXi7k7cd0pCMxpJw==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       pg-protocol: 1.6.0
       pg-types: 4.0.1
     dev: true
@@ -7877,11 +7823,12 @@ packages:
   /@types/qrcode@1.5.0:
     resolution: {integrity: sha512-x5ilHXRxUPIMfjtM+1vf/GPTRWZ81nqscursm5gMznJeK9M0YnZ1c3bEvRLQ0zSSgedLx1J6MGL231ObQGGhaA==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/qs@6.9.7:
     resolution: {integrity: sha512-FGa1F62FT09qcrueBA6qYTrJPVDzah9a+493+o2PCXsesWHIn27G98TsSMs3WPNbZIEj4+VJf6saSFpvD+3Zsw==}
+    dev: true
 
   /@types/random-seed@0.3.3:
     resolution: {integrity: sha512-kHsCbIRHNXJo6EN5W8EA5b4i1hdT6jaZke5crBPLUcLqaLdZ0QBq8QVMbafHzhjFF83Cl9qlee2dChD18d/kPg==}
@@ -7889,6 +7836,7 @@ packages:
 
   /@types/range-parser@1.2.4:
     resolution: {integrity: sha512-EEhsLsD6UsDM1yFhAvy0Cjr6VwmpMWqFBCb9w07wVugF7w9nfajxLuVmngTIpgS6svCnm6Vaw+MZhoDCKnOfsw==}
+    dev: true
 
   /@types/ratelimiter@3.4.4:
     resolution: {integrity: sha512-GSMb93iSA8KKFDgVL2Wzs/kqrHMJcU8xhLdwI5omoACcj7K18SacklLtY1C4G02HC5drd6GygtsIaGbfxJSe0g==}
@@ -7905,7 +7853,7 @@ packages:
   /@types/readdir-glob@1.1.1:
     resolution: {integrity: sha512-ImM6TmoF8bgOwvehGviEj3tRdRBbQujr1N+0ypaln/GWjaerOB26jb93vsRHmdMtvVQZQebOlqt2HROark87mQ==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/redis@4.0.11:
@@ -7921,7 +7869,7 @@ packages:
   /@types/responselike@1.0.0:
     resolution: {integrity: sha512-85Y2BjiufFzaMIlvJDvTTB8Fxl2xfLo4HgmHzVBz08w4wDePCTjYw66PdrolO0kzli3yam/YCgRufyo1DdQVTA==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: false
 
   /@types/sanitize-html@2.9.0:
@@ -7944,12 +7892,14 @@ packages:
 
   /@types/semver@7.5.0:
     resolution: {integrity: sha512-G8hZ6XJiHnuhQKR7ZmysCeJWE08o8T0AXtk5darsCaTVsYZhhgUrq53jizaR2FvsoeCwJhlmwTjkXBY5Pn/ZHw==}
+    dev: true
 
   /@types/serve-static@1.15.1:
     resolution: {integrity: sha512-NUo5XNiAdULrJENtJXZZ3fHtfMolzZwczzBbnAeBbqBwG+LaG6YaJtuwzwGSQZ2wsCrxjEhNNjAkKigy3n8teQ==}
     dependencies:
       '@types/mime': 3.0.1
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
+    dev: true
 
   /@types/serviceworker@0.0.67:
     resolution: {integrity: sha512-7TCH7iNsCSNb+aUD9M/36TekrWFSLCjNK8zw/3n5kOtRjbLtDfGYMXTrDnGhSfqXNwpqmt9Vd90w5C/ad1tX6Q==}
@@ -7958,7 +7908,7 @@ packages:
   /@types/set-cookie-parser@2.4.2:
     resolution: {integrity: sha512-fBZgytwhYAUkj/jC/FAV4RQ5EerRup1YQsXQCh8rZfiHkc4UahC192oH0smGwsXol3cL3A5oETuAHeQHmhXM4w==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/sharp@0.32.0:
@@ -8012,10 +7962,6 @@ packages:
     resolution: {integrity: sha512-Q5vtl1W5ue16D+nIaW8JWebSSraJVlK+EthKn7e7UcD4KWsaSJ8BqGPXNaPghgtcn/fhvrN17Tv8ksUsQpiplw==}
     dev: true
 
-  /@types/treeify@1.0.0:
-    resolution: {integrity: sha512-ONpcZAEYlbPx4EtJwfTyCDQJGUpKf4sEcuySdCVjK5Fj/3vHp5HII1fqa1/+qrsLnpYELCQTfVW/awsGJePoIg==}
-    dev: false
-
   /@types/undertaker-registry@1.0.1:
     resolution: {integrity: sha512-Z4TYuEKn9+RbNVk1Ll2SS4x1JeLHecolIbM/a8gveaHsW0Hr+RQMraZACwTO2VD7JvepgA6UO1A1VrbktQrIbQ==}
     dev: true
@@ -8023,7 +7969,7 @@ packages:
   /@types/undertaker@1.2.8:
     resolution: {integrity: sha512-gW3PRqCHYpo45XFQHJBhch7L6hytPsIe0QeLujlnFsjHPnXLhJcPdN6a9368d7aIQgH2I/dUTPFBlGeSNA3qOg==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       '@types/undertaker-registry': 1.0.1
       async-done: 1.3.2
     dev: true
@@ -8035,24 +7981,24 @@ packages:
   /@types/unzipper@0.10.6:
     resolution: {integrity: sha512-zcBj329AHgKLQyz209N/S9R0GZqXSkUQO4tJSYE3x02qg4JuDFpgKMj50r82Erk1natCWQDIvSccDddt7jPzjA==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
-  /@types/uuid@9.0.1:
-    resolution: {integrity: sha512-rFT3ak0/2trgvp4yYZo5iKFEPsET7vKydKF+VRCxlQ9bpheehyAJH89dAkaLEq/j/RZXJIqcgsmPJKUP1Z28HA==}
+  /@types/uuid@9.0.2:
+    resolution: {integrity: sha512-kNnC1GFBLuhImSnV7w4njQkUiJi0ZXUycu1rUaouPqiKlXkh77JKgdRnTAp1x5eBwcIwbtI+3otwzuIDEuDoxQ==}
     dev: true
 
   /@types/vary@1.1.0:
     resolution: {integrity: sha512-LQWqrIa0dvEOOH37lGksMEXbypRLUFqu6Gx0pmX7zIUisD2I/qaVgEX/vJ/PSVSW0Hk6yz1BNkFpqg6dZm3Wug==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/vinyl-fs@2.4.12:
     resolution: {integrity: sha512-LgBpYIWuuGsihnlF+OOWWz4ovwCYlT03gd3DuLwex50cYZLmX3yrW+sFF9ndtmh7zcZpS6Ri47PrIu+fV+sbXw==}
     dependencies:
       '@types/glob-stream': 6.1.1
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       '@types/vinyl': 2.0.7
     dev: true
 
@@ -8060,32 +8006,28 @@ packages:
     resolution: {integrity: sha512-4UqPv+2567NhMQuMLdKAyK4yzrfCqwaTt6bLhHEs8PFcxbHILsrxaY63n4wgE/BRLDWDQeI+WcTmkXKExh9hQg==}
     dependencies:
       '@types/expect': 1.20.4
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
 
   /@types/web-push@3.3.2:
     resolution: {integrity: sha512-JxWGVL/m7mWTIg4mRYO+A6s0jPmBkr4iJr39DqJpRJAc+jrPiEe1/asmkwerzRon8ZZDxaZJpsxpv0Z18Wo9gw==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/webgl-ext@0.0.30:
     resolution: {integrity: sha512-LKVgNmBxN0BbljJrVUwkxwRYqzsAEPcZOe6S2T6ZaBDIrFp0qu4FNlpc5sM1tGbXUYFgdVQIoeLk1Y1UoblyEg==}
     dev: false
 
-  /@types/webpack-env@1.18.0:
-    resolution: {integrity: sha512-56/MAlX5WMsPVbOg7tAxnYvNYMMWr/QJiIp6BxVSW3JJXUVzzOn64qW8TzQyMSqSUFM2+PVI4aUHcHOzIz/1tg==}
-    dev: false
-
   /@types/websocket@1.0.5:
     resolution: {integrity: sha512-NbsqiNX9CnEfC1Z0Vf4mE1SgAJ07JnRYcNex7AJ9zAVzmiGHmjKFEk7O4TJIsgv2B1sLEb6owKFZrACwdYngsQ==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
-  /@types/ws@8.5.4:
-    resolution: {integrity: sha512-zdQDHKUgcX/zBc4GrwsE/7dVdAD8JR4EuiAXiiUhhfyIJXXb2+PrGshFyeXWQPMmmZ2XxgaqclgpIC7eTXc1mg==}
+  /@types/ws@8.5.5:
+    resolution: {integrity: sha512-lwhs8hktwxSjf9UaZ9tG5M03PGogvFaH8gUgLNbN9HKIg0dvv6q+gkSuJ8HN4/VbyxkuLzCjlN7GquQ0gUJfIg==}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /@types/yargs-parser@21.0.0:
@@ -8108,12 +8050,12 @@ packages:
     resolution: {integrity: sha512-Cn6WYCm0tXv8p6k+A8PvbDG763EDpBoTzHdA+Q/MF6H3sapGjCm9NzoaJncJS9tUKSuCoDs9XHxYYsQDgxR6kw==}
     requiresBuild: true
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
     optional: true
 
-  /@typescript-eslint/eslint-plugin@5.59.5(@typescript-eslint/parser@5.59.5)(eslint@8.40.0)(typescript@5.0.4):
-    resolution: {integrity: sha512-feA9xbVRWJZor+AnLNAr7A8JRWeZqHUf4T9tlP+TN04b05pFVhO5eN7/O93Y/1OUlLMHKbnJisgDURs/qvtqdg==}
+  /@typescript-eslint/eslint-plugin@5.60.0(@typescript-eslint/parser@5.60.0)(eslint@8.43.0)(typescript@5.1.3):
+    resolution: {integrity: sha512-78B+anHLF1TI8Jn/cD0Q00TBYdMgjdOn980JfAVa9yw5sop8nyTfVOQAv6LWywkOGLclDBtv5z3oxN4w7jxyNg==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
       '@typescript-eslint/parser': ^5.0.0
@@ -8124,52 +8066,24 @@ packages:
         optional: true
     dependencies:
       '@eslint-community/regexpp': 4.5.0
-      '@typescript-eslint/parser': 5.59.5(eslint@8.40.0)(typescript@5.0.4)
-      '@typescript-eslint/scope-manager': 5.59.5
-      '@typescript-eslint/type-utils': 5.59.5(eslint@8.40.0)(typescript@5.0.4)
-      '@typescript-eslint/utils': 5.59.5(eslint@8.40.0)(typescript@5.0.4)
+      '@typescript-eslint/parser': 5.60.0(eslint@8.43.0)(typescript@5.1.3)
+      '@typescript-eslint/scope-manager': 5.60.0
+      '@typescript-eslint/type-utils': 5.60.0(eslint@8.43.0)(typescript@5.1.3)
+      '@typescript-eslint/utils': 5.60.0(eslint@8.43.0)(typescript@5.1.3)
       debug: 4.3.4(supports-color@8.1.1)
-      eslint: 8.40.0
+      eslint: 8.43.0
       grapheme-splitter: 1.0.4
       ignore: 5.2.4
       natural-compare-lite: 1.4.0
-      semver: 7.5.0
-      tsutils: 3.21.0(typescript@5.0.4)
-      typescript: 5.0.4
-    transitivePeerDependencies:
-      - supports-color
-    dev: true
-
-  /@typescript-eslint/eslint-plugin@5.59.8(@typescript-eslint/parser@5.59.8)(eslint@8.41.0)(typescript@5.1.3):
-    resolution: {integrity: sha512-JDMOmhXteJ4WVKOiHXGCoB96ADWg9q7efPWHRViT/f09bA8XOMLAVHHju3l0MkZnG1izaWXYmgvQcUjTRcpShQ==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    peerDependencies:
-      '@typescript-eslint/parser': ^5.0.0
-      eslint: ^6.0.0 || ^7.0.0 || ^8.0.0
-      typescript: '*'
-    peerDependenciesMeta:
-      typescript:
-        optional: true
-    dependencies:
-      '@eslint-community/regexpp': 4.5.0
-      '@typescript-eslint/parser': 5.59.8(eslint@8.41.0)(typescript@5.1.3)
-      '@typescript-eslint/scope-manager': 5.59.8
-      '@typescript-eslint/type-utils': 5.59.8(eslint@8.41.0)(typescript@5.1.3)
-      '@typescript-eslint/utils': 5.59.8(eslint@8.41.0)(typescript@5.1.3)
-      debug: 4.3.4(supports-color@8.1.1)
-      eslint: 8.41.0
-      grapheme-splitter: 1.0.4
-      ignore: 5.2.4
-      natural-compare-lite: 1.4.0
-      semver: 7.5.1
+      semver: 7.5.3
       tsutils: 3.21.0(typescript@5.1.3)
       typescript: 5.1.3
     transitivePeerDependencies:
       - supports-color
     dev: true
 
-  /@typescript-eslint/parser@5.59.5(eslint@8.40.0)(typescript@5.0.4):
-    resolution: {integrity: sha512-NJXQC4MRnF9N9yWqQE2/KLRSOLvrrlZb48NGVfBa+RuPMN6B7ZcK5jZOvhuygv4D64fRKnZI4L4p8+M+rfeQuw==}
+  /@typescript-eslint/parser@5.60.0(eslint@8.43.0)(typescript@5.1.3):
+    resolution: {integrity: sha512-jBONcBsDJ9UoTWrARkRRCgDz6wUggmH5RpQVlt7BimSwaTkTjwypGzKORXbR4/2Hqjk9hgwlon2rVQAjWNpkyQ==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
       eslint: ^6.0.0 || ^7.0.0 || ^8.0.0
@@ -8178,54 +8092,26 @@ packages:
       typescript:
         optional: true
     dependencies:
-      '@typescript-eslint/scope-manager': 5.59.5
-      '@typescript-eslint/types': 5.59.5
-      '@typescript-eslint/typescript-estree': 5.59.5(typescript@5.0.4)
+      '@typescript-eslint/scope-manager': 5.60.0
+      '@typescript-eslint/types': 5.60.0
+      '@typescript-eslint/typescript-estree': 5.60.0(typescript@5.1.3)
       debug: 4.3.4(supports-color@8.1.1)
-      eslint: 8.40.0
-      typescript: 5.0.4
-    transitivePeerDependencies:
-      - supports-color
-    dev: true
-
-  /@typescript-eslint/parser@5.59.8(eslint@8.41.0)(typescript@5.1.3):
-    resolution: {integrity: sha512-AnR19RjJcpjoeGojmwZtCwBX/RidqDZtzcbG3xHrmz0aHHoOcbWnpDllenRDmDvsV0RQ6+tbb09/kyc+UT9Orw==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    peerDependencies:
-      eslint: ^6.0.0 || ^7.0.0 || ^8.0.0
-      typescript: '*'
-    peerDependenciesMeta:
-      typescript:
-        optional: true
-    dependencies:
-      '@typescript-eslint/scope-manager': 5.59.8
-      '@typescript-eslint/types': 5.59.8
-      '@typescript-eslint/typescript-estree': 5.59.8(typescript@5.1.3)
-      debug: 4.3.4(supports-color@8.1.1)
-      eslint: 8.41.0
+      eslint: 8.43.0
       typescript: 5.1.3
     transitivePeerDependencies:
       - supports-color
     dev: true
 
-  /@typescript-eslint/scope-manager@5.59.5:
-    resolution: {integrity: sha512-jVecWwnkX6ZgutF+DovbBJirZcAxgxC0EOHYt/niMROf8p4PwxxG32Qdhj/iIQQIuOflLjNkxoXyArkcIP7C3A==}
+  /@typescript-eslint/scope-manager@5.60.0:
+    resolution: {integrity: sha512-hakuzcxPwXi2ihf9WQu1BbRj1e/Pd8ZZwVTG9kfbxAMZstKz8/9OoexIwnmLzShtsdap5U/CoQGRCWlSuPbYxQ==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     dependencies:
-      '@typescript-eslint/types': 5.59.5
-      '@typescript-eslint/visitor-keys': 5.59.5
+      '@typescript-eslint/types': 5.60.0
+      '@typescript-eslint/visitor-keys': 5.60.0
     dev: true
 
-  /@typescript-eslint/scope-manager@5.59.8:
-    resolution: {integrity: sha512-/w08ndCYI8gxGf+9zKf1vtx/16y8MHrZs5/tnjHhMLNSixuNcJavSX4wAiPf4aS5x41Es9YPCn44MIe4cxIlig==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    dependencies:
-      '@typescript-eslint/types': 5.59.8
-      '@typescript-eslint/visitor-keys': 5.59.8
-    dev: true
-
-  /@typescript-eslint/type-utils@5.59.5(eslint@8.40.0)(typescript@5.0.4):
-    resolution: {integrity: sha512-4eyhS7oGym67/pSxA2mmNq7X164oqDYNnZCUayBwJZIRVvKpBCMBzFnFxjeoDeShjtO6RQBHBuwybuX3POnDqg==}
+  /@typescript-eslint/type-utils@5.60.0(eslint@8.43.0)(typescript@5.1.3):
+    resolution: {integrity: sha512-X7NsRQddORMYRFH7FWo6sA9Y/zbJ8s1x1RIAtnlj6YprbToTiQnM6vxcMu7iYhdunmoC0rUWlca13D5DVHkK2g==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
       eslint: '*'
@@ -8234,48 +8120,23 @@ packages:
       typescript:
         optional: true
     dependencies:
-      '@typescript-eslint/typescript-estree': 5.59.5(typescript@5.0.4)
-      '@typescript-eslint/utils': 5.59.5(eslint@8.40.0)(typescript@5.0.4)
+      '@typescript-eslint/typescript-estree': 5.60.0(typescript@5.1.3)
+      '@typescript-eslint/utils': 5.60.0(eslint@8.43.0)(typescript@5.1.3)
       debug: 4.3.4(supports-color@8.1.1)
-      eslint: 8.40.0
-      tsutils: 3.21.0(typescript@5.0.4)
-      typescript: 5.0.4
-    transitivePeerDependencies:
-      - supports-color
-    dev: true
-
-  /@typescript-eslint/type-utils@5.59.8(eslint@8.41.0)(typescript@5.1.3):
-    resolution: {integrity: sha512-+5M518uEIHFBy3FnyqZUF3BMP+AXnYn4oyH8RF012+e7/msMY98FhGL5SrN29NQ9xDgvqCgYnsOiKp1VjZ/fpA==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    peerDependencies:
-      eslint: '*'
-      typescript: '*'
-    peerDependenciesMeta:
-      typescript:
-        optional: true
-    dependencies:
-      '@typescript-eslint/typescript-estree': 5.59.8(typescript@5.1.3)
-      '@typescript-eslint/utils': 5.59.8(eslint@8.41.0)(typescript@5.1.3)
-      debug: 4.3.4(supports-color@8.1.1)
-      eslint: 8.41.0
+      eslint: 8.43.0
       tsutils: 3.21.0(typescript@5.1.3)
       typescript: 5.1.3
     transitivePeerDependencies:
       - supports-color
     dev: true
 
-  /@typescript-eslint/types@5.59.5:
-    resolution: {integrity: sha512-xkfRPHbqSH4Ggx4eHRIO/eGL8XL4Ysb4woL8c87YuAo8Md7AUjyWKa9YMwTL519SyDPrfEgKdewjkxNCVeJW7w==}
+  /@typescript-eslint/types@5.60.0:
+    resolution: {integrity: sha512-ascOuoCpNZBccFVNJRSC6rPq4EmJ2NkuoKnd6LDNyAQmdDnziAtxbCGWCbefG1CNzmDvd05zO36AmB7H8RzKPA==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     dev: true
 
-  /@typescript-eslint/types@5.59.8:
-    resolution: {integrity: sha512-+uWuOhBTj/L6awoWIg0BlWy0u9TyFpCHrAuQ5bNfxDaZ1Ppb3mx6tUigc74LHcbHpOHuOTOJrBoAnhdHdaea1w==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    dev: true
-
-  /@typescript-eslint/typescript-estree@5.59.5(typescript@5.0.4):
-    resolution: {integrity: sha512-+XXdLN2CZLZcD/mO7mQtJMvCkzRfmODbeSKuMY/yXbGkzvA9rJyDY5qDYNoiz2kP/dmyAxXquL2BvLQLJFPQIg==}
+  /@typescript-eslint/typescript-estree@5.60.0(typescript@5.1.3):
+    resolution: {integrity: sha512-R43thAuwarC99SnvrBmh26tc7F6sPa2B3evkXp/8q954kYL6Ro56AwASYWtEEi+4j09GbiNAHqYwNNZuNlARGQ==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
       typescript: '*'
@@ -8283,92 +8144,43 @@ packages:
       typescript:
         optional: true
     dependencies:
-      '@typescript-eslint/types': 5.59.5
-      '@typescript-eslint/visitor-keys': 5.59.5
+      '@typescript-eslint/types': 5.60.0
+      '@typescript-eslint/visitor-keys': 5.60.0
       debug: 4.3.4(supports-color@8.1.1)
       globby: 11.1.0
       is-glob: 4.0.3
-      semver: 7.5.1
-      tsutils: 3.21.0(typescript@5.0.4)
-      typescript: 5.0.4
-    transitivePeerDependencies:
-      - supports-color
-    dev: true
-
-  /@typescript-eslint/typescript-estree@5.59.8(typescript@5.1.3):
-    resolution: {integrity: sha512-Jy/lPSDJGNow14vYu6IrW790p7HIf/SOV1Bb6lZ7NUkLc2iB2Z9elESmsaUtLw8kVqogSbtLH9tut5GCX1RLDg==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    peerDependencies:
-      typescript: '*'
-    peerDependenciesMeta:
-      typescript:
-        optional: true
-    dependencies:
-      '@typescript-eslint/types': 5.59.8
-      '@typescript-eslint/visitor-keys': 5.59.8
-      debug: 4.3.4(supports-color@8.1.1)
-      globby: 11.1.0
-      is-glob: 4.0.3
-      semver: 7.5.1
+      semver: 7.5.3
       tsutils: 3.21.0(typescript@5.1.3)
       typescript: 5.1.3
     transitivePeerDependencies:
       - supports-color
     dev: true
 
-  /@typescript-eslint/utils@5.59.5(eslint@8.40.0)(typescript@5.0.4):
-    resolution: {integrity: sha512-sCEHOiw+RbyTii9c3/qN74hYDPNORb8yWCoPLmB7BIflhplJ65u2PBpdRla12e3SSTJ2erRkPjz7ngLHhUegxA==}
+  /@typescript-eslint/utils@5.60.0(eslint@8.43.0)(typescript@5.1.3):
+    resolution: {integrity: sha512-ba51uMqDtfLQ5+xHtwlO84vkdjrqNzOnqrnwbMHMRY8Tqeme8C2Q8Fc7LajfGR+e3/4LoYiWXUM6BpIIbHJ4hQ==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     peerDependencies:
       eslint: ^6.0.0 || ^7.0.0 || ^8.0.0
     dependencies:
-      '@eslint-community/eslint-utils': 4.4.0(eslint@8.40.0)
+      '@eslint-community/eslint-utils': 4.4.0(eslint@8.43.0)
       '@types/json-schema': 7.0.11
       '@types/semver': 7.5.0
-      '@typescript-eslint/scope-manager': 5.59.5
-      '@typescript-eslint/types': 5.59.5
-      '@typescript-eslint/typescript-estree': 5.59.5(typescript@5.0.4)
-      eslint: 8.40.0
+      '@typescript-eslint/scope-manager': 5.60.0
+      '@typescript-eslint/types': 5.60.0
+      '@typescript-eslint/typescript-estree': 5.60.0(typescript@5.1.3)
+      eslint: 8.43.0
       eslint-scope: 5.1.1
-      semver: 7.5.1
+      semver: 7.5.3
     transitivePeerDependencies:
       - supports-color
       - typescript
     dev: true
 
-  /@typescript-eslint/utils@5.59.8(eslint@8.41.0)(typescript@5.1.3):
-    resolution: {integrity: sha512-Tr65630KysnNn9f9G7ROF3w1b5/7f6QVCJ+WK9nhIocWmx9F+TmCAcglF26Vm7z8KCTwoKcNEBZrhlklla3CKg==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    peerDependencies:
-      eslint: ^6.0.0 || ^7.0.0 || ^8.0.0
-    dependencies:
-      '@eslint-community/eslint-utils': 4.4.0(eslint@8.41.0)
-      '@types/json-schema': 7.0.11
-      '@types/semver': 7.5.0
-      '@typescript-eslint/scope-manager': 5.59.8
-      '@typescript-eslint/types': 5.59.8
-      '@typescript-eslint/typescript-estree': 5.59.8(typescript@5.1.3)
-      eslint: 8.41.0
-      eslint-scope: 5.1.1
-      semver: 7.5.1
-    transitivePeerDependencies:
-      - supports-color
-      - typescript
-    dev: true
-
-  /@typescript-eslint/visitor-keys@5.59.5:
-    resolution: {integrity: sha512-qL+Oz+dbeBRTeyJTIy0eniD3uvqU7x+y1QceBismZ41hd4aBSRh8UAw4pZP0+XzLuPZmx4raNMq/I+59W2lXKA==}
+  /@typescript-eslint/visitor-keys@5.60.0:
+    resolution: {integrity: sha512-wm9Uz71SbCyhUKgcaPRauBdTegUyY/ZWl8gLwD/i/ybJqscrrdVSFImpvUz16BLPChIeKBK5Fa9s6KDQjsjyWw==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     dependencies:
-      '@typescript-eslint/types': 5.59.5
-      eslint-visitor-keys: 3.4.1
-    dev: true
-
-  /@typescript-eslint/visitor-keys@5.59.8:
-    resolution: {integrity: sha512-pJhi2ms0x0xgloT7xYabil3SGGlojNNKjK/q6dB3Ey0uJLMjK2UDGJvHieiyJVW/7C3KI+Z4Q3pEHkm4ejA+xQ==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    dependencies:
-      '@typescript-eslint/types': 5.59.8
+      '@typescript-eslint/types': 5.60.0
       eslint-visitor-keys: 3.4.1
     dev: true
 
@@ -8383,7 +8195,7 @@ packages:
       '@babel/plugin-transform-react-jsx-source': 7.19.6(@babel/core@7.22.1)
       magic-string: 0.27.0
       react-refresh: 0.14.0
-      vite: 4.3.9(@types/node@20.2.5)(sass@1.62.1)
+      vite: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
     transitivePeerDependencies:
       - supports-color
     dev: true
@@ -8395,11 +8207,11 @@ packages:
       vite: ^4.0.0
       vue: ^3.2.25
     dependencies:
-      vite: 4.3.9(@types/node@20.2.5)(sass@1.62.1)
+      vite: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
       vue: 3.3.4
 
-  /@vitest/coverage-c8@0.31.4(vitest@0.31.4):
-    resolution: {integrity: sha512-VPx368m4DTcpA/P0v3YdVxl4QOSh1DbUcXURLRvDShrIB5KxOgfzw4Bn2R8AhAe/GyiWW/FIsJ/OJdYXCCiC1w==}
+  /@vitest/coverage-c8@0.32.2(vitest@0.32.2):
+    resolution: {integrity: sha512-z07kMTN6e4t1jDY4XXU6W1LxCb3V5Rw7KAZId4VM6BCIGLGz1QqwH9UWYWv7LemqQVnARl5CwaDDwVrkcYgwPg==}
     peerDependencies:
       vitest: '>=0.30.0 <1'
     dependencies:
@@ -8408,95 +8220,68 @@ packages:
       magic-string: 0.30.0
       picocolors: 1.0.0
       std-env: 3.3.2
-      vitest: 0.31.4(happy-dom@9.20.3)(sass@1.62.1)
+      vitest: 0.32.2(happy-dom@9.20.3)(sass@1.63.6)
     dev: true
 
-  /@vitest/expect@0.31.4:
-    resolution: {integrity: sha512-tibyx8o7GUyGHZGyPgzwiaPaLDQ9MMuCOrc03BYT0nryUuhLbL7NV2r/q98iv5STlwMgaKuFJkgBW/8iPKwlSg==}
+  /@vitest/expect@0.32.2:
+    resolution: {integrity: sha512-6q5yzweLnyEv5Zz1fqK5u5E83LU+gOMVBDuxBl2d2Jfx1BAp5M+rZgc5mlyqdnxquyoiOXpXmFNkcGcfFnFH3Q==}
     dependencies:
-      '@vitest/spy': 0.31.4
-      '@vitest/utils': 0.31.4
+      '@vitest/spy': 0.32.2
+      '@vitest/utils': 0.32.2
       chai: 4.3.7
     dev: true
 
-  /@vitest/runner@0.31.4:
-    resolution: {integrity: sha512-Wgm6UER+gwq6zkyrm5/wbpXGF+g+UBB78asJlFkIOwyse0pz8lZoiC6SW5i4gPnls/zUcPLWS7Zog0LVepXnpg==}
+  /@vitest/runner@0.32.2:
+    resolution: {integrity: sha512-06vEL0C1pomOEktGoLjzZw+1Fb+7RBRhmw/06WkDrd1akkT9i12su0ku+R/0QM69dfkIL/rAIDTG+CSuQVDcKw==}
     dependencies:
-      '@vitest/utils': 0.31.4
+      '@vitest/utils': 0.32.2
       concordance: 5.0.4
       p-limit: 4.0.0
       pathe: 1.1.0
     dev: true
 
-  /@vitest/snapshot@0.31.4:
-    resolution: {integrity: sha512-LemvNumL3NdWSmfVAMpXILGyaXPkZbG5tyl6+RQSdcHnTj6hvA49UAI8jzez9oQyE/FWLKRSNqTGzsHuk89LRA==}
+  /@vitest/snapshot@0.32.2:
+    resolution: {integrity: sha512-JwhpeH/PPc7GJX38vEfCy9LtRzf9F4er7i4OsAJyV7sjPwjj+AIR8cUgpMTWK4S3TiamzopcTyLsZDMuldoi5A==}
     dependencies:
       magic-string: 0.30.0
       pathe: 1.1.0
       pretty-format: 27.5.1
     dev: true
 
-  /@vitest/spy@0.31.4:
-    resolution: {integrity: sha512-3ei5ZH1s3aqbEyftPAzSuunGICRuhE+IXOmpURFdkm5ybUADk+viyQfejNk6q8M5QGX8/EVKw+QWMEP3DTJDag==}
+  /@vitest/spy@0.32.2:
+    resolution: {integrity: sha512-Q/ZNILJ4ca/VzQbRM8ur3Si5Sardsh1HofatG9wsJY1RfEaw0XKP8IVax2lI1qnrk9YPuG9LA2LkZ0EI/3d4ug==}
     dependencies:
       tinyspy: 2.1.0
     dev: true
 
-  /@vitest/utils@0.31.4:
-    resolution: {integrity: sha512-DobZbHacWznoGUfYU8XDPY78UubJxXfMNY1+SUdOp1NsI34eopSA6aZMeaGu10waSOeYwE8lxrd/pLfT0RMxjQ==}
+  /@vitest/utils@0.32.2:
+    resolution: {integrity: sha512-lnJ0T5i03j0IJaeW73hxe2AuVnZ/y1BhhCOuIcl9LIzXnbpXJT9Lrt6brwKHXLOiA7MZ6N5hSJjt0xE1dGNCzQ==}
     dependencies:
-      concordance: 5.0.4
+      diff-sequences: 29.4.3
       loupe: 2.3.6
       pretty-format: 27.5.1
     dev: true
 
-  /@volar/language-core@1.4.1:
-    resolution: {integrity: sha512-EIY+Swv+TjsWpxOxujjMf1ZXqOjg9MT2VMXZ+1dKva0wD8W0L6EtptFFcCJdBbcKmGMFkr57Qzz9VNMWhs3jXQ==}
+  /@volar/language-core@1.7.8:
+    resolution: {integrity: sha512-TPklg4c2e/f1xB/MGZEiQc3AWG+dH64ZfBlYjFB8nNaWJt4Z4k+IHBhmaP52APG+5PHFerwiWI9oF002RrRTPA==}
     dependencies:
-      '@volar/source-map': 1.4.1
+      '@volar/source-map': 1.7.8
     dev: true
 
-  /@volar/source-map@1.4.1:
-    resolution: {integrity: sha512-bZ46ad72dsbzuOWPUtJjBXkzSQzzSejuR3CT81+GvTEI2E994D8JPXzM3tl98zyCNnjgs4OkRyliImL1dvJ5BA==}
+  /@volar/source-map@1.7.8:
+    resolution: {integrity: sha512-g2dtC2kOghvfzMDWeODIo4HO1Ml4hxzPTZyAFDz+YhRF9HjZYJSCaWaVuPZ+z0kY+T2daOHYA10GdrWQ5q0teA==}
     dependencies:
-      muggle-string: 0.2.2
+      muggle-string: 0.3.1
     dev: true
 
-  /@volar/typescript@1.4.1-patch.2(typescript@5.1.3):
-    resolution: {integrity: sha512-lPFYaGt8OdMEzNGJJChF40uYqMO4Z/7Q9fHPQC/NRVtht43KotSXLrkPandVVMf9aPbiJ059eAT+fwHGX16k4w==}
-    peerDependencies:
-      typescript: '*'
+  /@volar/typescript@1.7.8:
+    resolution: {integrity: sha512-NDcI5ZQcdr8kgxzMQrhSSWIM8Tl0MbMFrkvJPTjfm2rdAQZPFT8zv3LrEW9Fqh0e9z2YbCry7jr4a/GShBqeDA==}
     dependencies:
-      '@volar/language-core': 1.4.1
-      typescript: 5.1.3
+      '@volar/language-core': 1.7.8
     dev: true
 
-  /@volar/vue-language-core@1.6.5:
-    resolution: {integrity: sha512-IF2b6hW4QAxfsLd5mePmLgtkXzNi+YnH6ltCd80gb7+cbdpFMjM1I+w+nSg2kfBTyfu+W8useCZvW89kPTBpzg==}
-    dependencies:
-      '@volar/language-core': 1.4.1
-      '@volar/source-map': 1.4.1
-      '@vue/compiler-dom': 3.3.4
-      '@vue/compiler-sfc': 3.3.4
-      '@vue/reactivity': 3.3.4
-      '@vue/shared': 3.3.4
-      minimatch: 9.0.0
-      muggle-string: 0.2.2
-      vue-template-compiler: 2.7.14
-    dev: true
-
-  /@volar/vue-typescript@1.6.5(typescript@5.1.3):
-    resolution: {integrity: sha512-er9rVClS4PHztMUmtPMDTl+7c7JyrxweKSAEe/o/Noeq2bQx6v3/jZHVHBe8ZNUti5ubJL/+Tg8L3bzmlalV8A==}
-    peerDependencies:
-      typescript: '*'
-    dependencies:
-      '@volar/typescript': 1.4.1-patch.2(typescript@5.1.3)
-      '@volar/vue-language-core': 1.6.5
-      typescript: 5.1.3
-    dev: true
-
-  /@vue-macros/common@1.3.3(rollup@3.23.0)(vue@3.3.4):
-    resolution: {integrity: sha512-bjHomaf3mu+ARMD4DX22C/lLVVocbmwgcLH7bg1rK4kB5ghesgShZTQIrNR6ZjifQmdGc/2jjZ/25kSb364uEA==}
+  /@vue-macros/common@1.4.0(rollup@3.25.1)(vue@3.3.4):
+    resolution: {integrity: sha512-Wnpk6OVPYw7ZrrShOS7RZL5AINFbuQWfkNCVWVESSPY+8id75YOKGzMs4X5YcNayywdSGEvV7ntVJ2RQ+ez21A==}
     engines: {node: '>=16.14.0'}
     peerDependencies:
       vue: ^2.7.0 || ^3.2.25
@@ -8505,8 +8290,9 @@ packages:
         optional: true
     dependencies:
       '@babel/types': 7.22.4
-      '@rollup/pluginutils': 5.0.2(rollup@3.23.0)
+      '@rollup/pluginutils': 5.0.2(rollup@3.25.1)
       '@vue/compiler-sfc': 3.3.4
+      ast-kit: 0.6.5(rollup@3.25.1)
       local-pkg: 0.4.3
       magic-string-ast: 0.1.2
       vue: 3.3.4
@@ -8514,14 +8300,14 @@ packages:
       - rollup
     dev: false
 
-  /@vue-macros/reactivity-transform@0.3.9(rollup@3.23.0)(vue@3.3.4):
-    resolution: {integrity: sha512-lzzH2qzIxc1LWRrSR+ax0TVeBTgwTpG9qTZOo4Au+ODgJyXpIWHGCnc9rjcxGfu6LitjZ75NmyjbEnaEkomefw==}
+  /@vue-macros/reactivity-transform@0.3.10(rollup@3.25.1)(vue@3.3.4):
+    resolution: {integrity: sha512-I6o4GfXXRg7zD3NgDxA0SU2ASCV5BB1LUW3WbFINxEu5WYvNXfSwzkhzC01z4kmtpXv2HMD65Ffi3ajpIugSog==}
     engines: {node: '>=16.14.0'}
     peerDependencies:
       vue: ^2.7.0 || ^3.2.25
     dependencies:
       '@babel/parser': 7.22.4
-      '@vue-macros/common': 1.3.3(rollup@3.23.0)(vue@3.3.4)
+      '@vue-macros/common': 1.4.0(rollup@3.25.1)(vue@3.3.4)
       '@vue/compiler-core': 3.3.4
       '@vue/shared': 3.3.4
       magic-string: 0.30.0
@@ -8565,6 +8351,25 @@ packages:
       '@vue/compiler-dom': 3.3.4
       '@vue/shared': 3.3.4
 
+  /@vue/language-core@1.8.1(typescript@5.1.3):
+    resolution: {integrity: sha512-pumv3k4J7P58hVh4YGRM9Qz3HaAr4TlFWM9bnVOkZ/2K9o2CK1lAP2y9Jw+Z0+mNL4F2uWQqnAPzj3seLyfpDA==}
+    peerDependencies:
+      typescript: '*'
+    peerDependenciesMeta:
+      typescript:
+        optional: true
+    dependencies:
+      '@volar/language-core': 1.7.8
+      '@volar/source-map': 1.7.8
+      '@vue/compiler-dom': 3.3.4
+      '@vue/reactivity': 3.3.4
+      '@vue/shared': 3.3.4
+      minimatch: 9.0.0
+      muggle-string: 0.3.1
+      typescript: 5.1.3
+      vue-template-compiler: 2.7.14
+    dev: true
+
   /@vue/reactivity-transform@3.3.4:
     resolution: {integrity: sha512-MXgwjako4nu5WFLAjpBnCj/ieqcjE2aJBINUNQzkZQfzIZA4xn+0fV1tIYBJvvva3N3OvKGofRLvQIwEQPpaXw==}
     dependencies:
@@ -8616,6 +8421,15 @@ packages:
       '@vue/server-renderer': 3.3.4(vue@3.3.4)
     dev: true
 
+  /@vue/typescript@1.8.1(typescript@5.1.3):
+    resolution: {integrity: sha512-nQpo55j/roie8heCfqyXHnyayqD5+p4/0fzfxH4ZuHf7NSBQS791PNv7ztp2CCOjnGAiaiCMdtC9rc6oriyPUg==}
+    dependencies:
+      '@volar/typescript': 1.7.8
+      '@vue/language-core': 1.8.1(typescript@5.1.3)
+    transitivePeerDependencies:
+      - typescript
+    dev: true
+
   /@webgpu/types@0.1.30:
     resolution: {integrity: sha512-9AXJSmL3MzY8ZL//JjudA//q+2kBRGhLBFpkdGksWIuxrMy81nFrCzj2Am+mbh8WoU6rXmv7cY5E3rdlyru2Qg==}
     dev: false
@@ -8625,43 +8439,6 @@ packages:
     engines: {node: '>=10.0.0'}
     dev: true
 
-  /@yarnpkg/core@2.4.0:
-    resolution: {integrity: sha512-FYjcPNTfDfMKLFafQPt49EY28jnYC82Z2S7oMwLPUh144BL8v8YXzb4aCnFyi5nFC5h2kcrJfZh7+Pm/qvCqGw==}
-    engines: {node: '>=10.19.0'}
-    dependencies:
-      '@arcanis/slice-ansi': 1.1.1
-      '@types/semver': 7.5.0
-      '@types/treeify': 1.0.0
-      '@yarnpkg/fslib': 2.10.2
-      '@yarnpkg/json-proxy': 2.1.1
-      '@yarnpkg/libzip': 2.3.0
-      '@yarnpkg/parsers': 2.5.1
-      '@yarnpkg/pnp': 2.3.2
-      '@yarnpkg/shell': 2.4.1
-      binjumper: 0.1.4
-      camelcase: 5.3.1
-      chalk: 3.0.0
-      ci-info: 2.0.0
-      clipanion: 2.6.2
-      cross-spawn: 7.0.3
-      diff: 4.0.2
-      globby: 11.1.0
-      got: 11.8.5
-      json-file-plus: 3.3.1
-      lodash: 4.17.21
-      micromatch: 4.0.5
-      mkdirp: 0.5.6
-      p-limit: 2.3.0
-      pluralize: 7.0.0
-      pretty-bytes: 5.6.0
-      semver: 7.5.1
-      stream-to-promise: 2.2.0
-      tar-stream: 2.2.0
-      treeify: 1.1.0
-      tslib: 1.14.1
-      tunnel: 0.0.6
-    dev: false
-
   /@yarnpkg/esbuild-plugin-pnp@3.0.0-rc.15(esbuild@0.17.18):
     resolution: {integrity: sha512-kYzDJO5CA9sy+on/s2aIW0411AklfCi8Ck/4QDivOqsMKpStZA2SsR+X27VTggGwpStWaLrjJcDcdDMowtG8MA==}
     engines: {node: '>=14.15.0'}
@@ -8669,69 +8446,9 @@ packages:
       esbuild: '>=0.10.0'
     dependencies:
       esbuild: 0.17.18
-      tslib: 2.5.2
+      tslib: 2.5.3
     dev: true
 
-  /@yarnpkg/fslib@2.10.2:
-    resolution: {integrity: sha512-6WfQrPEV8QVpDPw5kd5s5jsb3QLqwVFSGZy3rEjl3p2FZ3OtIfYcLbFirOxXj2jXiKQDe7XbYsw1WjSf8K94gw==}
-    engines: {node: '>=12 <14 || 14.2 - 14.9 || >14.10.0'}
-    dependencies:
-      '@yarnpkg/libzip': 2.3.0
-      tslib: 1.14.1
-    dev: false
-
-  /@yarnpkg/json-proxy@2.1.1:
-    resolution: {integrity: sha512-meUiCAgCYpXTH1qJfqfz+dX013ohW9p2dKfwIzUYAFutH+lsz1eHPBIk72cuCV84adh9gX6j66ekBKH/bIhCQw==}
-    engines: {node: '>=12 <14 || 14.2 - 14.9 || >14.10.0'}
-    dependencies:
-      '@yarnpkg/fslib': 2.10.2
-      tslib: 1.14.1
-    dev: false
-
-  /@yarnpkg/libzip@2.3.0:
-    resolution: {integrity: sha512-6xm38yGVIa6mKm/DUCF2zFFJhERh/QWp1ufm4cNUvxsONBmfPg8uZ9pZBdOmF6qFGr/HlT6ABBkCSx/dlEtvWg==}
-    engines: {node: '>=12 <14 || 14.2 - 14.9 || >14.10.0'}
-    dependencies:
-      '@types/emscripten': 1.39.6
-      tslib: 1.14.1
-    dev: false
-
-  /@yarnpkg/lockfile@1.1.0:
-    resolution: {integrity: sha512-GpSwvyXOcOOlV70vbnzjj4fW5xW/FdUF6nQEt1ENy7m4ZCczi1+/buVUPAqmGfqznsORNFzUMjctTIp8a9tuCQ==}
-    dev: false
-
-  /@yarnpkg/parsers@2.5.1:
-    resolution: {integrity: sha512-KtYN6Ez3x753vPF9rETxNTPnPjeaHY11Exlpqb4eTII7WRlnGiZ5rvvQBau4R20Ik5KBv+vS3EJEcHyCunwzzw==}
-    engines: {node: '>=12 <14 || 14.2 - 14.9 || >14.10.0'}
-    dependencies:
-      js-yaml: 3.14.1
-      tslib: 1.14.1
-    dev: false
-
-  /@yarnpkg/pnp@2.3.2:
-    resolution: {integrity: sha512-JdwHu1WBCISqJEhIwx6Hbpe8MYsYbkGMxoxolkDiAeJ9IGEe08mQcbX1YmUDV1ozSWlm9JZE90nMylcDsXRFpA==}
-    engines: {node: '>=10.19.0'}
-    dependencies:
-      '@types/node': 13.13.52
-      '@yarnpkg/fslib': 2.10.2
-      tslib: 1.14.1
-    dev: false
-
-  /@yarnpkg/shell@2.4.1:
-    resolution: {integrity: sha512-oNNJkH8ZI5uwu0dMkJf737yMSY1WXn9gp55DqSA5wAOhKvV5DJTXFETxkVgBQhO6Bow9tMGSpvowTMD/oAW/9g==}
-    engines: {node: '>=10.19.0'}
-    hasBin: true
-    dependencies:
-      '@yarnpkg/fslib': 2.10.2
-      '@yarnpkg/parsers': 2.5.1
-      clipanion: 2.6.2
-      cross-spawn: 7.0.3
-      fast-glob: 3.2.12
-      micromatch: 4.0.5
-      stream-buffers: 3.0.2
-      tslib: 1.14.1
-    dev: false
-
   /@zxing/text-encoding@0.9.0:
     resolution: {integrity: sha512-U/4aVJ2mxI0aDNI8Uq0wEhMgY+u4CNtEb0om3+y3+niDAsoTCOB33UF0sxpzqzdqXLqmvc+vZyAt4O8pPdfkwA==}
     requiresBuild: true
@@ -8771,12 +8488,12 @@ packages:
       acorn: 7.4.1
     dev: true
 
-  /acorn-jsx@5.3.2(acorn@8.8.2):
+  /acorn-jsx@5.3.2(acorn@8.9.0):
     resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==}
     peerDependencies:
       acorn: ^6.0.0 || ^7.0.0 || ^8.0.0
     dependencies:
-      acorn: 8.8.2
+      acorn: 8.9.0
     dev: true
 
   /acorn-walk@7.2.0:
@@ -8794,8 +8511,8 @@ packages:
     engines: {node: '>=0.4.0'}
     hasBin: true
 
-  /acorn@8.8.2:
-    resolution: {integrity: sha512-xjIYgE8HBrkpd/sJqOGNspf8uHG+NOHGOw6a/Urj8taM2EXfdNAH2oFcPeIFfsv3+kz/mJrS5VuMqbNLjCa2vw==}
+  /acorn@8.9.0:
+    resolution: {integrity: sha512-jaVNAFBHNLXspO543WnNNPZFRtavh3skAkITqD0/2aeMkKZTN+254PyhwxFYrk3vQ1xfY+2wbesJMs/JC8/PwQ==}
     engines: {node: '>=0.4.0'}
     hasBin: true
 
@@ -8831,6 +8548,15 @@ packages:
     transitivePeerDependencies:
       - supports-color
 
+  /agent-base@7.1.0:
+    resolution: {integrity: sha512-o/zjMZRhJxny7OyEF+Op8X+efiELC7k7yOjMzgfzVqOzXqkBkWI79YoTdOtsuWd5BWhAGAuOY/Xa6xpiaWXiNg==}
+    engines: {node: '>= 14'}
+    dependencies:
+      debug: 4.3.4(supports-color@8.1.1)
+    transitivePeerDependencies:
+      - supports-color
+    dev: false
+
   /agentkeepalive@4.2.1:
     resolution: {integrity: sha512-Zn4cw2NEqd+9fiSVWMscnjyQ1a8Yfoc5oBajLeo5w+YBHgDUcEBY2hS4YpTz6iN5f/2zQiktcuM6tS8x1p9dpA==}
     engines: {node: '>= 8.0.0'}
@@ -8927,6 +8653,11 @@ packages:
     resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==}
     engines: {node: '>=8'}
 
+  /ansi-regex@6.0.1:
+    resolution: {integrity: sha512-n5M855fKb2SsfMIiFFoVrABHJC8QtHwVx+mHWP3QcEqBHYienj5dHSgjbxtC0WEZXYt4wcD6zrQElDPhFuZgfA==}
+    engines: {node: '>=12'}
+    dev: false
+
   /ansi-styles@2.2.1:
     resolution: {integrity: sha512-kmCevFghRiWM7HB5zTPULl4r9bVFSWjz62MhqizDGUrq2NWuNMQyuv4tHHoKJHs69M/MF64lEcHdYIocrdWQYA==}
     engines: {node: '>=0.10.0'}
@@ -8937,6 +8668,7 @@ packages:
     engines: {node: '>=4'}
     dependencies:
       color-convert: 1.9.3
+    dev: true
 
   /ansi-styles@4.3.0:
     resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==}
@@ -8949,6 +8681,11 @@ packages:
     engines: {node: '>=10'}
     dev: true
 
+  /ansi-styles@6.2.1:
+    resolution: {integrity: sha512-bN798gFfQX+viw3R7yrGWRqnrN2oRkEkUjjl4JNn4E8GxxbjtG3FbrEIIY3l8/hrwUwIeCZvi4QuOTP4MErVug==}
+    engines: {node: '>=12'}
+    dev: false
+
   /ansi-wrap@0.1.0:
     resolution: {integrity: sha512-ZyznvL8k/FZeQHr2T6LzcJ/+vBApDnMNZvfVFy3At0knswWd6rJ3/0Hhmpu8oqa6C92npmozs890sX9Dl6q+Qw==}
     engines: {node: '>=0.10.0'}
@@ -9201,6 +8938,7 @@ packages:
       is-nan: 1.3.2
       object-is: 1.1.5
       util: 0.12.5
+    dev: true
 
   /assertion-error@1.1.0:
     resolution: {integrity: sha512-jgsaNduz+ndvGyFt3uSuWqvy4lCnIJiovtouQN5JZHOKCS2QuhEdbcQHFhVksz2N2U9hXJo8odG7ETyWlEeuDw==}
@@ -9210,6 +8948,17 @@ packages:
     resolution: {integrity: sha512-Q+JC7Whu8HhmTdBph/Tq59IoRtoy6KAm5zzPv00WdujX82lbAL8K7WVjne7vdCsAmbF4AYaDOPyO3k0kl8qIrw==}
     engines: {node: '>=0.10.0'}
 
+  /ast-kit@0.6.5(rollup@3.25.1):
+    resolution: {integrity: sha512-XCg0VWvmWU2T/6aMp8VRfJWZ6LZv1P0o8otWY7RAGtfKj0qGi45vtnKNkltJhu9tmbQNZxv+gJA4o7FtLDfmWg==}
+    engines: {node: '>=16.14.0'}
+    dependencies:
+      '@babel/parser': 7.22.4
+      '@rollup/pluginutils': 5.0.2(rollup@3.25.1)
+      pathe: 1.1.0
+    transitivePeerDependencies:
+      - rollup
+    dev: false
+
   /ast-types@0.14.2:
     resolution: {integrity: sha512-O0yuUDnZeQDL+ncNGlJ78BiO4jnYI3bvMsD5prT0/nsgijG/LpNBIr63gTjVTNsiGkgQhiyCShTgxt8oXOrklA==}
     engines: {node: '>=4'}
@@ -9221,14 +8970,15 @@ packages:
     resolution: {integrity: sha512-c27loCv9QkZinsa5ProX751khO9DJl/AcB5c2KNtA6NRvHKS0PgLfcftz72KVq504vB0Gku5s2kUZzDBvQWvHg==}
     engines: {node: '>=4'}
     dependencies:
-      tslib: 2.5.2
+      tslib: 2.5.3
     dev: true
 
   /ast-types@0.16.1:
     resolution: {integrity: sha512-6t10qk83GOG8p0vKmaCr8eiilZwO171AvbROMtvvNiwrTly62t+7XkA8RdIIVbpMhCASAsxgAzdRSwh6nw/5Dg==}
     engines: {node: '>=4'}
     dependencies:
-      tslib: 2.5.2
+      tslib: 2.5.3
+    dev: true
 
   /astral-regex@2.0.0:
     resolution: {integrity: sha512-Z7tMw1ytTXt5jqMcOP+OQteU1VuNK9Y02uuJtKQ1Sv69jXQKKg5cibLwGJow8yzZP+eAc18EmLGPal0bp36rvQ==}
@@ -9310,9 +9060,10 @@ packages:
   /available-typed-arrays@1.0.5:
     resolution: {integrity: sha512-DMD0KiN46eipeziST1LPP/STfDU0sufISXmjSgvVsoU2tqxctQeASejWcfNtxYKqETM1UxQ8sp2OrSBWpHY6sw==}
     engines: {node: '>= 0.4'}
+    dev: true
 
-  /avvio@8.2.0:
-    resolution: {integrity: sha512-bbCQdg7bpEv6kGH41RO/3B2/GMMmJSo2iBK+X8AWN9mujtfUipMDfIjsgHCfpnKqoGEQrrmCDKSa5OQ19+fDmg==}
+  /avvio@8.2.1:
+    resolution: {integrity: sha512-TAlMYvOuwGyLK3PfBb5WKBXZmXz2fVCgv23d6zZFdle/q3gPjmxBaeuC0pY0Dzs5PWMSgfqqEZkrye19GlDTgw==}
     dependencies:
       archy: 1.0.0
       debug: 4.3.4(supports-color@8.1.1)
@@ -9600,7 +9351,7 @@ packages:
     engines: {node: '>=12'}
     dependencies:
       bin-version: 6.0.0
-      semver: 7.5.1
+      semver: 7.5.3
       semver-truncate: 2.0.0
     dev: false
 
@@ -9628,11 +9379,6 @@ packages:
     engines: {node: '>=0.8'}
     dev: false
 
-  /binjumper@0.1.4:
-    resolution: {integrity: sha512-Gdxhj+U295tIM6cO4bJO1jsvSjBVHNpj2o/OwW7pqDEtaqF6KdOxjtbo93jMMKAkP7+u09+bV8DhSqjIv4qR3w==}
-    engines: {node: '>=10.12.0'}
-    dev: false
-
   /bl@4.1.0:
     resolution: {integrity: sha512-1W07cM9gS6DcLperZfFSj+bWLtaPGSOHWhPiGzXmvVJbRLdG82sH/Kn8EtW1VqWVA54AKf2h5k5BbnIbwF3h6w==}
     dependencies:
@@ -9849,16 +9595,16 @@ packages:
     dependencies:
       node-gyp-build: 4.6.0
 
-  /bullmq@3.15.0:
-    resolution: {integrity: sha512-U0LSRjuoyIBpnE62T4maCWMYEt3qdBCa1lnlPxYKQmRF/Y+FQ9W6iW5JvNNN+NA5Jet7k0uX71a93EX1zGnrhw==}
+  /bullmq@4.1.0:
+    resolution: {integrity: sha512-5vQ5hQmI4qmk1afGEBIBwKpgrufhtQVbVvckLQelIc2Tp8sQm9+QXXL1cauHV4UU3xqMRLQXL5d+U/0uzGHoFA==}
     dependencies:
       cron-parser: 4.8.1
       glob: 8.1.0
       ioredis: 5.3.2
       lodash: 4.17.21
       msgpackr: 1.9.2
-      semver: 7.5.1
-      tslib: 2.5.2
+      semver: 7.5.3
+      tslib: 2.5.3
       uuid: 9.0.0
     transitivePeerDependencies:
       - supports-color
@@ -9905,30 +9651,22 @@ packages:
     engines: {node: '>=8'}
     dev: true
 
-  /cacache@16.1.3:
-    resolution: {integrity: sha512-/+Emcj9DAXxX4cwlLmRI9c166RuL3w30zp4R7Joiv2cQTtTtA+jeuCAjH3ZlGnYS3tKENSrKhAzVVP9GVyzeYQ==}
-    engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0}
+  /cacache@17.1.3:
+    resolution: {integrity: sha512-jAdjGxmPxZh0IipMdR7fK/4sDSrHMLUV0+GvVUsjwyGNKHsh79kW/otg+GkbXwl6Uzvy9wsvHOX4nUoWldeZMg==}
+    engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0}
     dependencies:
-      '@npmcli/fs': 2.1.2
-      '@npmcli/move-file': 2.0.1
-      chownr: 2.0.0
-      fs-minipass: 2.1.0
-      glob: 8.1.0
-      infer-owner: 1.0.4
+      '@npmcli/fs': 3.1.0
+      fs-minipass: 3.0.2
+      glob: 10.3.0
       lru-cache: 7.14.1
-      minipass: 3.3.6
+      minipass: 5.0.0
       minipass-collect: 1.0.2
       minipass-flush: 1.0.5
       minipass-pipeline: 1.2.4
-      mkdirp: 1.0.4
       p-map: 4.0.0
-      promise-inflight: 1.0.1
-      rimraf: 3.0.2
-      ssri: 9.0.1
+      ssri: 10.0.4
       tar: 6.1.13
-      unique-filename: 2.0.1
-    transitivePeerDependencies:
-      - bluebird
+      unique-filename: 3.0.0
     dev: false
 
   /cache-base@1.0.1:
@@ -10101,6 +9839,7 @@ packages:
       ansi-styles: 3.2.1
       escape-string-regexp: 1.0.5
       supports-color: 5.5.0
+    dev: true
 
   /chalk@3.0.0:
     resolution: {integrity: sha512-4D3B6Wf41KOYRFdszmDqMCGq5VV/uMAB273JILmO+3jAlh8X4qDtdtgCR3fxtbLEMzSx22QdhnDcJvu2u1fVwg==}
@@ -10108,6 +9847,7 @@ packages:
     dependencies:
       ansi-styles: 4.3.0
       supports-color: 7.2.0
+    dev: true
 
   /chalk@4.1.1:
     resolution: {integrity: sha512-diHzdDKxcU+bAsUboHLPEDQiw0qEe0qd7SYUn3HgcFlWgbDcfLGswOHYeGrHKzG9z6UYf01d9VFMfZxPM1xZSg==}
@@ -10259,20 +9999,9 @@ packages:
     resolution: {integrity: sha512-bIomtDF5KGpdogkLd9VspvFzk9KfpyyGlS8YFVZl7TGPBHL5snIOnxeshwVgPteQ9b4Eydl+pVbIyE1DcvCWgQ==}
     engines: {node: '>=10'}
 
-  /chromatic@6.18.0:
-    resolution: {integrity: sha512-Sj7xMFGQ6jSTBrsdgMMjSQAP2OMNogg4GXV4djf4kAp6Dp+pY4FwByIagvbtQRjC33kQVi592FS52vMBOBMEzw==}
+  /chromatic@6.19.9:
+    resolution: {integrity: sha512-UHrPbPoLnJwd063cRSO0U865VhcATykpMiHsAnNFz5EFRsBvM9wefqyS2Z6W8Ti9J7Fjrf4MV4PA+Q5k2lhFfQ==}
     hasBin: true
-    dependencies:
-      '@discoveryjs/json-ext': 0.5.7
-      '@storybook/csf-tools': 7.0.18
-      '@types/webpack-env': 1.18.0
-      snyk-nodejs-lockfile-parser: 1.49.0
-    transitivePeerDependencies:
-      - supports-color
-    dev: false
-
-  /ci-info@2.0.0:
-    resolution: {integrity: sha512-5tK7EtrZ0N+OLFMthtqOj4fI2Jeb88C4CAZPu25LDVUgXJ0A3Js4PMGqrn0JU1W0Mh1/Z8wZzYPxqUrXeBboCQ==}
     dev: false
 
   /ci-info@3.7.1:
@@ -10355,10 +10084,6 @@ packages:
     engines: {node: '>= 10'}
     dev: true
 
-  /clipanion@2.6.2:
-    resolution: {integrity: sha512-0tOHJNMF9+4R3qcbBL+4IxLErpaYSYvzs10aXuECDbZdJOuJHdagJMAqvLdeaUQTI/o2uSCDRpet6ywDiKOAYw==}
-    dev: false
-
   /cliui@3.2.0:
     resolution: {integrity: sha512-0yayqDxWQbqk3ojkYqUKqaAQ6AfNKeKWRNA8kR0WXzAsdHpP4BIaOmMAG87JGuO6qcobyW4GjxHd9PmhEd+T9w==}
     dependencies:
@@ -10653,7 +10378,7 @@ packages:
       js-string-escape: 1.0.1
       lodash: 4.17.21
       md5-hex: 3.0.1
-      semver: 7.5.1
+      semver: 7.5.3
       well-known-symbols: 2.0.0
     dev: true
 
@@ -10756,11 +10481,11 @@ packages:
       luxon: 3.3.0
     dev: false
 
-  /cropperjs@2.0.0-beta.2:
-    resolution: {integrity: sha512-jDRSODDGKmi9vp3p/+WXkxMqV/AE+GpSld1U3cHZDRdLy9UykRzurSe8k1dR0TExn45ygCMrv31qkg+K3EeXXw==}
+  /cropperjs@2.0.0-beta.3:
+    resolution: {integrity: sha512-FmrQfDsyK/zgKd3ripivqw8XpthWd5k8TczmiA1JarXKvcC5GBzRnX9CBFls5MmkzW9WPHuX0B1TMQ1j7xP54Q==}
     dependencies:
-      '@cropper/elements': 2.0.0-beta.2
-      '@cropper/utils': 2.0.0-beta.2
+      '@cropper/elements': 2.0.0-beta.3
+      '@cropper/utils': 2.0.0-beta.3
     dev: false
 
   /cross-env@7.0.3:
@@ -10894,8 +10619,8 @@ packages:
       uniq: 1.0.1
     dev: false
 
-  /cypress@12.13.0:
-    resolution: {integrity: sha512-QJlSmdPk+53Zhy69woJMySZQJoWfEWun3X5OOenGsXjRPVfByVTHorxNehbzhZrEzH9RDUDqVcck0ahtlS+N/Q==}
+  /cypress@12.15.0:
+    resolution: {integrity: sha512-FqGbxsH+QgjStuTO9onXMIeF44eOrgVwPvlcvuzLIaePQMkl72YgBvpuHlBGRcrw3Q4SvqKfajN8iV5XWShAiQ==}
     engines: {node: ^14.0.0 || ^16.0.0 || >=18.0.0}
     hasBin: true
     requiresBuild: true
@@ -10937,7 +10662,7 @@ packages:
       pretty-bytes: 5.6.0
       proxy-from-env: 1.0.0
       request-progress: 3.0.0
-      semver: 7.5.1
+      semver: 7.5.3
       supports-color: 8.1.1
       tmp: 0.2.1
       untildify: 4.0.0
@@ -11288,11 +11013,6 @@ packages:
     engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
     dev: true
 
-  /diff@4.0.2:
-    resolution: {integrity: sha512-58lmxKSA4BNyLz+HHMUzlOEpg09FV+ev6ZMe3vJihgdxzgcwZ8VoEEPmALCZG9LmqfVoNMMKpttIYTVG6uDY7A==}
-    engines: {node: '>=0.3.1'}
-    dev: false
-
   /diff@5.1.0:
     resolution: {integrity: sha512-D+mk+qE8VC/PAUrlAU34N+VfXev0ghe5ywmpqrawphmVZc1bEfn56uo9qpyGp1p4xpzOHkSW4ztBd6L7Xx4ACw==}
     engines: {node: '>=0.3.1'}
@@ -11397,6 +11117,10 @@ packages:
       object.defaults: 1.1.0
     dev: false
 
+  /eastasianwidth@0.2.0:
+    resolution: {integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==}
+    dev: false
+
   /ecc-jsbn@0.1.2:
     resolution: {integrity: sha512-eh9O+hwRHNbG4BLTjEl3nw044CkGm5X6LoaCf7LPp7UU8Qrt47JYNi6nPX8xjW97TKGKm1ouctg0QSpZe9qrnw==}
     dependencies:
@@ -11445,6 +11169,10 @@ packages:
   /emoji-regex@8.0.0:
     resolution: {integrity: sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==}
 
+  /emoji-regex@9.2.2:
+    resolution: {integrity: sha512-L18DaJsXSUk2+42pv8mLs5jJT2hqFkFE4j21wOmgbUqsZ2hL72NsUU785g9RXgo3s0ZNgVl42TiHp3ZtOv/Vyg==}
+    dev: false
+
   /encode-utf8@1.0.3:
     resolution: {integrity: sha512-ucAnuBEhUK4boH2HjVYG5Q2mQyPorvv0u/ocS+zhdw0S8AlHYY+GOFhP1Gio5z4icpP2ivFSvhtFjQi8+T9ppw==}
     dev: false
@@ -11462,12 +11190,6 @@ packages:
     dev: false
     optional: true
 
-  /end-of-stream@1.1.0:
-    resolution: {integrity: sha512-EoulkdKF/1xa92q25PbjuDcgJ9RDHYU2Rs3SCIvs2/dSQ3BpmxneNHmA/M7fe60M3PrV7nNGTTNbkK62l6vXiQ==}
-    dependencies:
-      once: 1.3.3
-    dev: false
-
   /end-of-stream@1.4.4:
     resolution: {integrity: sha512-+uw1inIHVPQoaVuHzRyXd21icM+cnt4CzD5rW+NC1wjOUSTOs+Te7FOv7AhN7vS9x/oIyhLP5PR1H+phQAHu5Q==}
     dependencies:
@@ -11591,6 +11313,7 @@ packages:
 
   /es6-object-assign@1.1.0:
     resolution: {integrity: sha512-MEl9uirslVwqQU369iHNWZXsI8yaZYGg/D65aOgZkeyFJwHYSxilf7rQzXKI7DdDuBPrBXbfk3sl9hJhmd5AUw==}
+    dev: true
 
   /es6-promise@4.2.8:
     resolution: {integrity: sha512-HJDGx5daxeIvxdBxvG2cb9g4tEvwIk3i8+nhX0yGrYmZUzbkdg8QbDevheDB8gd0//uPj4c1EQua8Q+MViT0/w==}
@@ -11729,7 +11452,7 @@ packages:
       - supports-color
     dev: true
 
-  /eslint-module-utils@2.7.4(@typescript-eslint/parser@5.59.5)(eslint-import-resolver-node@0.3.7)(eslint@8.40.0):
+  /eslint-module-utils@2.7.4(@typescript-eslint/parser@5.60.0)(eslint-import-resolver-node@0.3.7)(eslint@8.43.0):
     resolution: {integrity: sha512-j4GT+rqzCoRKHwURX7pddtIPGySnX9Si/cgMI5ztrcqOPtk5dDEeZ34CQVPphnqkJytlc97Vuk05Um2mJ3gEQA==}
     engines: {node: '>=4'}
     peerDependencies:
@@ -11750,44 +11473,15 @@ packages:
       eslint-import-resolver-webpack:
         optional: true
     dependencies:
-      '@typescript-eslint/parser': 5.59.5(eslint@8.40.0)(typescript@5.0.4)
+      '@typescript-eslint/parser': 5.60.0(eslint@8.43.0)(typescript@5.1.3)
       debug: 3.2.7(supports-color@8.1.1)
-      eslint: 8.40.0
+      eslint: 8.43.0
       eslint-import-resolver-node: 0.3.7
     transitivePeerDependencies:
       - supports-color
     dev: true
 
-  /eslint-module-utils@2.7.4(@typescript-eslint/parser@5.59.8)(eslint-import-resolver-node@0.3.7)(eslint@8.41.0):
-    resolution: {integrity: sha512-j4GT+rqzCoRKHwURX7pddtIPGySnX9Si/cgMI5ztrcqOPtk5dDEeZ34CQVPphnqkJytlc97Vuk05Um2mJ3gEQA==}
-    engines: {node: '>=4'}
-    peerDependencies:
-      '@typescript-eslint/parser': '*'
-      eslint: '*'
-      eslint-import-resolver-node: '*'
-      eslint-import-resolver-typescript: '*'
-      eslint-import-resolver-webpack: '*'
-    peerDependenciesMeta:
-      '@typescript-eslint/parser':
-        optional: true
-      eslint:
-        optional: true
-      eslint-import-resolver-node:
-        optional: true
-      eslint-import-resolver-typescript:
-        optional: true
-      eslint-import-resolver-webpack:
-        optional: true
-    dependencies:
-      '@typescript-eslint/parser': 5.59.8(eslint@8.41.0)(typescript@5.1.3)
-      debug: 3.2.7(supports-color@8.1.1)
-      eslint: 8.41.0
-      eslint-import-resolver-node: 0.3.7
-    transitivePeerDependencies:
-      - supports-color
-    dev: true
-
-  /eslint-plugin-import@2.27.5(@typescript-eslint/parser@5.59.5)(eslint@8.40.0):
+  /eslint-plugin-import@2.27.5(@typescript-eslint/parser@5.60.0)(eslint@8.43.0):
     resolution: {integrity: sha512-LmEt3GVofgiGuiE+ORpnvP+kAm3h6MLZJ4Q5HCyHADofsb4VzXFsRiWj3c0OFiV+3DWFh0qg3v9gcPlfc3zRow==}
     engines: {node: '>=4'}
     peerDependencies:
@@ -11797,15 +11491,15 @@ packages:
       '@typescript-eslint/parser':
         optional: true
     dependencies:
-      '@typescript-eslint/parser': 5.59.5(eslint@8.40.0)(typescript@5.0.4)
+      '@typescript-eslint/parser': 5.60.0(eslint@8.43.0)(typescript@5.1.3)
       array-includes: 3.1.6
       array.prototype.flat: 1.3.1
       array.prototype.flatmap: 1.3.1
       debug: 3.2.7(supports-color@8.1.1)
       doctrine: 2.1.0
-      eslint: 8.40.0
+      eslint: 8.43.0
       eslint-import-resolver-node: 0.3.7
-      eslint-module-utils: 2.7.4(@typescript-eslint/parser@5.59.5)(eslint-import-resolver-node@0.3.7)(eslint@8.40.0)
+      eslint-module-utils: 2.7.4(@typescript-eslint/parser@5.60.0)(eslint-import-resolver-node@0.3.7)(eslint@8.43.0)
       has: 1.0.3
       is-core-module: 2.11.0
       is-glob: 4.0.3
@@ -11820,52 +11514,19 @@ packages:
       - supports-color
     dev: true
 
-  /eslint-plugin-import@2.27.5(@typescript-eslint/parser@5.59.8)(eslint@8.41.0):
-    resolution: {integrity: sha512-LmEt3GVofgiGuiE+ORpnvP+kAm3h6MLZJ4Q5HCyHADofsb4VzXFsRiWj3c0OFiV+3DWFh0qg3v9gcPlfc3zRow==}
-    engines: {node: '>=4'}
-    peerDependencies:
-      '@typescript-eslint/parser': '*'
-      eslint: ^2 || ^3 || ^4 || ^5 || ^6 || ^7.2.0 || ^8
-    peerDependenciesMeta:
-      '@typescript-eslint/parser':
-        optional: true
-    dependencies:
-      '@typescript-eslint/parser': 5.59.8(eslint@8.41.0)(typescript@5.1.3)
-      array-includes: 3.1.6
-      array.prototype.flat: 1.3.1
-      array.prototype.flatmap: 1.3.1
-      debug: 3.2.7(supports-color@8.1.1)
-      doctrine: 2.1.0
-      eslint: 8.41.0
-      eslint-import-resolver-node: 0.3.7
-      eslint-module-utils: 2.7.4(@typescript-eslint/parser@5.59.8)(eslint-import-resolver-node@0.3.7)(eslint@8.41.0)
-      has: 1.0.3
-      is-core-module: 2.11.0
-      is-glob: 4.0.3
-      minimatch: 3.1.2
-      object.values: 1.1.6
-      resolve: 1.22.1
-      semver: 6.3.0
-      tsconfig-paths: 3.14.1
-    transitivePeerDependencies:
-      - eslint-import-resolver-typescript
-      - eslint-import-resolver-webpack
-      - supports-color
-    dev: true
-
-  /eslint-plugin-vue@9.14.1(eslint@8.41.0):
-    resolution: {integrity: sha512-LQazDB1qkNEKejLe/b5a9VfEbtbczcOaui5lQ4Qw0tbRBbQYREyxxOV5BQgNDTqGPs9pxqiEpbMi9ywuIaF7vw==}
+  /eslint-plugin-vue@9.15.0(eslint@8.43.0):
+    resolution: {integrity: sha512-XYzpK6e2REli100+6iCeBA69v6Sm0D/yK2FZP+fCeNt0yH/m82qZQq+ztseyV0JsKdhFysuSEzeE1yCmSC92BA==}
     engines: {node: ^14.17.0 || >=16.0.0}
     peerDependencies:
       eslint: ^6.2.0 || ^7.0.0 || ^8.0.0
     dependencies:
-      '@eslint-community/eslint-utils': 4.4.0(eslint@8.41.0)
-      eslint: 8.41.0
+      '@eslint-community/eslint-utils': 4.4.0(eslint@8.43.0)
+      eslint: 8.43.0
       natural-compare: 1.4.0
       nth-check: 2.1.1
       postcss-selector-parser: 6.0.11
-      semver: 7.5.1
-      vue-eslint-parser: 9.3.0(eslint@8.41.0)
+      semver: 7.5.3
+      vue-eslint-parser: 9.3.1(eslint@8.43.0)
       xml-name-validator: 4.0.0
     transitivePeerDependencies:
       - supports-color
@@ -11896,65 +11557,16 @@ packages:
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     dev: true
 
-  /eslint@8.40.0:
-    resolution: {integrity: sha512-bvR+TsP9EHL3TqNtj9sCNJVAFK3fBN8Q7g5waghxyRsPLIMwL73XSKnZFK0hk/O2ANC+iAoq6PWMQ+IfBAJIiQ==}
+  /eslint@8.43.0:
+    resolution: {integrity: sha512-aaCpf2JqqKesMFGgmRPessmVKjcGXqdlAYLLC3THM8t5nBRZRQ+st5WM/hoJXkdioEXLLbXgclUpM0TXo5HX5Q==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     hasBin: true
     dependencies:
-      '@eslint-community/eslint-utils': 4.4.0(eslint@8.40.0)
+      '@eslint-community/eslint-utils': 4.4.0(eslint@8.43.0)
       '@eslint-community/regexpp': 4.5.0
       '@eslint/eslintrc': 2.0.3
-      '@eslint/js': 8.40.0
-      '@humanwhocodes/config-array': 0.11.8
-      '@humanwhocodes/module-importer': 1.0.1
-      '@nodelib/fs.walk': 1.2.8
-      ajv: 6.12.6
-      chalk: 4.1.2
-      cross-spawn: 7.0.3
-      debug: 4.3.4(supports-color@8.1.1)
-      doctrine: 3.0.0
-      escape-string-regexp: 4.0.0
-      eslint-scope: 7.2.0
-      eslint-visitor-keys: 3.4.1
-      espree: 9.5.2
-      esquery: 1.4.2
-      esutils: 2.0.3
-      fast-deep-equal: 3.1.3
-      file-entry-cache: 6.0.1
-      find-up: 5.0.0
-      glob-parent: 6.0.2
-      globals: 13.19.0
-      grapheme-splitter: 1.0.4
-      ignore: 5.2.4
-      import-fresh: 3.3.0
-      imurmurhash: 0.1.4
-      is-glob: 4.0.3
-      is-path-inside: 3.0.3
-      js-sdsl: 4.2.0
-      js-yaml: 4.1.0
-      json-stable-stringify-without-jsonify: 1.0.1
-      levn: 0.4.1
-      lodash.merge: 4.6.2
-      minimatch: 3.1.2
-      natural-compare: 1.4.0
-      optionator: 0.9.1
-      strip-ansi: 6.0.1
-      strip-json-comments: 3.1.1
-      text-table: 0.2.0
-    transitivePeerDependencies:
-      - supports-color
-    dev: true
-
-  /eslint@8.41.0:
-    resolution: {integrity: sha512-WQDQpzGBOP5IrXPo4Hc0814r4/v2rrIsB0rhT7jtunIalgg6gYXWhRMOejVO8yH21T/FGaxjmFjBMNqcIlmH1Q==}
-    engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
-    hasBin: true
-    dependencies:
-      '@eslint-community/eslint-utils': 4.4.0(eslint@8.41.0)
-      '@eslint-community/regexpp': 4.5.0
-      '@eslint/eslintrc': 2.0.3
-      '@eslint/js': 8.41.0
-      '@humanwhocodes/config-array': 0.11.8
+      '@eslint/js': 8.43.0
+      '@humanwhocodes/config-array': 0.11.10
       '@humanwhocodes/module-importer': 1.0.1
       '@nodelib/fs.walk': 1.2.8
       ajv: 6.12.6
@@ -11997,8 +11609,8 @@ packages:
     resolution: {integrity: sha512-7OASN1Wma5fum5SrNhFMAMJxOUAbhyfQ8dQ//PJaJbNw0URTPWqIghHWt1MmAANKhHZIYOHruW4Kw4ruUWOdGw==}
     engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0}
     dependencies:
-      acorn: 8.8.2
-      acorn-jsx: 5.3.2(acorn@8.8.2)
+      acorn: 8.9.0
+      acorn-jsx: 5.3.2(acorn@8.9.0)
       eslint-visitor-keys: 3.4.1
     dev: true
 
@@ -12012,6 +11624,7 @@ packages:
     resolution: {integrity: sha512-eGuFFw7Upda+g4p+QHvnW0RyTX/SVeJBDM/gCtMARO0cLuT2HcEKnTPvhjV6aGeqrCB/sbNop0Kszm0jsaWU4A==}
     engines: {node: '>=4'}
     hasBin: true
+    dev: true
 
   /esquery@1.4.2:
     resolution: {integrity: sha512-JVSoLdTlTDkmjFmab7H/9SL9qGSyjElT3myyKp7krqjVFQCDLmj1QFaCLRFBszBKI0XVZaiiXvuPIX3ZwHe1Ng==}
@@ -12067,12 +11680,6 @@ packages:
     engines: {node: '>= 0.6'}
     dev: true
 
-  /event-loop-spinner@2.2.0:
-    resolution: {integrity: sha512-KB44sV4Mv7uLIkJHJ5qhiZe5um6th2g57nHQL/uqnPHKP2IswoTRWUteEXTJQL4gW++1zqWUni+H2hGkP51c9w==}
-    dependencies:
-      tslib: 2.5.2
-    dev: false
-
   /event-stream@3.3.4:
     resolution: {integrity: sha512-QHpkERcGsR0T7Qm3HNJSyXKEEj8AHNxkY3PK8TS2KJvQ7NiSHe3DDpwVKKtoYprL/AreyzFBeIkBIWChAqn60g==}
     dependencies:
@@ -12210,6 +11817,10 @@ packages:
       jest-util: 29.5.0
     dev: true
 
+  /exponential-backoff@3.1.1:
+    resolution: {integrity: sha512-dX7e/LHVJ6W3DE1MHWi9S1EYzDESENfLrYohG2G++ovZrYOkm4Knwa0mc1cn84xJOR4KEU0WSchhLbd0UklbHw==}
+    dev: false
+
   /express@4.18.2:
     resolution: {integrity: sha512-5/PsL6iGPdfQ/lKM1UuielYgv3BUoJfz1aUwU9vHZ+J7gyvwdQXFEBIEIaxeGf0GIcreATNyBExtalisDbuMqQ==}
     engines: {node: '>= 0.10.0'}
@@ -12433,24 +12044,24 @@ packages:
     resolution: {integrity: sha512-79ak0JxddO0utAXAQ5ccKhvs6vX2MGyHHMMsmZkBANrq3hXc1CHzvNPHOcvTsVMEPl5I+NT+RO4YKMGehOfSIg==}
     dev: false
 
-  /fastify@4.17.0:
-    resolution: {integrity: sha512-tzuY1tgWJo2Y6qEKwmLhFvACUmr68Io2pqP/sDKU71KRM6A6R3DrCDqLGqANbeLZcKUfdfY58ut35CGqemcTgg==}
+  /fastify@4.18.0:
+    resolution: {integrity: sha512-L5o/2GEkBastQ3HV0dtKo7SUZ497Z1+q4fcqAoPyq6JCQ/8zdk1JQEoTQwnBWCp+EmA7AQa6mxNqSAEhzP0RwQ==}
     dependencies:
       '@fastify/ajv-compiler': 3.5.0
       '@fastify/error': 3.2.0
       '@fastify/fast-json-stringify-compiler': 4.3.0
       abstract-logging: 2.0.1
-      avvio: 8.2.0
+      avvio: 8.2.1
       fast-content-type-parse: 1.0.0
       fast-json-stringify: 5.7.0
       find-my-way: 7.6.0
-      light-my-request: 5.8.0
-      pino: 8.8.0
-      process-warning: 2.1.0
+      light-my-request: 5.10.0
+      pino: 8.14.1
+      process-warning: 2.2.0
       proxy-addr: 2.0.7
       rfdc: 1.3.0
       secure-json-parse: 2.7.0
-      semver: 7.5.1
+      semver: 7.5.3
       tiny-lru: 11.0.1
     transitivePeerDependencies:
       - supports-color
@@ -12516,6 +12127,7 @@ packages:
     dependencies:
       fs-extra: 11.1.0
       ramda: 0.28.0
+    dev: true
 
   /file-type@17.1.6:
     resolution: {integrity: sha512-hlDw5Ev+9e883s0pwUsuuYNu4tD7GgpUnOvykjv1Gya0ZIjuKumthDRua90VUn6/nlRKAjcxLUnHNTIUWwWIiw==}
@@ -12526,8 +12138,8 @@ packages:
       token-types: 5.0.1
     dev: false
 
-  /file-type@18.4.0:
-    resolution: {integrity: sha512-o6MQrZKTAK6WpvmQk3jqTVUmqxYBxW5bloUfrdH1ZnRFDvvAPNr+l+rgOxM3nkqWT+3khaj3FRMDydWe0xhu+w==}
+  /file-type@18.5.0:
+    resolution: {integrity: sha512-yvpl5U868+V6PqXHMmsESpg6unQ5GfnPssl4dxdJudBrr9qy7Fddt7EVX1VLlddFfe8Gj9N7goCZH22FXuSQXQ==}
     engines: {node: '>=14.16'}
     dependencies:
       readable-web-to-node-stream: 3.0.2
@@ -12739,6 +12351,7 @@ packages:
     resolution: {integrity: sha512-jqYfLp7mo9vIyQf8ykW2v7A+2N4QjeCeI5+Dz9XraiO1ign81wjiH7Fb9vSOWvQfNtmSa4H2RoQTrrXivdUZmw==}
     dependencies:
       is-callable: 1.2.7
+    dev: true
 
   /for-in@1.0.2:
     resolution: {integrity: sha512-7EwmXrOjyL+ChxMhmG5lnW9MPt1aIeZEwKhQzoBUdTV0N3zuwWDZYVJatDvZ2OyzPUvdIAZDsCetk3coyMfcnQ==}
@@ -12759,6 +12372,14 @@ packages:
       signal-exit: 3.0.7
     dev: true
 
+  /foreground-child@3.1.1:
+    resolution: {integrity: sha512-TMKDUnIte6bfb5nWv7V/caI169OHgvwjb7V4WkeUvbQQdjr5rWKqHFiKWb/fcOwB+CzBT+qbWjvj+DVwRskpIg==}
+    engines: {node: '>=14'}
+    dependencies:
+      cross-spawn: 7.0.3
+      signal-exit: 4.0.2
+    dev: false
+
   /forever-agent@0.6.1:
     resolution: {integrity: sha512-j0KLYPhm6zeac4lz3oJ3o65qvgQCcPubiyotZrXqEaG4hNagNYO8qdlUrX5vwqv9ohqeT/Z3j6+yW067yWWdUw==}
 
@@ -12830,6 +12451,7 @@ packages:
       graceful-fs: 4.2.11
       jsonfile: 6.1.0
       universalify: 2.0.0
+    dev: true
 
   /fs-extra@7.0.1:
     resolution: {integrity: sha512-YJDaCJZEnBmcbw13fvdAM9AwNOJwOzrE4pqMqBq5nFiEqXUqHwlK4B+3pUw6JNvfSPtX05xFHtYy/1ni01eGCw==}
@@ -12872,6 +12494,13 @@ packages:
     dependencies:
       minipass: 3.3.6
 
+  /fs-minipass@3.0.2:
+    resolution: {integrity: sha512-2GAfyfoaCDRrM6jaOS3UsBts8yJ55VioXdWcOL7dK9zdAuKT71+WBA4ifnNYqVjYv+4SsPxjK0JT4yIIn4cA/g==}
+    engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0}
+    dependencies:
+      minipass: 5.0.0
+    dev: false
+
   /fs-mkdirp-stream@1.0.0:
     resolution: {integrity: sha512-+vSd9frUnapVC2RZYfL3FCB2p3g4TBhaUmrsWlSudsGdnxIuUvBB2QM1VZeBtc49QFwrp+wQLrDs3+xxDgI5gQ==}
     engines: {node: '>= 0.10'}
@@ -13147,6 +12776,18 @@ packages:
       - supports-color
     dev: false
 
+  /glob@10.3.0:
+    resolution: {integrity: sha512-AQ1/SB9HH0yCx1jXAT4vmCbTOPe5RQ+kCurjbel5xSCGhebumUv+GJZfa1rEqor3XIViqwSEmlkZCQD43RWrBg==}
+    engines: {node: '>=16 || 14 >=14.17'}
+    hasBin: true
+    dependencies:
+      foreground-child: 3.1.1
+      jackspeak: 2.2.1
+      minimatch: 9.0.2
+      minipass: 5.0.0
+      path-scurry: 1.9.2
+    dev: false
+
   /glob@7.2.3:
     resolution: {integrity: sha512-nFR0zLpU2YCaRxwoCJvL6UvCH2JFyFVIvwTLsIf21AuHlMskA1hhTdk+LlYJtOlYt9v6dvszD2BGRqBL+iQK9Q==}
     dependencies:
@@ -13197,6 +12838,7 @@ packages:
   /globals@11.12.0:
     resolution: {integrity: sha512-WOBp/EEGUiIsJSp7wcv/y6MO+lV9UoncWqxuFfm8eBwzWNgyfBd6Gz+IeKQ9jCmyhoH99g15M3T+QaVHFjizVA==}
     engines: {node: '>=4'}
+    dev: true
 
   /globals@13.19.0:
     resolution: {integrity: sha512-dkQ957uSRWHw7CFXLUtUHQI3g3aWApYhfNR2O6jn/907riyTYKVBmxYVROkBcY614FSSeSJh7Xm7SrUWCxvJMQ==}
@@ -13232,6 +12874,7 @@ packages:
     resolution: {integrity: sha512-d65bNlIadxvpb/A2abVdlqKqV563juRnZ1Wtk6s1sIR8uNsXR70xqIzVqxVf1eTqDunwT2MkczEeaezCKTZhwA==}
     dependencies:
       get-intrinsic: 1.2.0
+    dev: true
 
   /got@11.8.5:
     resolution: {integrity: sha512-o0Je4NvQObAuZPHLFoRSkdG2lTgtcynqymzg2Vupdx6PorhaT5MCbIyXG6d4D94kk8ZG57QeosgdiqfJWhEhlQ==}
@@ -13271,6 +12914,7 @@ packages:
 
   /grapheme-splitter@1.0.4:
     resolution: {integrity: sha512-bzh50DW9kTPM00T8y4o8vQg89Di9oLJVLW/KaOGIXJWP/iqCN6WKYkbNOF04vFLJhwcpYUh9ydh/+5vpOqV4YQ==}
+    dev: true
 
   /graphemer@1.4.0:
     resolution: {integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==}
@@ -13281,8 +12925,8 @@ packages:
     engines: {node: ^12.22.0 || ^14.16.0 || ^16.0.0 || >=17.0.0}
     dev: true
 
-  /gsap@3.11.5:
-    resolution: {integrity: sha512-Q89nKCLgoX5xUjznh9LcaIUkz54k1voNucT1Rpf9SJNFIQznBwFqt5qUUQbeVInFyN/n18OUJkpeI6CNEDt74w==}
+  /gsap@3.12.1:
+    resolution: {integrity: sha512-FXtb2YbBE9l8I9Pl5DFLpCMedaiMPztRlr0Ln0CMSnJn+pbTaeKlzgth8cLNPc7PzNwIZe+SEQiBBAWaBKJdVA==}
     dev: false
 
   /gulp-cli@2.3.0:
@@ -13443,6 +13087,7 @@ packages:
   /has-flag@3.0.0:
     resolution: {integrity: sha512-sKJf1+ceQBr4SMkvQnBDNDtf4TXpVhVGateu0t918bl30FnbE2m4vNLX+VWe/dpjlb+HugGYzW7uQXH98HPEYw==}
     engines: {node: '>=4'}
+    dev: true
 
   /has-flag@4.0.0:
     resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==}
@@ -13530,11 +13175,6 @@ packages:
     resolution: {integrity: sha512-tWCK4biJ6hcLqTviLXVR9DTRfYGQMXEIUj3gwJ2rZ5wO/at3XtkI4g8mCvFdUF9l1KMBNCfmNAdnahm1cgavQA==}
     dev: true
 
-  /hexoid@1.0.0:
-    resolution: {integrity: sha512-QFLV0taWQOZtvIRIAdBChesmogZrtuXvVWsFHZTk2SU+anspqZ2vMnoLg7IE1+Uk16N19APic1BuF8bC8c2m5g==}
-    engines: {node: '>=8'}
-    dev: false
-
   /highlight.js@10.7.3:
     resolution: {integrity: sha512-tzcUFauisWKNHaRkN4Wjl/ZA07gENAjFl3J/c480dprkGTg5EQstgaNFqBfUqCq54kZRIEcreTsAgF/m2quD7A==}
 
@@ -13685,6 +13325,16 @@ packages:
     transitivePeerDependencies:
       - supports-color
 
+  /https-proxy-agent@7.0.0:
+    resolution: {integrity: sha512-0euwPCRyAPSgGdzD1IVN9nJYHtBhJwb6XPfbpQcYbPCwrBidX6GzxmchnaF4sfF/jPb74Ojx5g4yTg3sixlyPw==}
+    engines: {node: '>= 14'}
+    dependencies:
+      agent-base: 7.1.0
+      debug: 4.3.4(supports-color@8.1.1)
+    transitivePeerDependencies:
+      - supports-color
+    dev: false
+
   /human-signals@1.1.1:
     resolution: {integrity: sha512-SEQu7vl8KjNL2eoGBLF3+wAjpsNfA9XMlXAYj/3EdaNfAlxKthD1xjEQfGOUhllCGGJVNY34bRr6lPINhNjyZw==}
     engines: {node: '>=8.12.0'}
@@ -13771,10 +13421,6 @@ packages:
     resolution: {integrity: sha512-bup+4tap3Hympa+JBJUG7XuOsdNQ6fxt0MHyXMKuLBKn0OqsTfvUxkUrroEX1+B2VsSHvCjiIcZVxRtYa4nllA==}
     dev: false
 
-  /infer-owner@1.0.4:
-    resolution: {integrity: sha512-IClj+Xz94+d7irH5qRyfJonOdfTzuDaifE6ZPWfx0N0+/ATZCbuTPq2prFl526urkQd90WyUKIh1DfBQ2hMz9A==}
-    dev: false
-
   /inflight@1.0.6:
     resolution: {integrity: sha512-k92I/b08q4wvFscXCLvqfsHCrjrF7yiXsQuIVvVE7N82W3+aqpzuUdBbfhWcy/FZR3/4IgflMgKLOsvPDrGCJA==}
     dependencies:
@@ -13949,6 +13595,7 @@ packages:
     dependencies:
       call-bind: 1.0.2
       has-tostringtag: 1.0.0
+    dev: true
 
   /is-array-buffer@3.0.2:
     resolution: {integrity: sha512-y+FyyR/w8vfIRq4eQcM1EYgSTnmHXPqaF+IgzgraytCFq5Xh8lllDVmAZolPJiZttZLeFSINPYMaEJ7/vWUa1w==}
@@ -13990,6 +13637,7 @@ packages:
   /is-callable@1.2.7:
     resolution: {integrity: sha512-1BC0BVFhS/p0qtw6enp8e+8OD0UrK0oFLztSjNzhcKA3WDuJxxAPXzPuPtKkjEY9UUoEWlX/8fgKeu2S8i9JTA==}
     engines: {node: '>= 0.4'}
+    dev: true
 
   /is-ci@3.0.1:
     resolution: {integrity: sha512-ZYvCgrefwqoQ6yTyYUbQu64HsITZ3NfKX1lzaEYdkTDcfKzzCI/wthRRYKkdjHKFVgNiXKAKm65Zo1pk2as/QQ==}
@@ -14102,6 +13750,7 @@ packages:
     engines: {node: '>= 0.4'}
     dependencies:
       has-tostringtag: 1.0.0
+    dev: true
 
   /is-glob@3.1.0:
     resolution: {integrity: sha512-UFpDDrPgM6qpnFNI+rh/p3bUaq9hKLZN8bMUWzxmcnZVS3omf4IPK+BrewlnWjO1WmUsMYuSjKh4UJuV4+Lqmw==}
@@ -14158,6 +13807,7 @@ packages:
     dependencies:
       call-bind: 1.0.2
       define-properties: 1.1.4
+    dev: true
 
   /is-negated-glob@1.0.0:
     resolution: {integrity: sha512-czXVVn/QEmgvej1f50BZ648vUI+em0xqMq2Sn+QncCLN4zj1UAxlT+kw/6ggQTOaZPd1HqKQGEqbpQVtJucWug==}
@@ -14305,6 +13955,7 @@ packages:
       for-each: 0.3.3
       gopd: 1.0.1
       has-tostringtag: 1.0.0
+    dev: true
 
   /is-typedarray@1.0.0:
     resolution: {integrity: sha512-cyA56iCMHAh5CdzjJIa4aohJyeO1YbwLi3Jc35MmRU6poroFjIGZzUzupGiRPOjgHg9TLu43xbpwXk523fMxKA==}
@@ -14358,10 +14009,6 @@ packages:
       is-docker: 2.2.1
     dev: true
 
-  /is@3.3.0:
-    resolution: {integrity: sha512-nW24QBoPcFGGHJGUwnfpI7Yc5CdqWNdsyHQszVE/z2pKHXzh7FZ5GWhJqSyaQ9wMkQnsTx+kAI8bHlCX4tKdbg==}
-    dev: false
-
   /isarray@0.0.1:
     resolution: {integrity: sha512-D2S+3GLxWH+uhrNEcoh/fnmYeP8E8/zHl644d/jdA0g2uyXvy3sb0qxotE+ne0LtccHknQzWwZEzhak7oJ0COQ==}
 
@@ -14456,6 +14103,15 @@ packages:
     engines: {node: '>=6'}
     dev: false
 
+  /jackspeak@2.2.1:
+    resolution: {integrity: sha512-MXbxovZ/Pm42f6cDIDkl3xpwv1AGwObKwfmjs2nQePiy85tP3fatofl3FC1aBsOtP/6fq5SbtgHwWcMsLP+bDw==}
+    engines: {node: '>=14'}
+    dependencies:
+      '@isaacs/cliui': 8.0.2
+    optionalDependencies:
+      '@pkgjs/parseargs': 0.11.0
+    dev: false
+
   /jake@10.8.5:
     resolution: {integrity: sha512-sVpxYeuAhWt0OTWITwT98oyV0GsXyMlXCF+3L1SuafBVUIr/uILGRB+NqwkzhgXKvoJpDIpQvqkUALgdmQsQxw==}
     engines: {node: '>=10'}
@@ -14482,7 +14138,7 @@ packages:
       '@jest/expect': 29.5.0
       '@jest/test-result': 29.5.0
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       chalk: 4.1.2
       co: 4.6.0
       dedent: 0.7.0
@@ -14502,7 +14158,7 @@ packages:
       - supports-color
     dev: true
 
-  /jest-cli@29.5.0(@types/node@18.16.3):
+  /jest-cli@29.5.0(@types/node@20.3.1):
     resolution: {integrity: sha512-L1KcP1l4HtfwdxXNFCL5bmUbLQiKrakMUriBEcc1Vfz6gx31ORKdreuWvmQVBit+1ss9NNR3yxjwfwzZNdQXJw==}
     engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
     hasBin: true
@@ -14519,7 +14175,7 @@ packages:
       exit: 0.1.2
       graceful-fs: 4.2.11
       import-local: 3.1.0
-      jest-config: 29.5.0(@types/node@18.16.3)
+      jest-config: 29.5.0(@types/node@20.3.1)
       jest-util: 29.5.0
       jest-validate: 29.5.0
       prompts: 2.4.2
@@ -14530,35 +14186,7 @@ packages:
       - ts-node
     dev: true
 
-  /jest-cli@29.5.0(@types/node@20.2.5):
-    resolution: {integrity: sha512-L1KcP1l4HtfwdxXNFCL5bmUbLQiKrakMUriBEcc1Vfz6gx31ORKdreuWvmQVBit+1ss9NNR3yxjwfwzZNdQXJw==}
-    engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
-    hasBin: true
-    peerDependencies:
-      node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0
-    peerDependenciesMeta:
-      node-notifier:
-        optional: true
-    dependencies:
-      '@jest/core': 29.5.0
-      '@jest/test-result': 29.5.0
-      '@jest/types': 29.5.0
-      chalk: 4.1.2
-      exit: 0.1.2
-      graceful-fs: 4.2.11
-      import-local: 3.1.0
-      jest-config: 29.5.0(@types/node@20.2.5)
-      jest-util: 29.5.0
-      jest-validate: 29.5.0
-      prompts: 2.4.2
-      yargs: 17.6.2
-    transitivePeerDependencies:
-      - '@types/node'
-      - supports-color
-      - ts-node
-    dev: true
-
-  /jest-config@29.5.0(@types/node@18.16.3):
+  /jest-config@29.5.0(@types/node@20.3.1):
     resolution: {integrity: sha512-kvDUKBnNJPNBmFFOhDbm59iu1Fii1Q6SxyhXfvylq3UTHbg6o7j/g8k2dZyXWLvfdKB1vAPxNZnMgtKJcmu3kA==}
     engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
     peerDependencies:
@@ -14573,46 +14201,7 @@ packages:
       '@babel/core': 7.21.3
       '@jest/test-sequencer': 29.5.0
       '@jest/types': 29.5.0
-      '@types/node': 18.16.3
-      babel-jest: 29.5.0(@babel/core@7.21.3)
-      chalk: 4.1.2
-      ci-info: 3.7.1
-      deepmerge: 4.2.2
-      glob: 7.2.3
-      graceful-fs: 4.2.11
-      jest-circus: 29.5.0
-      jest-environment-node: 29.5.0
-      jest-get-type: 29.4.3
-      jest-regex-util: 29.4.3
-      jest-resolve: 29.5.0
-      jest-runner: 29.5.0
-      jest-util: 29.5.0
-      jest-validate: 29.5.0
-      micromatch: 4.0.5
-      parse-json: 5.2.0
-      pretty-format: 29.5.0
-      slash: 3.0.0
-      strip-json-comments: 3.1.1
-    transitivePeerDependencies:
-      - supports-color
-    dev: true
-
-  /jest-config@29.5.0(@types/node@20.2.5):
-    resolution: {integrity: sha512-kvDUKBnNJPNBmFFOhDbm59iu1Fii1Q6SxyhXfvylq3UTHbg6o7j/g8k2dZyXWLvfdKB1vAPxNZnMgtKJcmu3kA==}
-    engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
-    peerDependencies:
-      '@types/node': '*'
-      ts-node: '>=9.0.0'
-    peerDependenciesMeta:
-      '@types/node':
-        optional: true
-      ts-node:
-        optional: true
-    dependencies:
-      '@babel/core': 7.21.3
-      '@jest/test-sequencer': 29.5.0
-      '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       babel-jest: 29.5.0(@babel/core@7.21.3)
       chalk: 4.1.2
       ci-info: 3.7.1
@@ -14681,7 +14270,7 @@ packages:
       '@jest/environment': 29.5.0
       '@jest/fake-timers': 29.5.0
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       jest-mock: 29.5.0
       jest-util: 29.5.0
     dev: true
@@ -14711,7 +14300,7 @@ packages:
     dependencies:
       '@jest/types': 29.5.0
       '@types/graceful-fs': 4.1.6
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       anymatch: 3.1.3
       fb-watchman: 2.0.2
       graceful-fs: 4.2.11
@@ -14762,7 +14351,7 @@ packages:
     engines: {node: ^10.13.0 || ^12.13.0 || ^14.15.0 || >=15.0.0}
     dependencies:
       '@jest/types': 27.5.1
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
     dev: true
 
   /jest-mock@29.5.0:
@@ -14770,7 +14359,7 @@ packages:
     engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
     dependencies:
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       jest-util: 29.5.0
     dev: true
 
@@ -14825,7 +14414,7 @@ packages:
       '@jest/test-result': 29.5.0
       '@jest/transform': 29.5.0
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       chalk: 4.1.2
       emittery: 0.13.1
       graceful-fs: 4.2.11
@@ -14856,7 +14445,7 @@ packages:
       '@jest/test-result': 29.5.0
       '@jest/transform': 29.5.0
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       chalk: 4.1.2
       cjs-module-lexer: 1.2.2
       collect-v8-coverage: 1.0.1
@@ -14901,7 +14490,7 @@ packages:
       jest-util: 29.5.0
       natural-compare: 1.4.0
       pretty-format: 29.5.0
-      semver: 7.5.1
+      semver: 7.5.3
     transitivePeerDependencies:
       - supports-color
     dev: true
@@ -14911,7 +14500,7 @@ packages:
     engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
     dependencies:
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       chalk: 4.1.2
       ci-info: 3.7.1
       graceful-fs: 4.2.11
@@ -14936,7 +14525,7 @@ packages:
     dependencies:
       '@jest/test-result': 29.5.0
       '@jest/types': 29.5.0
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       ansi-escapes: 4.3.2
       chalk: 4.1.2
       emittery: 0.13.1
@@ -14955,13 +14544,13 @@ packages:
     resolution: {integrity: sha512-NcrQnevGoSp4b5kg+akIpthoAFHxPBcb5P6mYPY0fUNT+sSvmtu6jlkEle3anczUKIKEbMxFimk9oTP/tpIPgA==}
     engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       jest-util: 29.5.0
       merge-stream: 2.0.0
       supports-color: 8.1.1
     dev: true
 
-  /jest@29.5.0(@types/node@18.16.3):
+  /jest@29.5.0(@types/node@20.3.1):
     resolution: {integrity: sha512-juMg3he2uru1QoXX078zTa7pO85QyB9xajZc6bU+d9yEGwrKX6+vGmJQ3UdVZsvTEUARIdObzH68QItim6OSSQ==}
     engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
     hasBin: true
@@ -14974,27 +14563,7 @@ packages:
       '@jest/core': 29.5.0
       '@jest/types': 29.5.0
       import-local: 3.1.0
-      jest-cli: 29.5.0(@types/node@18.16.3)
-    transitivePeerDependencies:
-      - '@types/node'
-      - supports-color
-      - ts-node
-    dev: true
-
-  /jest@29.5.0(@types/node@20.2.5):
-    resolution: {integrity: sha512-juMg3he2uru1QoXX078zTa7pO85QyB9xajZc6bU+d9yEGwrKX6+vGmJQ3UdVZsvTEUARIdObzH68QItim6OSSQ==}
-    engines: {node: ^14.15.0 || ^16.10.0 || >=18.0.0}
-    hasBin: true
-    peerDependencies:
-      node-notifier: ^8.0.1 || ^9.0.0 || ^10.0.0
-    peerDependenciesMeta:
-      node-notifier:
-        optional: true
-    dependencies:
-      '@jest/core': 29.5.0
-      '@jest/types': 29.5.0
-      import-local: 3.1.0
-      jest-cli: 29.5.0(@types/node@20.2.5)
+      jest-cli: 29.5.0(@types/node@20.3.1)
     transitivePeerDependencies:
       - '@types/node'
       - supports-color
@@ -15043,10 +14612,6 @@ packages:
     engines: {node: '>=0.10.0'}
     dev: true
 
-  /js-sdsl@4.2.0:
-    resolution: {integrity: sha512-dyBIzQBDkCqCu+0upx25Y2jGdbTGxE9fshMsCdK0ViOongpV+n5tXRcZY9v7CaVQ79AGS9KA1KHtojxiM7aXSQ==}
-    dev: true
-
   /js-string-escape@1.0.1:
     resolution: {integrity: sha512-Smw4xcfIQ5LVjAOuJCvN/zIodzA/BBSsluuoSykP+lUvScIi4U6RJLfwHet5cxFnCswUjISV8oAXaqaJDY3chg==}
     engines: {node: '>= 0.8'}
@@ -15057,6 +14622,7 @@ packages:
 
   /js-tokens@4.0.0:
     resolution: {integrity: sha512-RdJUflcE3cUzKiMqQgsCu06FPu9UdIJO0beYbPhHN4k6apgJtifcoCtT9bcxOpYBtpD2kCM6Sbzg4CausW/PKQ==}
+    dev: true
 
   /js-yaml@3.14.1:
     resolution: {integrity: sha512-okMH7OXXJ7YrN9Ok3/SXrnu4iX9yOk+25nqX4imS2npuvTYDmo/QEZoqwZkYaIDk3jVvBOTOIEgEhaLOynBS9g==}
@@ -15064,6 +14630,7 @@ packages:
     dependencies:
       argparse: 1.0.10
       esprima: 4.0.1
+    dev: true
 
   /js-yaml@3.7.0:
     resolution: {integrity: sha512-eIlkGty7HGmntbV6P/ZlAsoncFLGsNoM27lkTzS+oneY/EiNhj+geqD9ezg/ip+SW6Var0BJU2JtV0vEUZpWVQ==}
@@ -15166,25 +14733,26 @@ packages:
     resolution: {integrity: sha512-OYu7XEzjkCQ3C5Ps3QIZsQfNpqoJyZZA99wd9aWd05NCtC5pWOkShK2mkL6HXQR6/Cy2lbNdPlZBpuQHXE63gA==}
     engines: {node: '>=4'}
     hasBin: true
+    dev: true
 
   /json-buffer@3.0.1:
     resolution: {integrity: sha512-4bV5BfR2mqfQTJm+V5tPPdf+ZpuhiIvTuAB5g8kcrXOZpTT/QwwVRWBywX1ozr6lEuPdbHxwaJlm9G6mI2sfSQ==}
 
-  /json-file-plus@3.3.1:
-    resolution: {integrity: sha512-wo0q1UuiV5NsDPQDup1Km8IwEeqe+olr8tkWxeJq9Bjtcp7DZ0l+yrg28fSC3DEtrE311mhTZ54QGS6oiqnZEA==}
-    engines: {node: '>= 0.4'}
-    dependencies:
-      is: 3.3.0
-      node.extend: 2.0.2
-      object.assign: 4.1.4
-      promiseback: 2.0.3
-      safer-buffer: 2.1.2
-    dev: false
-
   /json-parse-even-better-errors@2.3.1:
     resolution: {integrity: sha512-xyFwyhro/JEof6Ghe2iz2NcXoj2sloNsWr/XsERDK/oiPCfaNhl5ONfp+jQdAZRQQ0IJWNzH9zIZF7li91kh2w==}
     dev: true
 
+  /json-schema-resolver@2.0.0:
+    resolution: {integrity: sha512-pJ4XLQP4Q9HTxl6RVDLJ8Cyh1uitSs0CzDBAz1uoJ4sRD/Bk7cFSXL1FUXDW3zJ7YnfliJx6eu8Jn283bpZ4Yg==}
+    engines: {node: '>=10'}
+    dependencies:
+      debug: 4.3.4(supports-color@8.1.1)
+      rfdc: 1.3.0
+      uri-js: 4.4.1
+    transitivePeerDependencies:
+      - supports-color
+    dev: false
+
   /json-schema-traverse@0.4.1:
     resolution: {integrity: sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==}
 
@@ -15235,6 +14803,7 @@ packages:
       universalify: 2.0.0
     optionalDependencies:
       graceful-fs: 4.2.11
+    dev: true
 
   /jsonld@8.2.0:
     resolution: {integrity: sha512-qHUa9pn3/cdAZw26HY1Jmy9+sHOxaLrveTRWUcrSDx5apTa20bBTe+X4nzI7dlqc+M5GkwQW6RgRdqO6LF5nkw==}
@@ -15435,11 +15004,11 @@ packages:
       - supports-color
     dev: false
 
-  /light-my-request@5.8.0:
-    resolution: {integrity: sha512-4BtD5C+VmyTpzlDPCZbsatZMJVgUIciSOwYhJDCbLffPZ35KoDkDj4zubLeHDEb35b4kkPeEv5imbh+RJxK/Pg==}
+  /light-my-request@5.10.0:
+    resolution: {integrity: sha512-ZU2D9GmAcOUculTTdH9/zryej6n8TzT+fNGdNtm6SDp5MMMpHrJJkvAdE3c6d8d2chE9i+a//dS9CWZtisknqA==}
     dependencies:
       cookie: 0.5.0
-      process-warning: 2.1.0
+      process-warning: 2.2.0
       set-cookie-parser: 2.5.1
     dev: false
 
@@ -15507,18 +15076,6 @@ packages:
       p-locate: 5.0.0
     dev: true
 
-  /lodash.clone@4.5.0:
-    resolution: {integrity: sha512-GhrVeweiTD6uTmmn5hV/lzgCQhccwReIVRLHp7LT4SopOjqEZ5BbX8b5WWEtAKasjmy8hR7ZPwsYlxRCku5odg==}
-    dev: false
-
-  /lodash.clonedeep@4.5.0:
-    resolution: {integrity: sha512-H5ZhCF25riFd9uB5UCkVKo61m3S/xZk1x4wA6yp/L3RFP6Z/eHH1ymQcGLo7J3GMPfm0V/7m1tryHuGVxpqEBQ==}
-    dev: false
-
-  /lodash.constant@3.0.0:
-    resolution: {integrity: sha512-X5XMrB+SdI1mFa81162NSTo/YNd23SLdLOLzcXTwS4inDZ5YCL8X67UFzZJAH4CqIa6R8cr56CShfA5K5MFiYQ==}
-    dev: false
-
   /lodash.debounce@4.0.8:
     resolution: {integrity: sha512-FT1yDzDYEoYWhnSGnpE/4Kj1fLZkDFyqRb7fNt6FdYOSxlUWAtp42Eh6Wb0rGIv/m9Bgo7x4GhQbm5Ys4SG5ow==}
     dev: true
@@ -15531,61 +15088,26 @@ packages:
     resolution: {integrity: sha512-dS2j+W26TQ7taQBGN8Lbbq04ssV3emRw4NY58WErlTO29pIqS0HmoT5aJ9+TUQ1N3G+JOZSji4eugsWwGp9yPA==}
     dev: false
 
-  /lodash.filter@4.6.0:
-    resolution: {integrity: sha512-pXYUy7PR8BCLwX5mgJ/aNtyOvuJTdZAo9EQFUvMIYugqmJxnrYaANvTbgndOzHSCSR0wnlBBfRXJL5SbWxo3FQ==}
-    dev: false
-
-  /lodash.flatmap@4.5.0:
-    resolution: {integrity: sha512-/OcpcAGWlrZyoHGeHh3cAoa6nGdX6QYtmzNP84Jqol6UEQQ2gIaU3H+0eICcjcKGl0/XF8LWOujNn9lffsnaOg==}
-    dev: false
-
   /lodash.flatten@4.4.0:
     resolution: {integrity: sha512-C5N2Z3DgnnKr0LOpv/hKCgKdb7ZZwafIrsesve6lmzvZIRZRGaZ/l6Q8+2W7NaT+ZwO3fFlSCzCzrDCFdJfZ4g==}
     dev: false
 
-  /lodash.foreach@4.5.0:
-    resolution: {integrity: sha512-aEXTF4d+m05rVOAUG3z4vZZ4xVexLKZGF0lIxuHZ1Hplpk/3B6Z1+/ICICYRLm7c41Z2xiejbkCkJoTlypoXhQ==}
-    dev: false
-
   /lodash.get@4.4.2:
     resolution: {integrity: sha512-z+Uw/vLuy6gQe8cfaFWD7p0wVv8fJl3mbzXh33RS+0oW2wvUqiRXiQ69gLWSLpgB5/6sU+r6BlQR0MBILadqTQ==}
     dev: true
 
-  /lodash.has@4.5.2:
-    resolution: {integrity: sha512-rnYUdIo6xRCJnQmbVFEwcxF144erlD+M3YcJUVesflU9paQaE8p+fJDcIQrlMYbxoANFL+AB9hZrzSBBk5PL+g==}
-    dev: false
-
   /lodash.isarguments@3.1.0:
     resolution: {integrity: sha512-chi4NHZlZqZD18a0imDHnZPrDeBbTtVN7GXMwuGdRH9qotxAjYs3aVLKc7zNOG9eddR5Ksd8rvFEBc9SsggPpg==}
     dev: false
 
-  /lodash.isempty@4.4.0:
-    resolution: {integrity: sha512-oKMuF3xEeqDltrGMfDxAPGIVMSSRv8tbRSODbrs4KGsRRLEhrW8N8Rd4DRgB2+621hY8A8XwwrTVhXWpxFvMzg==}
-    dev: false
-
   /lodash.isequal@4.5.0:
     resolution: {integrity: sha512-pDo3lu8Jhfjqls6GkMgpahsF9kCyayhgykjyLMNFTKWrpVdAQtYyB4muAMWozBB4ig/dtWAmsMxLEI8wuz+DYQ==}
-
-  /lodash.isfunction@3.0.9:
-    resolution: {integrity: sha512-AirXNj15uRIMMPihnkInB4i3NHeb4iBtNg9WRWuK2o31S+ePwwNmDPaTL3o7dTJ+VXNZim7rFs4rxN4YU1oUJw==}
-    dev: false
+    dev: true
 
   /lodash.isplainobject@4.0.6:
     resolution: {integrity: sha512-oSXzaWypCMHkPC3NvBEaPHf0KsA5mvPrOPgQWDsbg8n7orZ290M0BmC/jgRZ4vcJ6DTAhjrsSYgdsW/F+MFOBA==}
     dev: false
 
-  /lodash.isundefined@3.0.1:
-    resolution: {integrity: sha512-MXB1is3s899/cD8jheYYE2V9qTHwKvt+npCwpD+1Sxm3Q3cECXCiYHjeHWXNwr6Q0SOBPrYUDxendrO6goVTEA==}
-    dev: false
-
-  /lodash.keys@4.2.0:
-    resolution: {integrity: sha512-J79MkJcp7Df5mizHiVNpjoHXLi4HLjh9VLS/M7lQSGoQ+0oQ+lWEigREkqKyizPB1IawvQLLKY8mzEcm1tkyxQ==}
-    dev: false
-
-  /lodash.map@4.6.0:
-    resolution: {integrity: sha512-worNHGKLDetmcEYDvh2stPCrrQRkP20E4l0iIS7F8EvzMqBBi7ltvFN5m1HvTf1P7Jk1txKhvFcmYsCr8O2F1Q==}
-    dev: false
-
   /lodash.memoize@4.1.2:
     resolution: {integrity: sha512-t7j+NzmgnQzTAYXcsHYLgimltOV1MXHtlOWf6GjL9Kj8GK5FInw5JotxvbOs+IvV1/Dzo04/fCGfLVs7aXb4Ag==}
     dev: false
@@ -15597,26 +15119,10 @@ packages:
     resolution: {integrity: sha512-Sb487aTOCr9drQVL8pIxOzVhafOjZN9UU54hiN8PU3uAiSV7lx1yYNpbNmex2PK6dSJoNTSJUUswT651yww3Mg==}
     dev: true
 
-  /lodash.reduce@4.6.0:
-    resolution: {integrity: sha512-6raRe2vxCYBhpBu+B+TtNGUzah+hQjVdu3E17wfusjyrXBka2nBS8OH/gjVZ5PvHOhWmIZTYri09Z6n/QfnNMw==}
-    dev: false
-
-  /lodash.size@4.2.0:
-    resolution: {integrity: sha512-wbu3SF1XC5ijqm0piNxw59yCbuUf2kaShumYBLWUrcCvwh6C8odz6SY/wGVzCWTQTFL/1Ygbvqg2eLtspUVVAQ==}
-    dev: false
-
   /lodash.throttle@4.1.1:
     resolution: {integrity: sha512-wIkUCfVKpVsWo3JSZlc+8MB5it+2AN5W8J7YVMST30UrvcQNZ1Okbj+rbVniijTWE6FGYy4XJq/rHkas8qJMLQ==}
     dev: true
 
-  /lodash.topairs@4.3.0:
-    resolution: {integrity: sha512-qrRMbykBSEGdOgQLJJqVSdPWMD7Q+GJJ5jMRfQYb+LTLsw3tYVIabnCzRqTJb2WTo17PG5gNzXuFaZgYH/9SAQ==}
-    dev: false
-
-  /lodash.transform@4.6.0:
-    resolution: {integrity: sha512-LO37ZnhmBVx0GvOU/caQuipEh4GN82TcWv3yHlebGDgOxbxiwwzW5Pcx2AcvpIv2WmvmSMoC492yQFNhy/l/UQ==}
-    dev: false
-
   /lodash.union@4.6.0:
     resolution: {integrity: sha512-c4pB2CdGrGdjMKYLA+XiRDO7Y0PRQbm/Gzg8qMj+QH+pFVAoTp5sBpO0odL3FjoPCGjK96p6qsP+yQoiLoOBcw==}
     dev: false
@@ -15625,10 +15131,6 @@ packages:
     resolution: {integrity: sha512-xfBaXQd9ryd9dlSDvnvI0lvxfLJlYAZzXomUYzLKtUeOQvOP5piqAWuGtrhWeqaXK9hhoM/iyJc5AV+XfsX3HQ==}
     dev: false
 
-  /lodash.values@4.3.0:
-    resolution: {integrity: sha512-r0RwvdCv8id9TUblb/O7rYPwVy6lerCbcawrfdo9iC/1t1wsNMJknO79WNBgwkH0hIeJ08jmvvESbFpNb4jH0Q==}
-    dev: false
-
   /lodash@4.17.21:
     resolution: {integrity: sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==}
 
@@ -15711,6 +15213,11 @@ packages:
     engines: {node: '>=16.14'}
     dev: true
 
+  /lru-cache@9.1.2:
+    resolution: {integrity: sha512-ERJq3FOzJTxBbFjZ7iDs+NiK4VI9Wz+RdrrAB8dio1oV+YvdPzUEE4QNiT2VD51DkIbCYRUUzCRkssXCHqSnKQ==}
+    engines: {node: 14 || >=16.14}
+    dev: false
+
   /luxon@3.3.0:
     resolution: {integrity: sha512-An0UCfG/rSiqtAIiBPO0Y9/zAnHUZxAMiCpTd5h2smgsj7GGmcenvrvww2cqNA8/4A5ZrD1gJpHN2mIHZQF+Mg==}
     engines: {node: '>=12'}
@@ -15758,28 +15265,26 @@ packages:
     dependencies:
       semver: 6.3.0
 
-  /make-fetch-happen@10.2.1:
-    resolution: {integrity: sha512-NgOPbRiaQM10DYXvN3/hhGVI2M5MtITFryzBGxHM5p4wnFxsVCbxkrBrDsk+EZ5OB4jEOT7AjDxtdF+KVEFT7w==}
-    engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0}
+  /make-fetch-happen@11.1.1:
+    resolution: {integrity: sha512-rLWS7GCSTcEujjVBs2YqG7Y4643u8ucvCJeSRqiLYhesrDuzeuFIk37xREzAsfQaqzl8b9rNCE4m6J8tvX4Q8w==}
+    engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0}
     dependencies:
       agentkeepalive: 4.2.1
-      cacache: 16.1.3
+      cacache: 17.1.3
       http-cache-semantics: 4.1.1
       http-proxy-agent: 5.0.0
       https-proxy-agent: 5.0.1
       is-lambda: 1.0.1
       lru-cache: 7.14.1
-      minipass: 3.3.6
-      minipass-collect: 1.0.2
-      minipass-fetch: 2.1.2
+      minipass: 5.0.0
+      minipass-fetch: 3.0.3
       minipass-flush: 1.0.5
       minipass-pipeline: 1.2.4
       negotiator: 0.6.3
       promise-retry: 2.0.1
       socks-proxy-agent: 7.0.0
-      ssri: 9.0.1
+      ssri: 10.0.4
     transitivePeerDependencies:
-      - bluebird
       - supports-color
     dev: false
 
@@ -15875,8 +15380,8 @@ packages:
     engines: {node: '>= 0.6'}
     dev: true
 
-  /meilisearch@0.32.5:
-    resolution: {integrity: sha512-pVccjGAGP1IDSLg3lx9VhyQjUo7kN8x/HVjSurtb8U24V5/pALpf5H2hj6f60QhJd0Ea4tnGRv8fGr2YqWMo9A==}
+  /meilisearch@0.33.0:
+    resolution: {integrity: sha512-bYPb9WyITnJfzf92e7QFK8Rc50DmshFWxypXCs3ILlpNh8pT15A7KSu9Xgnnk/K3G/4vb3wkxxtFS4sxNkWB8w==}
     dependencies:
       cross-fetch: 3.1.6
     transitivePeerDependencies:
@@ -16033,6 +15538,13 @@ packages:
       brace-expansion: 2.0.1
     dev: true
 
+  /minimatch@9.0.2:
+    resolution: {integrity: sha512-PZOT9g5v2ojiTL7r1xF6plNHLtOeTpSlDI007As2NlA2aYBMfVom17yqa6QzhmDP8QOhn7LjHTg7DFCVSSa6yg==}
+    engines: {node: '>=16 || 14 >=14.17'}
+    dependencies:
+      brace-expansion: 2.0.1
+    dev: false
+
   /minimist-options@4.1.0:
     resolution: {integrity: sha512-Q4r8ghd80yhO/0j1O3B2BjweX3fiHg9cdOwjJd2J76Q135c+NDxGCqdYKQ1SKBuFfgWbAUzBfvYjPUEeNgqN1A==}
     engines: {node: '>= 6'}
@@ -16056,11 +15568,11 @@ packages:
       minipass: 3.3.6
     dev: false
 
-  /minipass-fetch@2.1.2:
-    resolution: {integrity: sha512-LT49Zi2/WMROHYoqGgdlQIZh8mLPZmOrN2NdJjMXxYe4nkN6FUyuPuOAOedNJDrx0IRGg9+4guZewtp8hE6TxA==}
-    engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0}
+  /minipass-fetch@3.0.3:
+    resolution: {integrity: sha512-n5ITsTkDqYkYJZjcRWzZt9qnZKCT7nKCosJhHoj7S7zD+BP4jVbWs+odsniw5TA3E0sLomhTKOKjF86wf11PuQ==}
+    engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0}
     dependencies:
-      minipass: 3.3.6
+      minipass: 5.0.0
       minipass-sized: 1.0.3
       minizlib: 2.1.2
     optionalDependencies:
@@ -16106,6 +15618,11 @@ packages:
     resolution: {integrity: sha512-+yQl7SX3bIT83Lhb4BVorMAHVuqsskxRdlmO9kTpyukp8vsm2Sn/fUOV9xlnG8/a5JsypJzap21lz/y3FBMJ8Q==}
     engines: {node: '>=8'}
 
+  /minipass@5.0.0:
+    resolution: {integrity: sha512-3FnjYuehv9k6ovOEbyOswadCDPX1piCfhV8ncmYtHOjuPwylVWsghTLo7rabjC3Rx5xD4HDx8Wm1xnMF7S5qFQ==}
+    engines: {node: '>=8'}
+    dev: false
+
   /minizlib@1.3.3:
     resolution: {integrity: sha512-6ZYMOEnmVsdCeTJVE0W9ZD+pVnE8h9Hma/iOwwRDsdQoePpoX56/8B6z3P9VNwppJuBKNRuFDRNRqRWexT9G9Q==}
     dependencies:
@@ -16150,7 +15667,7 @@ packages:
   /mlly@1.2.0:
     resolution: {integrity: sha512-+c7A3CV0KGdKcylsI6khWyts/CYrGTrRVo4R/I7u/cUsy0Conxa6LUhiEzVKIw14lc2L5aiO4+SeVe4TeGRKww==}
     dependencies:
-      acorn: 8.8.2
+      acorn: 8.9.0
       pathe: 1.1.0
       pkg-types: 1.0.2
       ufo: 1.1.1
@@ -16212,22 +15729,22 @@ packages:
       msgpackr-extract: 3.0.2
     dev: false
 
-  /msw-storybook-addon@1.8.0(msw@1.2.1):
+  /msw-storybook-addon@1.8.0(msw@1.2.2):
     resolution: {integrity: sha512-dw3vZwqjixmiur0vouRSOax7wPSu9Og2Hspy9JZFHf49bZRjwDiLF0Pfn2NXEkGviYJOJiGxS1ejoTiUwoSg4A==}
     peerDependencies:
       msw: '>=0.35.0 <2.0.0'
     dependencies:
       is-node-process: 1.0.1
-      msw: 1.2.1(typescript@5.1.3)
+      msw: 1.2.2(typescript@5.1.3)
     dev: true
 
-  /msw@1.2.1(typescript@5.1.3):
-    resolution: {integrity: sha512-bF7qWJQSmKn6bwGYVPXOxhexTCGD5oJSZg8yt8IBClxvo3Dx/1W0zqE1nX9BSWmzRsCKWfeGWcB/vpqV6aclpw==}
+  /msw@1.2.2(typescript@5.1.3):
+    resolution: {integrity: sha512-GsW3PE/Es/a1tYThXcM8YHOZ1S1MtivcS3He/LQbbTCx3rbWJYCtWD5XXyJ53KlNPT7O1VI9sCW3xMtgFe8XpQ==}
     engines: {node: '>=14'}
     hasBin: true
     requiresBuild: true
     peerDependencies:
-      typescript: '>= 4.4.x <= 5.0.x'
+      typescript: '>= 4.4.x <= 5.1.x'
     peerDependenciesMeta:
       typescript:
         optional: true
@@ -16245,7 +15762,7 @@ packages:
       inquirer: 8.2.5
       is-node-process: 1.2.0
       js-levenshtein: 1.1.6
-      node-fetch: 2.6.7
+      node-fetch: 2.6.11
       outvariant: 1.4.0
       path-to-regexp: 6.2.1
       strict-event-emitter: 0.4.6
@@ -16257,8 +15774,8 @@ packages:
       - supports-color
     dev: true
 
-  /muggle-string@0.2.2:
-    resolution: {integrity: sha512-YVE1mIJ4VpUMqZObFndk9CJu6DBJR/GB13p3tXuNbwD4XExaI5EOuRl6BHeIDxIqXZVxSfAC+y6U1Z/IxCfKUg==}
+  /muggle-string@0.3.1:
+    resolution: {integrity: sha512-ckmWDJjphvd/FvZawgygcUeQCxzvohjFO5RxTjj4eq8kw359gFF3E1brjfI+viLMxss5JrHTDRHZvu2/tuy0Qg==}
     dev: true
 
   /multi-integer-range@3.0.0:
@@ -16291,12 +15808,6 @@ packages:
     resolution: {integrity: sha512-2ZTgtl0nJsO0KQCjEpxcIr5D+Yv90plTitZt9JBfQvVJDS5seMl3FOvsh3+9CoYWXf/1l5OaZzzF6nDm4cagaQ==}
     dev: false
 
-  /nanoid@3.3.4:
-    resolution: {integrity: sha512-MqBkQh/OHTS2egovRtLk45wEyNXwF+cokD+1YPf9u5VfJiRdAiRwB2froX5Co9Rh20xs4siNPm8naNotSD6RBw==}
-    engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1}
-    hasBin: true
-    dev: false
-
   /nanoid@3.3.6:
     resolution: {integrity: sha512-BGcqMMJuToF7i1rt+2PWSNVnWIkGCU78jBG3RxO/bZlnZPK2Cmi2QaffxGO/2RvWi9sL+FAiRiXMgsyxQ1DIDA==}
     engines: {node: ^10 || ^12 || ^13.7 || ^14 || >=15.0.1}
@@ -16393,7 +15904,7 @@ packages:
     resolution: {integrity: sha512-8+Ib8rRJ4L0o3kfmyVCL7gzrohyDe0cMFTBa2d364yIrEGMEoetznKJx899YxjybU6bL9SQkYPSBBs1gyYs8Xg==}
     dependencies:
       '@sinonjs/commons': 2.0.0
-      '@sinonjs/fake-timers': 10.2.0
+      '@sinonjs/fake-timers': 10.3.0
       '@sinonjs/text-encoding': 0.7.2
       just-extend: 4.2.1
       path-to-regexp: 1.8.0
@@ -16403,7 +15914,7 @@ packages:
     resolution: {integrity: sha512-eSKV6s+APenqVh8ubJyiu/YhZgxQpGP66ntzUb3lY1xB9ukSRaGnx0AIxI+IM+1+IVYC1oWobgG5L3Lt9ARykQ==}
     engines: {node: '>=10'}
     dependencies:
-      semver: 7.5.1
+      semver: 7.5.3
 
   /node-addon-api@5.0.0:
     resolution: {integrity: sha512-CvkDw2OEnme7ybCykJpVcKH+uAOLV2qLqiyla128dN9TkEWfrYmxG6C2boDe5KcNQqZF3orkqzGgOMvZ/JNekA==}
@@ -16472,23 +15983,23 @@ packages:
     resolution: {integrity: sha512-NTZVKn9IylLwUzaKjkas1e4u2DLNcV4rdYagA4PWdPwW87Bi7z+BznyKSRwS/761tV/lzCGXplWsiaMjLqP2zQ==}
     hasBin: true
 
-  /node-gyp@9.3.1:
-    resolution: {integrity: sha512-4Q16ZCqq3g8awk6UplT7AuxQ35XN4R/yf/+wSAwcBUAjg7l58RTactWaP8fIDTi0FzI7YcVLujwExakZlfWkXg==}
+  /node-gyp@9.4.0:
+    resolution: {integrity: sha512-dMXsYP6gc9rRbejLXmTbVRYjAHw7ppswsKyMxuxJxxOHzluIO1rGp9TOQgjFJ+2MCqcOcQTOPB/8Xwhr+7s4Eg==}
     engines: {node: ^12.13 || ^14.13 || >=16}
     hasBin: true
     dependencies:
       env-paths: 2.2.1
+      exponential-backoff: 3.1.1
       glob: 7.2.3
       graceful-fs: 4.2.11
-      make-fetch-happen: 10.2.1
+      make-fetch-happen: 11.1.1
       nopt: 6.0.0
       npmlog: 6.0.2
       rimraf: 3.0.2
-      semver: 7.5.1
+      semver: 7.5.3
       tar: 6.1.13
       which: 2.0.2
     transitivePeerDependencies:
-      - bluebird
       - supports-color
     dev: false
 
@@ -16500,14 +16011,6 @@ packages:
     resolution: {integrity: sha512-dFSmB8fFHEH/s81Xi+Y/15DQY6VHW81nXRj86EMSL3lmuTmK1e+aT4wrFCkTbm+gSwkw4KpX+rT/pMM2c1mF+A==}
     dev: true
 
-  /node.extend@2.0.2:
-    resolution: {integrity: sha512-pDT4Dchl94/+kkgdwyS2PauDFjZG0Hk0IcHIB+LkW27HLDtdoeMxHTxZh39DYbPP8UflWXWj9JcdDozF+YDOpQ==}
-    engines: {node: '>=0.4.0'}
-    dependencies:
-      has: 1.0.3
-      is: 3.3.0
-    dev: false
-
   /nodemailer@6.9.3:
     resolution: {integrity: sha512-fy9v3NgTzBngrMFkDsKEj0r02U7jm6XfC3b52eoNV+GCrGj+s8pt5OqhiJdWKuw51zCTdiNR/IUD1z33LIIGpg==}
     engines: {node: '>=6.0.0'}
@@ -16547,7 +16050,7 @@ packages:
     dependencies:
       hosted-git-info: 4.1.0
       is-core-module: 2.11.0
-      semver: 7.5.1
+      semver: 7.5.3
       validate-npm-package-license: 3.0.4
     dev: true
 
@@ -16682,11 +16185,6 @@ packages:
       define-property: 0.2.5
       kind-of: 3.2.2
 
-  /object-hash@3.0.0:
-    resolution: {integrity: sha512-RSn9F68PjH9HqtltsSnqYC1XXoWe9Bju5+213R98cNGttag9q9yAOTzdbsqvIa7aNm5WffBZFpWYr2aWrklWAw==}
-    engines: {node: '>= 6'}
-    dev: false
-
   /object-inspect@1.12.2:
     resolution: {integrity: sha512-z+cPxW0QGUp0mcqcsgQyLVRDoXFQbXOwBaqyF7VIgI4TWNQsDHrBpUQslRmIfAoYWdYzs6UlKJtB2XJpTaNSpQ==}
     dev: true
@@ -16697,6 +16195,7 @@ packages:
     dependencies:
       call-bind: 1.0.2
       define-properties: 1.1.4
+    dev: true
 
   /object-keys@1.1.1:
     resolution: {integrity: sha512-NuAESUOUMrlIXOfHKzD6bpPu3tYt3xvjNdRIQ+FeT0lNb4K8WR70CaDxhuNguS2XG+GjkyMwOzsN5ZktImfhLA==}
@@ -16790,12 +16289,6 @@ packages:
     engines: {node: '>= 0.8'}
     dev: true
 
-  /once@1.3.3:
-    resolution: {integrity: sha512-6vaNInhu+CHxtONf3zw3vq4SP2DOQhjBvIa3rNcG0+P7eKWlYH6Peu7rHizSloRU2EwMz6GraLieis9Ac9+p1w==}
-    dependencies:
-      wrappy: 1.0.2
-    dev: false
-
   /once@1.4.0:
     resolution: {integrity: sha512-lNaJgI+2Q5URQBkccEKHTQOPaXdUxnZZElQTZY0MFUAuaEqe1E+Nyvgdz/aIyNi6Z9MzO5dv1H8n58/GELp3+w==}
     dependencies:
@@ -16831,6 +16324,10 @@ packages:
       is-wsl: 2.2.0
     dev: true
 
+  /openapi-types@12.1.3:
+    resolution: {integrity: sha512-N4YtSYJqghVu4iek2ZUvcN/0aqH1kRDuNqzcycDxhOUpg7GdvLa2F3DgS6yBNhInhv2r/6I0Flkn7CqL8+nIcw==}
+    dev: false
+
   /opentype.js@0.4.11:
     resolution: {integrity: sha512-GthxucX/6aftfLdeU5Ho7o7zmQcC8uVtqdcelVq12X++ndxwBZG8Xb5rFEKT7nEcWDD2P1x+TNuJ70jtj1Mbpw==}
     dev: false
@@ -16995,10 +16492,6 @@ packages:
     resolution: {integrity: sha512-R4nPAVTAU0B9D35/Gk3uJf/7XYbQcyohSKdvAxIRSNghFl4e71hVoGnBNQz9cWaXxO2I10KTC+3jMdvvoKw6dQ==}
     engines: {node: '>=6'}
 
-  /packageurl-js@1.0.1:
-    resolution: {integrity: sha512-EtXC0kgLjy/C7S4SN3Kk1SDRWLzIn/LUK0gXlz3gsxDdpI0k7q8C3SASpV0pc+v0yADBTt5rWewq/flGdGxtoQ==}
-    dev: false
-
   /packet-reader@1.0.0:
     resolution: {integrity: sha512-HAKu/fG3HpHFO0AA8WE8q2g+gBJaZ9MG7fcKk+IJPLTGAD6Psw4443l+9DGRbOIh3/aXr7Phy0TjilYivJo5XQ==}
     dev: false
@@ -17158,6 +16651,14 @@ packages:
       path-root-regex: 0.1.2
     dev: false
 
+  /path-scurry@1.9.2:
+    resolution: {integrity: sha512-qSDLy2aGFPm8i4rsbHd4MNyTcrzHFsLQykrtbuGRknZZCBBVXSv2tSCDN2Cg6Rt/GFRw8GoW9y9Ecw5rIPG1sg==}
+    engines: {node: '>=16 || 14 >=14.17'}
+    dependencies:
+      lru-cache: 9.1.2
+      minipass: 5.0.0
+    dev: false
+
   /path-to-regexp@0.1.7:
     resolution: {integrity: sha512-5DFkuoqlv1uYQKxy8omFBeJPQcdoE07Kv2sferDCrAq1ohOU+MSDswDIbnx3YAM60qIOnYa53wBhXW0EbMonrQ==}
     dev: true
@@ -17191,7 +16692,6 @@ packages:
 
   /pathe@1.1.0:
     resolution: {integrity: sha512-ODbEPR0KKHqECXW1GoxdDb+AZvULmXjVPy4rt+pGo2+TnjJTIPJQSVS6N63n8T2Ip+syHhbn52OewKicV0373w==}
-    dev: true
 
   /pathval@1.1.1:
     resolution: {integrity: sha512-Dp6zGqpTdETdR63lehJYPeIOqpiNBNtc7BpWSLrOje7UaIsE5aY92r/AunQA7rsXvet3lrJ3JnZX29UPTKXyKQ==}
@@ -17347,8 +16847,8 @@ packages:
     resolution: {integrity: sha512-KO0m2f1HkrPe9S0ldjx7za9BJjeHqBku5Ch8JyxETxT8dEFGz1PwgrHaOQupVYitpzbFSYm7nnljxD8dik2c+g==}
     dev: false
 
-  /pino@8.8.0:
-    resolution: {integrity: sha512-cF8iGYeu2ODg2gIwgAHcPrtR63ILJz3f7gkogaHC/TXVVXxZgInmNYiIpDYEwgEkxZti2Se6P2W2DxlBIZe6eQ==}
+  /pino@8.14.1:
+    resolution: {integrity: sha512-8LYNv7BKWXSfS+k6oEc6occy5La+q2sPwU3q2ljTX5AZk7v+5kND2o5W794FyRaqha6DJajmkNRsWtPpFyMUdw==}
     hasBin: true
     dependencies:
       atomic-sleep: 1.0.0
@@ -17356,7 +16856,7 @@ packages:
       on-exit-leak-free: 2.1.0
       pino-abstract-transport: 1.0.0
       pino-std-serializers: 6.1.0
-      process-warning: 2.1.0
+      process-warning: 2.2.0
       quick-format-unescaped: 4.0.4
       real-require: 0.2.0
       safe-stable-stringify: 2.4.2
@@ -17421,11 +16921,6 @@ packages:
       irregular-plurals: 3.5.0
     dev: true
 
-  /pluralize@7.0.0:
-    resolution: {integrity: sha512-ARhBOdzS3e41FbkW/XWrTEtukqqLoK5+Z/4UeDaLuSW+39JPeFgs4gCGqsrJHVZX0fUrx//4OF0K1CUGwlIFow==}
-    engines: {node: '>=4'}
-    dev: false
-
   /pngjs-nozlib@1.0.0:
     resolution: {integrity: sha512-N1PggqLp9xDqwAoKvGohmZ3m4/N9xpY0nDZivFqQLcpLHmliHnCp9BuNCsOeqHWMuEEgFjpEaq9dZq6RZyy0fA==}
     engines: {iojs: '>= 1.0.0', node: '>=0.10.0'}
@@ -17671,15 +17166,6 @@ packages:
       supports-color: 3.2.3
     dev: false
 
-  /postcss@8.4.21:
-    resolution: {integrity: sha512-tP7u/Sn/dVxK2NnruI4H9BG+x+Wxz6oeZ1cJ8P6G/PZY0IKk4k/63TDsQf2kQq3+qoJeLm2kIBUNlZe3zgb4Zg==}
-    engines: {node: ^10 || ^12 || >=14}
-    dependencies:
-      nanoid: 3.3.4
-      picocolors: 1.0.0
-      source-map-js: 1.0.2
-    dev: false
-
   /postcss@8.4.23:
     resolution: {integrity: sha512-bQ3qMcpF6A/YjR55xtoTr0jGOlnPOKAIMdOWiv0EIT6HVPEaJiJB4NLljSbiHoC2RX7DN5Uvjtpbg1NPdwv1oA==}
     engines: {node: ^10 || ^12 || >=14}
@@ -17778,6 +17264,7 @@ packages:
   /pretty-bytes@5.6.0:
     resolution: {integrity: sha512-FFw039TmrBqFK8ma/7OL3sDz/VytdtJr044/QUJtH0wK9lb9jLq9tJyIxUwtQJHwar2BqtiA4iCWSwo9JLkzFg==}
     engines: {node: '>=6'}
+    dev: true
 
   /pretty-format@27.5.1:
     resolution: {integrity: sha512-Qb1gy5OrP5+zDf2Bvnzdl3jsTf1qXVMazbvCoKhtKqVs4/YK4ozX4gKQJJVyNe+cajNPn0KoC0MC3FUmaHWEmQ==}
@@ -17851,8 +17338,8 @@ packages:
   /process-nextick-args@2.0.1:
     resolution: {integrity: sha512-3ouUOpQhtgrbOa17J7+uxOTpITYWaGP7/AhoR3+A+/1e9skrzelGi/dXzEYyvbxubEF6Wn2ypscTKiKJFFn1ag==}
 
-  /process-warning@2.1.0:
-    resolution: {integrity: sha512-9C20RLxrZU/rFnxWncDkuF6O999NdIf3E1ws4B0ZeY3sRVPzWBMsYDE2lxjxhiXxg464cQTgKUGm8/i6y2YGXg==}
+  /process-warning@2.2.0:
+    resolution: {integrity: sha512-/1WZ8+VQjR6avWOgHeEPd7SDQmFQ1B5mC1eRXsCm5TarlNmx/wCsa5GEaxGm05BORRtyG/Ex/3xq3TuRvq57qg==}
     dev: false
 
   /process@0.11.10:
@@ -17863,22 +17350,6 @@ packages:
     resolution: {integrity: sha512-7PiHtLll5LdnKIMw100I+8xJXR5gW2QwWYkT6iJva0bXitZKa/XMrSbdmg3r2Xnaidz9Qumd0VPaMrZlF9V9sA==}
     engines: {node: '>=0.4.0'}
 
-  /promise-deferred@2.0.3:
-    resolution: {integrity: sha512-n10XaoznCzLfyPFOlEE8iurezHpxrYzyjgq/1eW9Wk1gJwur/N7BdBmjJYJpqMeMcXK4wEbzo2EvZQcqjYcKUQ==}
-    engines: {node: '>= 0.4'}
-    dependencies:
-      promise: 7.3.1
-    dev: false
-
-  /promise-inflight@1.0.1:
-    resolution: {integrity: sha512-6zWPyEOFaQBJYcGMHBKTKJ3u6TBsnMFOIZSa6ce1e/ZrrsOlnHRHbabMjLiBYKp+n44X9eUI6VUPaukCXHuG4g==}
-    peerDependencies:
-      bluebird: '*'
-    peerDependenciesMeta:
-      bluebird:
-        optional: true
-    dev: false
-
   /promise-limit@2.7.0:
     resolution: {integrity: sha512-7nJ6v5lnJsXwGprnGXga4wx6d1POjvi5Qmf1ivTRxTjH4Z/9Czja/UCMLVmB9N93GeWOU93XaFaEt6jbuoagNw==}
     dev: false
@@ -17900,14 +17371,6 @@ packages:
     dependencies:
       asap: 2.0.6
 
-  /promiseback@2.0.3:
-    resolution: {integrity: sha512-VZXdCwS0ppVNTIRfNsCvVwJAaP2b+pxQF7lM8DMWfmpNWyTxB6O5YNbzs+8z0ki/KIBHKHk308NTIl4kJUem3w==}
-    engines: {node: '>= 0.4'}
-    dependencies:
-      is-callable: 1.2.7
-      promise-deferred: 2.0.3
-    dev: false
-
   /prompts@2.4.2:
     resolution: {integrity: sha512-NxNv/kLguCA7p3jE8oL2aEBsrJWgAakBpgmgK6lpPWV+WuOmY6r2/zbAVnP+T8bQlA0nzHXSJSJW0Hq7ylaD2Q==}
     engines: {node: '>= 6'}
@@ -18175,6 +17638,7 @@ packages:
 
   /ramda@0.28.0:
     resolution: {integrity: sha512-9QnLuG/kPVgWvMQ4aODhsBUFKOUmnbUnsSXACv+NCQZcHbeb+v8Lodp8OVxtRULN1/xOyYLLaL6npE6dMq5QTA==}
+    dev: true
 
   /random-seed@0.3.0:
     resolution: {integrity: sha512-y13xtn3kcTlLub3HKWXxJNeC2qK4mB59evwZ5EkeRlolx+Bp2ztF7LbcZmyCnOqlHQrLnfuNbi1sVmm9lPDlDA==}
@@ -18222,15 +17686,14 @@ packages:
       setimmediate: 1.0.5
     dev: false
 
-  /re2@1.19.0:
-    resolution: {integrity: sha512-y0LcLZgBF3L7mDtNfbghb7dCmChYQO2QsUGklNueAJUH+HAZO8UZUubgNsf6OxRTAQpeE4KMPR7vcpK3+Q+GiA==}
+  /re2@1.19.1:
+    resolution: {integrity: sha512-pML2LZvGdjESWAsufwlFwF+TBauIx7ItgcPIL0KiiZ9GrJ5OU3aJEc/EZvygB32nhjrRxe6QQFbie79QhT7gVA==}
     requiresBuild: true
     dependencies:
       install-artifact-from-github: 1.3.3
       nan: 2.17.0
-      node-gyp: 9.3.1
+      node-gyp: 9.4.0
     transitivePeerDependencies:
-      - bluebird
       - supports-color
     dev: false
 
@@ -18448,7 +17911,7 @@ packages:
       ast-types: 0.15.2
       esprima: 4.0.1
       source-map: 0.6.1
-      tslib: 2.5.2
+      tslib: 2.5.3
     dev: true
 
   /recast@0.22.0:
@@ -18459,7 +17922,7 @@ packages:
       ast-types: 0.15.2
       esprima: 4.0.1
       source-map: 0.6.1
-      tslib: 2.5.2
+      tslib: 2.5.3
     dev: true
 
   /recast@0.23.1:
@@ -18470,7 +17933,8 @@ packages:
       ast-types: 0.16.1
       esprima: 4.0.1
       source-map: 0.6.1
-      tslib: 2.5.2
+      tslib: 2.5.3
+    dev: true
 
   /rechoir@0.6.2:
     resolution: {integrity: sha512-HFM8rkZ+i3zrV+4LQjwQ0W+ez98pApMGM3HUrN04j3CqzPOzl9nmP15Y8YXNm8QHGv/eacOVEjqhmWpkRV0NAw==}
@@ -18860,8 +18324,8 @@ packages:
       seedrandom: 2.4.2
     dev: false
 
-  /rollup@3.23.0:
-    resolution: {integrity: sha512-h31UlwEi7FHihLe1zbk+3Q7z1k/84rb9BSwmBSr/XjOCEaBJ2YyedQDuM0t/kfOS0IxM+vk1/zI9XxYj9V+NJQ==}
+  /rollup@3.25.1:
+    resolution: {integrity: sha512-tywOR+rwIt5m2ZAWSe5AIJcTat8vGlnPFAv15ycCrw33t6iFsXZ6mzHVFh2psSjxQPmI+xgzMZZizUAukBI4aQ==}
     engines: {node: '>=14.18.0', npm: '>=8.0.0'}
     hasBin: true
     optionalDependencies:
@@ -18938,19 +18402,19 @@ packages:
   /safer-buffer@2.1.2:
     resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==}
 
-  /sanitize-html@2.10.0:
-    resolution: {integrity: sha512-JqdovUd81dG4k87vZt6uA6YhDfWkUGruUu/aPmXLxXi45gZExnt9Bnw/qeQU8oGf82vPyaE0vO4aH0PbobB9JQ==}
+  /sanitize-html@2.11.0:
+    resolution: {integrity: sha512-BG68EDHRaGKqlsNjJ2xUB7gpInPA8gVx/mvjO743hZaeMCZ2DwzW7xvsqZ+KNU4QKwj86HJ3uu2liISf2qBBUA==}
     dependencies:
       deepmerge: 4.2.2
       escape-string-regexp: 4.0.0
       htmlparser2: 8.0.1
       is-plain-object: 5.0.0
       parse-srcset: 1.0.2
-      postcss: 8.4.21
+      postcss: 8.4.23
     dev: false
 
-  /sass@1.62.1:
-    resolution: {integrity: sha512-NHpxIzN29MXvWiuswfc1W3I0N8SXBd8UR26WntmDlRYf0bSADnwnOjsyMZ3lMezSlArD33Vs3YFhp7dWvL770A==}
+  /sass@1.63.6:
+    resolution: {integrity: sha512-MJuxGMHzaOW7ipp+1KdELtqKbfAWbH7OLIdoSMnVe3EXPMTmxTmlaZDCTsgIpPCs3w99lLo9/zDKkOrJuT5byw==}
     engines: {node: '>=14.0.0'}
     hasBin: true
     dependencies:
@@ -19027,16 +18491,8 @@ packages:
       lru-cache: 6.0.0
     dev: true
 
-  /semver@7.5.0:
-    resolution: {integrity: sha512-+XC0AD/R7Q2mPSRuy2Id0+CGTZ98+8f+KvwirxOKIEyid+XSx6HbC63p+O4IndTHuX5Z+JxQ0TghCkO5Cg/2HA==}
-    engines: {node: '>=10'}
-    hasBin: true
-    dependencies:
-      lru-cache: 6.0.0
-    dev: true
-
-  /semver@7.5.1:
-    resolution: {integrity: sha512-Wvss5ivl8TMRZXXESstBA4uR5iXgEN/VC5/sOcuXdVLzcdkz4HWetIoRfG5gb5X+ij/G9rw9YoGn3QoQ8OCSpw==}
+  /semver@7.5.3:
+    resolution: {integrity: sha512-QBlUtyVk/5EeHbi7X0fw6liDZc7BBmEaSYn01fMU1OUYbf6GPsbTtd8WmnqbI20SeycoHSeiybkE/q1Q+qlThQ==}
     engines: {node: '>=10'}
     hasBin: true
     dependencies:
@@ -19132,7 +18588,7 @@ packages:
       detect-libc: 2.0.1
       node-addon-api: 5.0.0
       prebuild-install: 7.1.1
-      semver: 7.5.1
+      semver: 7.5.3
       simple-get: 4.0.1
       tar-fs: 2.1.1
       tunnel-agent: 0.6.0
@@ -19147,7 +18603,7 @@ packages:
       detect-libc: 2.0.1
       node-addon-api: 6.1.0
       prebuild-install: 7.1.1
-      semver: 7.5.1
+      semver: 7.5.3
       simple-get: 4.0.1
       tar-fs: 2.1.1
       tunnel-agent: 0.6.0
@@ -19203,6 +18659,11 @@ packages:
   /signal-exit@3.0.7:
     resolution: {integrity: sha512-wnD2ZE+l+SPC/uoS0vXeE9L1+0wuaMqKlfz9AMUo38JsyLSBWSFcHR1Rri62LZc12vLr1gb3jl7iwQhgwpAbGQ==}
 
+  /signal-exit@4.0.2:
+    resolution: {integrity: sha512-MY2/qGx4enyjprQnFaZsHib3Yadh3IXyV2C321GY0pjGfVBu4un0uDJkwgdxqO+Rdx8JMT8IfJIRwbYVz3Ob3Q==}
+    engines: {node: '>=14'}
+    dev: false
+
   /simple-concat@1.0.1:
     resolution: {integrity: sha512-cSFtAPtRhljv69IK0hTVZQ+OfE9nePi/rtJmw5UjHeVyVroEqJXP1sFztKUy1qU+xvz3u/sfYJLa947b7nAN2Q==}
 
@@ -19426,42 +18887,6 @@ packages:
     transitivePeerDependencies:
       - supports-color
 
-  /snyk-config@5.1.0:
-    resolution: {integrity: sha512-wqVMxUGqjjHX+MJrz0WHa/pJTDWU17aRv6cnI/6i7cq93J3TkkJZ8sjgvwCgP8cWX5wTHIlRuMV+IAd59K4X/g==}
-    dependencies:
-      async: 3.2.4
-      debug: 4.3.4(supports-color@8.1.1)
-      lodash.merge: 4.6.2
-      minimist: 1.2.8
-    transitivePeerDependencies:
-      - supports-color
-    dev: false
-
-  /snyk-nodejs-lockfile-parser@1.49.0:
-    resolution: {integrity: sha512-73iqwHB8YSWex/PTx+TRUwtNPyKn5wP4n/kxEPbX9EfN3uSIcw6mSKiLm8gSKl5gtf8hcP0R0f1tBFjjdzQvRQ==}
-    engines: {node: '>=10'}
-    hasBin: true
-    dependencies:
-      '@snyk/dep-graph': 2.6.0
-      '@snyk/graphlib': 2.1.9-patch.3
-      '@yarnpkg/core': 2.4.0
-      '@yarnpkg/lockfile': 1.1.0
-      event-loop-spinner: 2.2.0
-      js-yaml: 4.1.0
-      lodash.clonedeep: 4.5.0
-      lodash.flatmap: 4.5.0
-      lodash.isempty: 4.4.0
-      lodash.topairs: 4.3.0
-      micromatch: 4.0.5
-      p-map: 4.0.0
-      semver: 7.5.1
-      snyk-config: 5.1.0
-      tslib: 1.14.1
-      uuid: 8.3.2
-    transitivePeerDependencies:
-      - supports-color
-    dev: false
-
   /socks-proxy-agent@7.0.0:
     resolution: {integrity: sha512-Fgl0YPZ902wEsAyiQ+idGd1A7rSFx/ayC1CQVMw5P+EQx2V0SgpGtf6OKFhVjPflPUl9YMmEOnmfjCdMUsygww==}
     engines: {node: '>= 10'}
@@ -19614,11 +19039,11 @@ packages:
       safer-buffer: 2.1.2
       tweetnacl: 0.14.5
 
-  /ssri@9.0.1:
-    resolution: {integrity: sha512-o57Wcn66jMQvfHG1FlYbWeZWW/dHZhJXjpIcTfXldXEk5nz5lStPo3mK0OJQfGR3RbZUlbISexbljkJzuEj/8Q==}
-    engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0}
+  /ssri@10.0.4:
+    resolution: {integrity: sha512-12+IR2CB2C28MMAw0Ncqwj5QbTcs0nGIhgJzYWzDkb21vWmfNI83KS4f3Ci6GI98WreIfG7o9UXp3C0qbpA8nQ==}
+    engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0}
     dependencies:
-      minipass: 3.3.6
+      minipass: 5.0.0
     dev: false
 
   /stack-trace@0.0.10:
@@ -19702,11 +19127,6 @@ packages:
       readable-stream: 3.6.0
     dev: false
 
-  /stream-buffers@3.0.2:
-    resolution: {integrity: sha512-DQi1h8VEBA/lURbSwFtEHnSTb9s2/pwLEaFuNhXwy1Dx3Sa0lOuYT2yNUr4/j2fs8oCAMANtrZ5OrPZtyVs3MQ==}
-    engines: {node: '>= 0.10.0'}
-    dev: false
-
   /stream-combiner@0.0.4:
     resolution: {integrity: sha512-rT00SPnTVyRsaSz5zgSPma/aHSOic5U1prhYdRy5HS2kTZviFpmDgzilbtsJsxiroqACmayynDN/9VzIbX5DOw==}
     dependencies:
@@ -19727,20 +19147,6 @@ packages:
   /stream-shift@1.0.1:
     resolution: {integrity: sha512-AiisoFqQ0vbGcZgQPY1cdP2I76glaVA/RauYR4G4thNFgkTqr90yXTo4LYX60Jl+sIlPNHHdGSwo01AvbKUSVQ==}
 
-  /stream-to-array@2.3.0:
-    resolution: {integrity: sha512-UsZtOYEn4tWU2RGLOXr/o/xjRBftZRlG3dEWoaHr8j4GuypJ3isitGbVyjQKAuMu+xbiop8q224TjiZWc4XTZA==}
-    dependencies:
-      any-promise: 1.3.0
-    dev: false
-
-  /stream-to-promise@2.2.0:
-    resolution: {integrity: sha512-HAGUASw8NT0k8JvIVutB2Y/9iBk7gpgEyAudXwNJmZERdMITGdajOa4VJfD/kNiA3TppQpTP4J+CtcHwdzKBAw==}
-    dependencies:
-      any-promise: 1.3.0
-      end-of-stream: 1.1.0
-      stream-to-array: 2.3.0
-    dev: false
-
   /stream-wormhole@1.1.0:
     resolution: {integrity: sha512-gHFfL3px0Kctd6Po0M8TzEvt3De/xu6cnRrjlfYNhwbhLPLwigI2t1nc6jrzNuaYg5C4YF78PPFuQPzRiqn9ew==}
     engines: {node: '>=4.0.0'}
@@ -19809,6 +19215,15 @@ packages:
       is-fullwidth-code-point: 3.0.0
       strip-ansi: 6.0.1
 
+  /string-width@5.1.2:
+    resolution: {integrity: sha512-HnLOCR3vjcY8beoNLtcjZ5/nxn2afmME6lhrDrebokqMap+XbeW8n9TXpPDOqdGK5qcI3oT0GKTW6wC7EMiVqA==}
+    engines: {node: '>=12'}
+    dependencies:
+      eastasianwidth: 0.2.0
+      emoji-regex: 9.2.2
+      strip-ansi: 7.1.0
+    dev: false
+
   /string.prototype.trimend@1.0.6:
     resolution: {integrity: sha512-JySq+4mrPf9EsDBEDYMOb/lM7XQLulwg5R/m1r0PXEFqrV0qHvl58sdTilSXtKOflCsK2E8jxf+GKC0T07RWwQ==}
     dependencies:
@@ -19865,6 +19280,13 @@ packages:
     dependencies:
       ansi-regex: 5.0.1
 
+  /strip-ansi@7.1.0:
+    resolution: {integrity: sha512-iq6eVVI64nQQTRYq2KtEg2d2uU7LElhTJwsH4YzIHZshxlgZms/wIc4VoDQTlG/IvVIrBKG06CrZnp0qv7hkcQ==}
+    engines: {node: '>=12'}
+    dependencies:
+      ansi-regex: 6.0.1
+    dev: false
+
   /strip-bom@2.0.0:
     resolution: {integrity: sha512-kwrX1y7czp1E69n2ajbG65mIo9dqvJ+8aBQXOGVxqwvNbsXdFM6Lq37dLAY3mknUwru8CfcCbfOLL/gMo+fi3g==}
     engines: {node: '>=0.10.0'}
@@ -19914,7 +19336,7 @@ packages:
   /strip-literal@1.0.1:
     resolution: {integrity: sha512-QZTsipNpa2Ppr6v1AmJHESqJ3Uz247MUS0OjrnnZjFAvEoWqxuyFuXn2xLgMtRnijJShAa1HL0gtJyUs7u7n3Q==}
     dependencies:
-      acorn: 8.8.2
+      acorn: 8.9.0
     dev: true
 
   /strip-outer@2.0.0:
@@ -19951,6 +19373,7 @@ packages:
     engines: {node: '>=4'}
     dependencies:
       has-flag: 3.0.0
+    dev: true
 
   /supports-color@7.2.0:
     resolution: {integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==}
@@ -20004,8 +19427,8 @@ packages:
     resolution: {integrity: sha512-AsS729u2RHUfEra9xJrE39peJcc2stq2+poBXX8bcM08Y6g9j/i/PUzwNQqkaJde7Ntg1TO7bSREbR5sdosQ+g==}
     dev: true
 
-  /systeminformation@5.17.16:
-    resolution: {integrity: sha512-dl2QLa7yp9QbBl9um+51CAr3p/40tbz+f34X1lUXkk1SnDcNeJR2iWu/8HD7GM2yRukmy3RCRXFYcPZs0lCs0Q==}
+  /systeminformation@5.18.4:
+    resolution: {integrity: sha512-x1MHqHooJ2n9fmQRngH5TdSk/BcPAPLBBBmS7BSTkALRT56RlgiiNPP7HKoNu2SIFXSG4nPfi1gWh8ASmHPCrA==}
     engines: {node: '>=8.0.0'}
     os: [darwin, linux, win32, freebsd, openbsd, netbsd, sunos, android]
     hasBin: true
@@ -20092,7 +19515,7 @@ packages:
     engines: {node: '>=10'}
     dependencies:
       '@jridgewell/source-map': 0.3.2
-      acorn: 8.8.2
+      acorn: 8.9.0
       commander: 2.20.3
       source-map-support: 0.5.21
     dev: false
@@ -20336,11 +19759,6 @@ packages:
     resolution: {integrity: sha512-iawgk0hLP3SxGKDfnDJf8wTz4p2qImnyihM5Hh/sGvQ3K37dPi/w8sRhdNIxYA1TwFwc5mDhIJq+O0RsvXBKdQ==}
     dev: false
 
-  /treeify@1.1.0:
-    resolution: {integrity: sha512-1m4RA7xVAJrSGrrXGs0L3YTwyvBs2S8PbRHaLZAkFw7JR8oIFwYtysxlBZhYIa7xSyiYJKZ3iGrrk55cGA3i9A==}
-    engines: {node: '>=0.6'}
-    dev: false
-
   /trim-newlines@3.0.1:
     resolution: {integrity: sha512-c1PTsA3tYrIsLGkJkzHF+w9F2EyxfXGo4UyJc4pFL++FMjnq0HJS69T3M7d//gKrFKwy429bouPescbjecU+Zw==}
     engines: {node: '>=8'}
@@ -20356,6 +19774,7 @@ packages:
   /ts-dedent@2.2.0:
     resolution: {integrity: sha512-q5W7tVM71e2xjHZTlgfTDoPF/SmqKG5hddq9SzR49CH2hayqRKJtQ4mtRlSxKaJlR/+9rEM+mnBHf7I2/BQcpQ==}
     engines: {node: '>=6.10'}
+    dev: true
 
   /ts-map@1.0.3:
     resolution: {integrity: sha512-vDWbsl26LIcPGmDpoVzjEP6+hvHZkBkLW7JpvwbCv/5IYPJlsbzCVXY3wsCeAxAUeTclNOUZxnLdGh3VBD/J6w==}
@@ -20414,15 +19833,8 @@ packages:
   /tslib@2.5.2:
     resolution: {integrity: sha512-5svOrSA2w3iGFDs1HibEVBGbDrAY82bFQ3HZ3ixB+88nsbsWQoKqDRb5UBYAUPEzbBn6dAp5gRNXglySbx1MlA==}
 
-  /tsutils@3.21.0(typescript@5.0.4):
-    resolution: {integrity: sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==}
-    engines: {node: '>= 6'}
-    peerDependencies:
-      typescript: '>=2.8.0 || >= 3.2.0-dev || >= 3.3.0-dev || >= 3.4.0-dev || >= 3.5.0-dev || >= 3.6.0-dev || >= 3.6.0-beta || >= 3.7.0-dev || >= 3.7.0-beta'
-    dependencies:
-      tslib: 1.14.1
-      typescript: 5.0.4
-    dev: true
+  /tslib@2.5.3:
+    resolution: {integrity: sha512-mSxlJJwl3BMEQCUNnxXBU9jP4JBktcEGhURcPR6VQVlnP0FdDEsIaz0C35dXNGLyRfrATNofF0F5p2KPxQgB+w==}
 
   /tsutils@3.21.0(typescript@5.1.3):
     resolution: {integrity: sha512-mHKK3iUXL+3UF6xL5k0PEhKRUBKPBCv/+RkEOpjRWxxx27KKRBmmA60A9pgOUvMi8GKhRMPEmjBRPzs2W7O1OA==}
@@ -20439,11 +19851,6 @@ packages:
     dependencies:
       safe-buffer: 5.2.1
 
-  /tunnel@0.0.6:
-    resolution: {integrity: sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==}
-    engines: {node: '>=0.6.11 <=0.7.0 || >=0.7.3'}
-    dev: false
-
   /tweetnacl@0.14.5:
     resolution: {integrity: sha512-KXXFFdAbFXY4geFIwoyNK+f5Z1b7swfXABfL7HXCmoIWMKU3dmS26672A4EeQtDzLKy7SXmfBu51JolvEKwtGA==}
 
@@ -20502,6 +19909,7 @@ packages:
   /type-fest@2.19.0:
     resolution: {integrity: sha512-RAH822pAdBgcNMAfWnCBU3CFZcfZ/i1eZjwFU/dsLKumyuuP3niueg2UAukXYF0E2AAoc82ZSSf9J0WQBinzHA==}
     engines: {node: '>=12.20'}
+    dev: true
 
   /type-is@1.6.18:
     resolution: {integrity: sha512-TkRKr9sUTxEH8MdfuCSP7VizJyzRNMjj2J2do2Jr3Kym598JVdEksuzPQCnlFPW4ky9Q+iA+ma9BGm06XQBy8g==}
@@ -20522,8 +19930,8 @@ packages:
   /typedarray@0.0.6:
     resolution: {integrity: sha512-/aCDEGatGvZ2BIk+HmLf4ifCJFwvKFNb9/JeZPMulfgFracn9QFcAf5GO8B/mweUjSoblS5In0cWhqpfs/5PQA==}
 
-  /typeorm@0.3.16(ioredis@5.3.2)(pg@8.11.0):
-    resolution: {integrity: sha512-wJ4Qy1oqRKNDdZiBTTaVMqwo/XxC52Q7uNPTjltPgLhvIW173bL6Iad0lhptMOsFlpixFPaUu3PNziaRBwX2Zw==}
+  /typeorm@0.3.17(ioredis@5.3.2)(pg@8.11.0):
+    resolution: {integrity: sha512-UDjUEwIQalO9tWw9O2A4GU+sT3oyoUXheHJy4ft+RFdnRdQctdQ34L9SqE2p7LdwzafHx1maxT+bqXON+Qnmig==}
     engines: {node: '>= 12.9.0'}
     hasBin: true
     peerDependencies:
@@ -20594,19 +20002,13 @@ packages:
       pg: 8.11.0
       reflect-metadata: 0.1.13
       sha.js: 2.4.11
-      tslib: 2.5.0
+      tslib: 2.5.3
       uuid: 9.0.0
       yargs: 17.6.2
     transitivePeerDependencies:
       - supports-color
     dev: false
 
-  /typescript@4.8.4:
-    resolution: {integrity: sha512-QCh+85mCy+h0IGff8r5XWzOVSbBO+KfeYrMQh7NJ58QujwcE22u+NUSmUxqF+un70P9GXKxa2HCNiTTMJknyjQ==}
-    engines: {node: '>=4.2.0'}
-    hasBin: true
-    dev: true
-
   /typescript@5.0.4:
     resolution: {integrity: sha512-cW9T5W9xY37cc+jfEnaUvX91foxtHkza3Nw3wkoF4sSlKn0MONdkdEndig/qPBWXNkmplh3NzayQzCiHM4/hqw==}
     engines: {node: '>=12.20'}
@@ -20676,13 +20078,6 @@ packages:
       undertaker-registry: 1.0.1
     dev: false
 
-  /undici@5.21.0:
-    resolution: {integrity: sha512-HOjK8l6a57b2ZGXOcUsI5NLfoTrfmbOl90ixJDl0AEFG4wgHNDQxtZy15/ZQp7HhjkpaGlp/eneMgtsu1dIlUA==}
-    engines: {node: '>=12.18'}
-    dependencies:
-      busboy: 1.6.0
-    dev: false
-
   /undici@5.22.1:
     resolution: {integrity: sha512-Ji2IJhFXZY0x/0tVBXeQwgPlLWw13GVzpsWPQ3rV50IFMMof2I55PZZxtm4P6iNq+L5znYN9nSTAq0ZyE6lSJw==}
     engines: {node: '>=14.0'}
@@ -20734,16 +20129,16 @@ packages:
     resolution: {integrity: sha512-mZdDpf3vBV5Efh29kMw5tXoup/buMgxLzOt/XKFKcVmi+15ManNQWr6HfZ2aiZTYlYixbdNJ0KFmIZIv52tHSQ==}
     dev: false
 
-  /unique-filename@2.0.1:
-    resolution: {integrity: sha512-ODWHtkkdx3IAR+veKxFV+VBkUMcN+FaqzUUd7IZzt+0zhDZFPFxhlqwPF3YQvMHx1TD0tdgYl+kuPnJ8E6ql7A==}
-    engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0}
+  /unique-filename@3.0.0:
+    resolution: {integrity: sha512-afXhuC55wkAmZ0P18QsVE6kp8JaxrEokN2HGIoIVv2ijHQd419H0+6EigAFcIzXeMIkcIkNBpB3L/DXB3cTS/g==}
+    engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0}
     dependencies:
-      unique-slug: 3.0.0
+      unique-slug: 4.0.0
     dev: false
 
-  /unique-slug@3.0.0:
-    resolution: {integrity: sha512-8EyMynh679x/0gqE9fT9oilG+qEt+ibFyqjuVTsZn1+CMxH+XLlpvr2UZx4nVcCwTpx81nICr2JQFkM+HPLq4w==}
-    engines: {node: ^12.13.0 || ^14.15.0 || >=16.0.0}
+  /unique-slug@4.0.0:
+    resolution: {integrity: sha512-WrcA6AyEfqDX5bWige/4NQfPZMtASNVxdmWR76WESYQVAACSgWcR6e9i0mofqqBxYFtL4oAxPIptY73/0YE1DQ==}
+    engines: {node: ^14.17.0 || ^16.13.0 || >=18.0.0}
     dependencies:
       imurmurhash: 0.1.4
     dev: false
@@ -20793,6 +20188,7 @@ packages:
   /universalify@2.0.0:
     resolution: {integrity: sha512-hAZsKq7Yy11Zu1DE0OzWjw7nnLZmJZYTDZZyEFHZdUhV8FkH5MCfoU1XMaxXovpyW5nq5scPqq0ZDP9Zyl04oQ==}
     engines: {node: '>= 10.0.0'}
+    dev: true
 
   /unload@2.4.1:
     resolution: {integrity: sha512-IViSAm8Z3sRBYA+9wc0fLQmU9Nrxb16rcDmIiR6Y9LJSZzI7QY5QsDhqPpKOjAn0O9/kfK1TfNEMMAGPTIraPw==}
@@ -20806,7 +20202,7 @@ packages:
   /unplugin@0.10.2:
     resolution: {integrity: sha512-6rk7GUa4ICYjae5PrAllvcDeuT8pA9+j5J5EkxbMFaV+SalHhxZ7X2dohMzu6C3XzsMT+6jwR/+pwPNR3uK9MA==}
     dependencies:
-      acorn: 8.8.2
+      acorn: 8.9.0
       chokidar: 3.5.3
       webpack-sources: 3.2.3
       webpack-virtual-modules: 0.4.6
@@ -20815,7 +20211,7 @@ packages:
   /unplugin@1.3.1:
     resolution: {integrity: sha512-h4uUTIvFBQRxUKS2Wjys6ivoeofGhxzTe2sRWlooyjHXVttcVfV/JiavNd3d4+jty0SVV0dxGw9AkY9MwiaCEw==}
     dependencies:
-      acorn: 8.8.2
+      acorn: 8.9.0
       chokidar: 3.5.3
       webpack-sources: 3.2.3
       webpack-virtual-modules: 0.5.0
@@ -20912,6 +20308,7 @@ packages:
       is-generator-function: 1.0.10
       is-typed-array: 1.1.10
       which-typed-array: 1.1.9
+    dev: true
 
   /utils-merge@1.0.1:
     resolution: {integrity: sha512-pMZTvIkT1d+TFGvDOqodOclx0QWkkgi6Tdoa8gC8ffGAAqz9pzPTZWAybbsHHoED/ztMtkv/VoYTYyShUn81hA==}
@@ -21037,8 +20434,8 @@ packages:
       replace-ext: 1.0.1
     dev: false
 
-  /vite-node@0.31.4(@types/node@20.2.5)(sass@1.62.1):
-    resolution: {integrity: sha512-uzL377GjJtTbuc5KQxVbDu2xfU/x0wVjUtXQR2ihS21q/NK6ROr4oG0rsSkBBddZUVCwzfx22in76/0ZZHXgkQ==}
+  /vite-node@0.32.2(@types/node@20.3.1)(sass@1.63.6):
+    resolution: {integrity: sha512-dTQ1DCLwl2aEseov7cfQ+kDMNJpM1ebpyMMMwWzBvLbis8Nla/6c9WQcqpPssTwS6Rp/+U6KwlIj8Eapw4bLdA==}
     engines: {node: '>=v14.18.0'}
     hasBin: true
     dependencies:
@@ -21047,7 +20444,7 @@ packages:
       mlly: 1.2.0
       pathe: 1.1.0
       picocolors: 1.0.0
-      vite: 4.3.9(@types/node@20.2.5)(sass@1.62.1)
+      vite: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
     transitivePeerDependencies:
       - '@types/node'
       - less
@@ -21062,7 +20459,7 @@ packages:
     resolution: {integrity: sha512-irjKcKXRn7v5bPAg4mAbsS6DgibpP1VUFL9tlgxU6lloK6V9yw9qCZkS+s2PtbkZpWNzr3TN3zVJAc6J7gJZmA==}
     dev: true
 
-  /vite@4.3.9(@types/node@20.2.5)(sass@1.62.1):
+  /vite@4.3.9(@types/node@20.3.1)(sass@1.63.6):
     resolution: {integrity: sha512-qsTNZjO9NoJNW7KnOrgYwczm0WctJ8m/yqYAMAK9Lxt4SoySUfS5S8ia9K7JHpa3KEeMfyF8LoJ3c5NeBJy6pg==}
     engines: {node: ^14.18.0 || >=16.0.0}
     hasBin: true
@@ -21087,28 +20484,28 @@ packages:
       terser:
         optional: true
     dependencies:
-      '@types/node': 20.2.5
+      '@types/node': 20.3.1
       esbuild: 0.17.18
       postcss: 8.4.23
-      rollup: 3.23.0
-      sass: 1.62.1
+      rollup: 3.25.1
+      sass: 1.63.6
     optionalDependencies:
       fsevents: 2.3.2
 
-  /vitest-fetch-mock@0.2.2(vitest@0.31.4):
+  /vitest-fetch-mock@0.2.2(vitest@0.32.2):
     resolution: {integrity: sha512-XmH6QgTSjCWrqXoPREIdbj40T7i1xnGmAsTAgfckoO75W1IEHKR8hcPCQ7SO16RsdW1t85oUm6pcQRLeBgjVYQ==}
     engines: {node: '>=14.14.0'}
     peerDependencies:
       vitest: '>=0.16.0'
     dependencies:
       cross-fetch: 3.1.5
-      vitest: 0.31.4(happy-dom@9.20.3)(sass@1.62.1)
+      vitest: 0.32.2(happy-dom@9.20.3)(sass@1.63.6)
     transitivePeerDependencies:
       - encoding
     dev: true
 
-  /vitest@0.31.4(happy-dom@9.20.3)(sass@1.62.1):
-    resolution: {integrity: sha512-GoV0VQPmWrUFOZSg3RpQAPN+LPmHg2/gxlMNJlyxJihkz6qReHDV6b0pPDcqFLNEPya4tWJ1pgwUNP9MLmUfvQ==}
+  /vitest@0.32.2(happy-dom@9.20.3)(sass@1.63.6):
+    resolution: {integrity: sha512-hU8GNNuQfwuQmqTLfiKcqEhZY72Zxb7nnN07koCUNmntNxbKQnVbeIS6sqUgR3eXSlbOpit8+/gr1KpqoMgWCQ==}
     engines: {node: '>=v14.18.0'}
     hasBin: true
     peerDependencies:
@@ -21140,13 +20537,13 @@ packages:
     dependencies:
       '@types/chai': 4.3.5
       '@types/chai-subset': 1.3.3
-      '@types/node': 20.2.5
-      '@vitest/expect': 0.31.4
-      '@vitest/runner': 0.31.4
-      '@vitest/snapshot': 0.31.4
-      '@vitest/spy': 0.31.4
-      '@vitest/utils': 0.31.4
-      acorn: 8.8.2
+      '@types/node': 20.3.1
+      '@vitest/expect': 0.32.2
+      '@vitest/runner': 0.32.2
+      '@vitest/snapshot': 0.32.2
+      '@vitest/spy': 0.32.2
+      '@vitest/utils': 0.32.2
+      acorn: 8.9.0
       acorn-walk: 8.2.0
       cac: 6.7.14
       chai: 4.3.7
@@ -21161,8 +20558,8 @@ packages:
       strip-literal: 1.0.1
       tinybench: 2.5.0
       tinypool: 0.5.0
-      vite: 4.3.9(@types/node@20.2.5)(sass@1.62.1)
-      vite-node: 0.31.4(@types/node@20.2.5)(sass@1.62.1)
+      vite: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
+      vite-node: 0.32.2(@types/node@20.3.1)(sass@1.63.6)
       why-is-node-running: 2.2.2
     transitivePeerDependencies:
       - less
@@ -21199,20 +20596,20 @@ packages:
       - vue
     dev: true
 
-  /vue-eslint-parser@9.3.0(eslint@8.41.0):
-    resolution: {integrity: sha512-48IxT9d0+wArT1+3wNIy0tascRoywqSUe2E1YalIC1L8jsUGe5aJQItWfRok7DVFGz3UYvzEI7n5wiTXsCMAcQ==}
+  /vue-eslint-parser@9.3.1(eslint@8.43.0):
+    resolution: {integrity: sha512-Clr85iD2XFZ3lJ52/ppmUDG/spxQu6+MAeHXjjyI4I1NUYZ9xmenQp4N0oaHJhrA8OOxltCVxMRfANGa70vU0g==}
     engines: {node: ^14.17.0 || >=16.0.0}
     peerDependencies:
       eslint: '>=6.0.0'
     dependencies:
       debug: 4.3.4(supports-color@8.1.1)
-      eslint: 8.41.0
+      eslint: 8.43.0
       eslint-scope: 7.2.0
       eslint-visitor-keys: 3.4.1
       espree: 9.5.2
       esquery: 1.4.2
       lodash: 4.17.21
-      semver: 7.5.1
+      semver: 7.5.3
     transitivePeerDependencies:
       - supports-color
     dev: true
@@ -21241,15 +20638,15 @@ packages:
       he: 1.2.0
     dev: true
 
-  /vue-tsc@1.6.5(typescript@5.1.3):
-    resolution: {integrity: sha512-Wtw3J7CC+JM2OR56huRd5iKlvFWpvDiU+fO1+rqyu4V2nMTotShz4zbOZpW5g9fUOcjnyZYfBo5q5q+D/q27JA==}
+  /vue-tsc@1.8.1(typescript@5.1.3):
+    resolution: {integrity: sha512-GxBQrcb0Qvyrj1uZqnTXQyWbXdNDRY2MTa+r7ESgjhf+WzBSdxZfkS3KD/C3WhKYG+aN8hf44Hp5Gqzb6PehAA==}
     hasBin: true
     peerDependencies:
       typescript: '*'
     dependencies:
-      '@volar/vue-language-core': 1.6.5
-      '@volar/vue-typescript': 1.6.5(typescript@5.1.3)
-      semver: 7.5.1
+      '@vue/language-core': 1.8.1(typescript@5.1.3)
+      '@vue/typescript': 1.8.1(typescript@5.1.3)
+      semver: 7.5.3
       typescript: 5.1.3
     dev: true
 
@@ -21320,17 +20717,16 @@ packages:
       '@zxing/text-encoding': 0.9.0
     dev: true
 
-  /web-push@3.6.1:
-    resolution: {integrity: sha512-+eN2/4Ybu+nkRgXqlPXUzqeA5BgQ7J4StYJM/e2uJpsSIGhkZJFrTlCx+ow9sD0mn+4jgbo2FkFoMBKftl49ZQ==}
-    engines: {node: '>= 6'}
+  /web-push@3.6.3:
+    resolution: {integrity: sha512-3RlA0lRmLcwlHCRR94Tz+Fw6wPtm0lFm8oyukQunlEIarANxE84Ox9XBgF4+jNlXgO40DIwblOiC43oR46helA==}
+    engines: {node: '>= 16'}
     hasBin: true
     dependencies:
       asn1.js: 5.4.1
       http_ece: 1.1.0
-      https-proxy-agent: 5.0.1
+      https-proxy-agent: 7.0.0
       jws: 4.0.0
       minimist: 1.2.8
-      urlsafe-base64: 1.0.0
     transitivePeerDependencies:
       - supports-color
     dev: false
@@ -21428,6 +20824,7 @@ packages:
       gopd: 1.0.1
       has-tostringtag: 1.0.0
       is-typed-array: 1.1.10
+    dev: true
 
   /which@1.3.1:
     resolution: {integrity: sha512-HxJdYWq1MTIQbJ3nw0cqssHoTNU267KlrDuGZ1WYlxDStUtKUhOaJmh112/TZmHxxUfuJqPXSOm7tDyas0OSIQ==}
@@ -21515,6 +20912,15 @@ packages:
       string-width: 4.2.3
       strip-ansi: 6.0.1
 
+  /wrap-ansi@8.1.0:
+    resolution: {integrity: sha512-si7QWI6zUMq56bESFvagtmzMdGOtoxfR+Sez11Mobfc7tm+VkUckk9bW2UeffTGVUbOksxmSw0AA2gs8g71NCQ==}
+    engines: {node: '>=12'}
+    dependencies:
+      ansi-styles: 6.2.1
+      string-width: 5.1.2
+      strip-ansi: 7.1.0
+    dev: false
+
   /wrappy@1.0.2:
     resolution: {integrity: sha512-l4Sp/DRseor9wL6EvV2+TuQn63dMkPjZ/sp9XkghTEbV9KlPS1xUsZ3u7/IQO4wxtcFB4bgpQPRcR3QCvezPcQ==}
 
@@ -21618,6 +21024,11 @@ packages:
   /yallist@4.0.0:
     resolution: {integrity: sha512-3wdGidZyq5PB084XLES5TpOSRA3wjXAlIWMhum2kRcv/41Sn2emQ0dycQW4uZXLejwKvg6EsvbdlVL+FYEct7A==}
 
+  /yaml@2.3.1:
+    resolution: {integrity: sha512-2eHWfjaoXgTBC2jNM1LRef62VQa0umtvRiDSk6HSzW7RvS5YtkabJrwYLLEKWBc8a5U2PTSCs+dJjUTJdlHsWQ==}
+    engines: {node: '>= 14'}
+    dev: false
+
   /yargs-parser@13.1.2:
     resolution: {integrity: sha512-3lbsNRf/j+A4QuSZfDRA7HRSfWrzO0YjqTJd5kjAq37Zep1CEgaYmrH9Q3GwPiB9cHyd1Y1UwggGhJGoxipbzg==}
     dependencies:
@@ -21765,10 +21176,10 @@ packages:
     version: 2.2.1-misskey.3
     dev: false
 
-  github.com/misskey-dev/buraha/92b20c1ab15c5cb5a224cf3b1ecd4f6baca12b7c:
-    resolution: {tarball: https://codeload.github.com/misskey-dev/buraha/tar.gz/92b20c1ab15c5cb5a224cf3b1ecd4f6baca12b7c}
+  github.com/misskey-dev/buraha/822d4be21126156c3e1827a771444b3fceb6be58:
+    resolution: {tarball: https://codeload.github.com/misskey-dev/buraha/tar.gz/822d4be21126156c3e1827a771444b3fceb6be58}
     name: buraha
-    version: 0.0.0
+    version: 0.0.1
     dev: false
 
   github.com/misskey-dev/sharp-read-bmp/02d9dc189fa7df0c4bea09330be26741772dac01:

From fd4c43786a232ece9c940d2c41a03a50bd045f3f Mon Sep 17 00:00:00 2001
From: syuilo <Syuilotan@yahoo.co.jp>
Date: Sat, 24 Jun 2023 18:22:53 +0900
Subject: [PATCH 07/17] chore(dev): use buraha via npm

---
 packages/frontend/package.json |  2 +-
 pnpm-lock.yaml                 | 14 ++++++--------
 2 files changed, 7 insertions(+), 9 deletions(-)

diff --git a/packages/frontend/package.json b/packages/frontend/package.json
index 398d6421a6..034b2fdda3 100644
--- a/packages/frontend/package.json
+++ b/packages/frontend/package.json
@@ -28,7 +28,7 @@
 		"autosize": "6.0.1",
 		"broadcast-channel": "5.1.0",
 		"browser-image-resizer": "github:misskey-dev/browser-image-resizer#v2.2.1-misskey.3",
-		"buraha": "github:misskey-dev/buraha",
+		"buraha": "0.0.1",
 		"canvas-confetti": "1.6.0",
 		"chart.js": "4.3.0",
 		"chartjs-adapter-date-fns": "3.0.0",
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index fcb058828b..3839a2f473 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -674,8 +674,8 @@ importers:
         specifier: github:misskey-dev/browser-image-resizer#v2.2.1-misskey.3
         version: github.com/misskey-dev/browser-image-resizer/0227e860621e55cbed0aabe6dc601096a7748c4a
       buraha:
-        specifier: github:misskey-dev/buraha
-        version: github.com/misskey-dev/buraha/822d4be21126156c3e1827a771444b3fceb6be58
+        specifier: 0.0.1
+        version: 0.0.1
       canvas-confetti:
         specifier: 1.6.0
         version: 1.6.0
@@ -9610,6 +9610,10 @@ packages:
       - supports-color
     dev: false
 
+  /buraha@0.0.1:
+    resolution: {integrity: sha512-G563A0mTbzknm2jDaNxfZuNKIdeArs8T+XQN6t+KbmgnOoevXSXhKDkyf8Md/36Jrx99ikwbCag37VGe3myExQ==}
+    dev: false
+
   /busboy@1.6.0:
     resolution: {integrity: sha512-8SFQbg/0hQ9xy3UNTB0YEnsNBbWfhf7RtnzpL7TkBiTBRfrQ9Fxcnz7VJsleJpyp6rVLvXiuORqjlHi5q+PYuA==}
     engines: {node: '>=10.16.0'}
@@ -21176,12 +21180,6 @@ packages:
     version: 2.2.1-misskey.3
     dev: false
 
-  github.com/misskey-dev/buraha/822d4be21126156c3e1827a771444b3fceb6be58:
-    resolution: {tarball: https://codeload.github.com/misskey-dev/buraha/tar.gz/822d4be21126156c3e1827a771444b3fceb6be58}
-    name: buraha
-    version: 0.0.1
-    dev: false
-
   github.com/misskey-dev/sharp-read-bmp/02d9dc189fa7df0c4bea09330be26741772dac01:
     resolution: {tarball: https://codeload.github.com/misskey-dev/sharp-read-bmp/tar.gz/02d9dc189fa7df0c4bea09330be26741772dac01}
     name: sharp-read-bmp

From f0b5860b9c4bf77261478eec2bcde1bbd21abbcc Mon Sep 17 00:00:00 2001
From: Kagami Sascha Rosylight <saschanaz@outlook.com>
Date: Sat, 24 Jun 2023 14:20:28 +0200
Subject: [PATCH 08/17] chore(misskey-js): fix invalid version string format

---
 packages/misskey-js/package.json | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/packages/misskey-js/package.json b/packages/misskey-js/package.json
index 2f9aba864e..77c9568d80 100644
--- a/packages/misskey-js/package.json
+++ b/packages/misskey-js/package.json
@@ -1,6 +1,6 @@
 {
 	"name": "misskey-js",
-	"version": "0.0.16 ",
+	"version": "0.0.16",
 	"description": "Misskey SDK for JavaScript",
 	"main": "./built/index.js",
 	"types": "./built/index.d.ts",

From 5d922e3084cefd444a7da31ed80a5fbd4bf24d1e Mon Sep 17 00:00:00 2001
From: Kagami Sascha Rosylight <saschanaz@outlook.com>
Date: Sat, 24 Jun 2023 15:20:15 +0200
Subject: [PATCH 09/17] chore(frontend): use @vitest/coverage-v8

---
 packages/frontend/package.json |  2 +-
 pnpm-lock.yaml                 | 36 +++++++++++++++++-----------------
 2 files changed, 19 insertions(+), 19 deletions(-)

diff --git a/packages/frontend/package.json b/packages/frontend/package.json
index 034b2fdda3..b9208a566e 100644
--- a/packages/frontend/package.json
+++ b/packages/frontend/package.json
@@ -116,7 +116,7 @@
 		"@types/ws": "8.5.5",
 		"@typescript-eslint/eslint-plugin": "5.60.0",
 		"@typescript-eslint/parser": "5.60.0",
-		"@vitest/coverage-c8": "0.32.2",
+		"@vitest/coverage-v8": "0.32.2",
 		"@vue/runtime-core": "3.3.4",
 		"acorn": "8.9.0",
 		"chokidar-cli": "3.0.0",
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index 3839a2f473..2259cb2a27 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -932,7 +932,7 @@ importers:
       '@typescript-eslint/parser':
         specifier: 5.60.0
         version: 5.60.0(eslint@8.43.0)(typescript@5.1.3)
-      '@vitest/coverage-c8':
+      '@vitest/coverage-v8':
         specifier: 0.32.2
         version: 0.32.2(vitest@0.32.2)
       '@vue/runtime-core':
@@ -5120,7 +5120,7 @@ packages:
       slash: 3.0.0
       string-length: 4.0.2
       strip-ansi: 6.0.1
-      v8-to-istanbul: 9.0.1
+      v8-to-istanbul: 9.1.0
     transitivePeerDependencies:
       - supports-color
     dev: true
@@ -8210,17 +8210,25 @@ packages:
       vite: 4.3.9(@types/node@20.3.1)(sass@1.63.6)
       vue: 3.3.4
 
-  /@vitest/coverage-c8@0.32.2(vitest@0.32.2):
-    resolution: {integrity: sha512-z07kMTN6e4t1jDY4XXU6W1LxCb3V5Rw7KAZId4VM6BCIGLGz1QqwH9UWYWv7LemqQVnARl5CwaDDwVrkcYgwPg==}
+  /@vitest/coverage-v8@0.32.2(vitest@0.32.2):
+    resolution: {integrity: sha512-/+V3nB3fyeuuSeKxCfi6XmWjDIxpky7AWSkGVfaMjAk7di8igBwRsThLjultwIZdTDH1RAxpjmCXEfSqsMFZOA==}
     peerDependencies:
-      vitest: '>=0.30.0 <1'
+      vitest: '>=0.32.0 <1'
     dependencies:
       '@ampproject/remapping': 2.2.1
-      c8: 7.13.0
+      '@bcoe/v8-coverage': 0.2.3
+      istanbul-lib-coverage: 3.2.0
+      istanbul-lib-report: 3.0.0
+      istanbul-lib-source-maps: 4.0.1
+      istanbul-reports: 3.1.5
       magic-string: 0.30.0
       picocolors: 1.0.0
       std-env: 3.3.2
+      test-exclude: 6.0.0
+      v8-to-istanbul: 9.1.0
       vitest: 0.32.2(happy-dom@9.20.3)(sass@1.63.6)
+    transitivePeerDependencies:
+      - supports-color
     dev: true
 
   /@vitest/expect@0.32.2:
@@ -8364,7 +8372,7 @@ packages:
       '@vue/compiler-dom': 3.3.4
       '@vue/reactivity': 3.3.4
       '@vue/shared': 3.3.4
-      minimatch: 9.0.0
+      minimatch: 9.0.2
       muggle-string: 0.3.1
       typescript: 5.1.3
       vue-template-compiler: 2.7.14
@@ -9645,7 +9653,7 @@ packages:
       istanbul-reports: 3.1.5
       rimraf: 3.0.2
       test-exclude: 6.0.0
-      v8-to-istanbul: 9.0.1
+      v8-to-istanbul: 9.1.0
       yargs: 16.2.0
       yargs-parser: 20.2.9
     dev: true
@@ -15535,19 +15543,11 @@ packages:
     dependencies:
       brace-expansion: 2.0.1
 
-  /minimatch@9.0.0:
-    resolution: {integrity: sha512-0jJj8AvgKqWN05mrwuqi8QYKx1WmYSUoKSxu5Qhs9prezTz10sxAHGNZe9J9cqIJzta8DWsleh2KaVaLl6Ru2w==}
-    engines: {node: '>=16 || 14 >=14.17'}
-    dependencies:
-      brace-expansion: 2.0.1
-    dev: true
-
   /minimatch@9.0.2:
     resolution: {integrity: sha512-PZOT9g5v2ojiTL7r1xF6plNHLtOeTpSlDI007As2NlA2aYBMfVom17yqa6QzhmDP8QOhn7LjHTg7DFCVSSa6yg==}
     engines: {node: '>=16 || 14 >=14.17'}
     dependencies:
       brace-expansion: 2.0.1
-    dev: false
 
   /minimist-options@4.1.0:
     resolution: {integrity: sha512-Q4r8ghd80yhO/0j1O3B2BjweX3fiHg9cdOwjJd2J76Q135c+NDxGCqdYKQ1SKBuFfgWbAUzBfvYjPUEeNgqN1A==}
@@ -20332,8 +20332,8 @@ packages:
   /uuid@9.0.0:
     resolution: {integrity: sha512-MXcSTerfPa4uqyzStbRoTgt5XIe3x5+42+q1sDuy3R5MDk66URdLMOZe5aPX/SQd+kuYAh0FdP/pO28IkQyTeg==}
 
-  /v8-to-istanbul@9.0.1:
-    resolution: {integrity: sha512-74Y4LqY74kLE6IFyIjPtkSTWzUZmj8tdHT9Ii/26dvQ6K9Dl2NbEfj0XgU2sHCtKgt5VupqhlO/5aWuqS+IY1w==}
+  /v8-to-istanbul@9.1.0:
+    resolution: {integrity: sha512-6z3GW9x8G1gd+JIIgQQQxXuiJtCXeAjp6RaPEPLv62mH3iPHPxV6W3robxtCzNErRo6ZwTmzWhsbNvjyEBKzKA==}
     engines: {node: '>=10.12.0'}
     dependencies:
       '@jridgewell/trace-mapping': 0.3.17

From a2c0573f843ee9e8b17d97a6d0e0b5582653fe35 Mon Sep 17 00:00:00 2001
From: Kagami Sascha Rosylight <saschanaz@outlook.com>
Date: Sat, 24 Jun 2023 23:35:09 +0200
Subject: [PATCH 10/17] refactor(backend): replace private-ip with ipaddr.js
 (#11041)

* refactor(backend): replace private-ip with ipaddr.js

* restore ip-cidr
---
 packages/backend/package.json                |  2 +-
 packages/backend/src/core/DownloadService.ts | 18 ++++++------
 packages/backend/src/misc/get-ip-hash.ts     |  2 +-
 pnpm-lock.yaml                               | 31 ++++----------------
 4 files changed, 17 insertions(+), 36 deletions(-)

diff --git a/packages/backend/package.json b/packages/backend/package.json
index c5b6278b69..b9995d8117 100644
--- a/packages/backend/package.json
+++ b/packages/backend/package.json
@@ -100,6 +100,7 @@
 		"hpagent": "1.2.0",
 		"ioredis": "5.3.2",
 		"ip-cidr": "3.1.0",
+		"ipaddr.js": "2.1.0",
 		"is-svg": "4.3.2",
 		"js-yaml": "4.1.0",
 		"jsdom": "22.1.0",
@@ -120,7 +121,6 @@
 		"otpauth": "9.1.2",
 		"parse5": "7.1.2",
 		"pg": "8.11.0",
-		"private-ip": "3.0.0",
 		"probe-image-size": "7.2.3",
 		"promise-limit": "2.7.0",
 		"pug": "3.0.2",
diff --git a/packages/backend/src/core/DownloadService.ts b/packages/backend/src/core/DownloadService.ts
index bd535c6032..09039a8b57 100644
--- a/packages/backend/src/core/DownloadService.ts
+++ b/packages/backend/src/core/DownloadService.ts
@@ -2,8 +2,7 @@ import * as fs from 'node:fs';
 import * as stream from 'node:stream';
 import * as util from 'node:util';
 import { Inject, Injectable } from '@nestjs/common';
-import IPCIDR from 'ip-cidr';
-import PrivateIp from 'private-ip';
+import ipaddr from 'ipaddr.js';
 import chalk from 'chalk';
 import got, * as Got from 'got';
 import { parse } from 'content-disposition';
@@ -123,15 +122,15 @@ export class DownloadService {
 	public async downloadTextFile(url: string): Promise<string> {
 		// Create temp file
 		const [path, cleanup] = await createTemp();
-	
+
 		this.logger.info(`text file: Temp file is ${path}`);
-	
+
 		try {
 			// write content at URL to temp file
 			await this.downloadUrl(url, path);
-	
+
 			const text = await util.promisify(fs.readFile)(path, 'utf8');
-	
+
 			return text;
 		} finally {
 			cleanup();
@@ -140,13 +139,14 @@ export class DownloadService {
 
 	@bindThis
 	private isPrivateIp(ip: string): boolean {
+		const parsedIp = ipaddr.parse(ip);
+
 		for (const net of this.config.allowedPrivateNetworks ?? []) {
-			const cidr = new IPCIDR(net);
-			if (cidr.contains(ip)) {
+			if (parsedIp.match(ipaddr.parseCIDR(net))) {
 				return false;
 			}
 		}
 
-		return PrivateIp(ip) ?? false;
+		return parsedIp.range() !== 'unicast';
 	}
 }
diff --git a/packages/backend/src/misc/get-ip-hash.ts b/packages/backend/src/misc/get-ip-hash.ts
index 70e61aef8c..1a86fb8814 100644
--- a/packages/backend/src/misc/get-ip-hash.ts
+++ b/packages/backend/src/misc/get-ip-hash.ts
@@ -1,6 +1,6 @@
 import IPCIDR from 'ip-cidr';
 
-export function getIpHash(ip: string) {
+export function getIpHash(ip: string): string {
 	try {
 		// because a single person may control many IPv6 addresses,
 		// only a /64 subnet prefix of any IP will be taken into account.
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index 2259cb2a27..97f9a9583c 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -215,6 +215,9 @@ importers:
       ip-cidr:
         specifier: 3.1.0
         version: 3.1.0
+      ipaddr.js:
+        specifier: 2.1.0
+        version: 2.1.0
       is-svg:
         specifier: 4.3.2
         version: 4.3.2
@@ -275,9 +278,6 @@ importers:
       pg:
         specifier: 8.11.0
         version: 8.11.0
-      private-ip:
-        specifier: 3.0.0
-        version: 3.0.0
       probe-image-size:
         specifier: 7.2.3
         version: 7.2.3
@@ -4387,10 +4387,6 @@ packages:
     resolution: {integrity: sha512-BxOqI5LgsIQP1odU5KMwV9yoijleOPzHL18/YvNqF9KFSGF2K/DLlYAbDQsWqd/1nbaFuSkYD/191dpMtNh4vw==}
     dev: false
 
-  /@chainsafe/is-ip@2.0.1:
-    resolution: {integrity: sha512-nqSJ8u2a1Rv9FYbyI8qpDhTYujaKEyLknNrTejLYoSWmdeg+2WB7R6BZqPZYfrJzDxVi3rl6ZQuoaEvpKRZWgQ==}
-    dev: false
-
   /@colors/colors@1.5.0:
     resolution: {integrity: sha512-ooWCrlZP11i8GImSjTHYHLkvFDP48nS4+204nGb1RiX/WXYHmJA2III9/e2DWVabCESdW7hBAEzHRqUn9OUVvQ==}
     engines: {node: '>=0.1.90'}
@@ -13539,11 +13535,6 @@ packages:
     resolution: {integrity: sha512-B9ZWJxHHOHUhUjCPrMpLD4xEq35bUTClHM1S6CBU5ixQnkZmwipwgc96vAd7AAGM9TGHvJR+Uss+/Ak6UphK+Q==}
     engines: {node: '>=8'}
 
-  /ip-regex@5.0.0:
-    resolution: {integrity: sha512-fOCG6lhoKKakwv+C6KdsOnGvgXnmgfmp0myi3bcNwj3qfwPAxRKWEuFhvEFF7ceYIz6+1jRZ+yguLFAmUNPEfw==}
-    engines: {node: ^12.20.0 || ^14.13.1 || >=16.0.0}
-    dev: false
-
   /ip@2.0.0:
     resolution: {integrity: sha512-WKa+XuLG1A1R0UWhl2+1XQSi+fZWMsYKffMZTTYsiZaUD8k2yDAj5atimTUD2TZkyCkNEeYE5NhFZmupOGtjYQ==}
 
@@ -13551,8 +13542,8 @@ packages:
     resolution: {integrity: sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==}
     engines: {node: '>= 0.10'}
 
-  /ipaddr.js@2.0.1:
-    resolution: {integrity: sha512-1qTgH9NG+IIJ4yfKs2e6Pp1bZg8wbDbKHT21HrLIeYBTRLgMYKnMTPAuI3Lcs61nfx5h1xlXnbJtH1kX5/d/ng==}
+  /ipaddr.js@2.1.0:
+    resolution: {integrity: sha512-LlbxQ7xKzfBusov6UMi4MFpEg0m+mAm9xyNGEduwXMEDuf4WfzB/RZwMVYEd7IKGvh4IUkEXYxtAVu9T3OelJQ==}
     engines: {node: '>= 10'}
 
   /irregular-plurals@3.5.0:
@@ -17315,20 +17306,10 @@ packages:
     resolution: {integrity: sha512-5zyFfekIVUOTVbL92hc8LJOtE/gyGHeREHkJ2yTyByP8Q2YZVoBqLg3EfYLeF0oVvGqtaEX2t2Qovja0/gStXw==}
     dependencies:
       ip-regex: 4.3.0
-      ipaddr.js: 2.0.1
+      ipaddr.js: 2.1.0
       is-ip: 3.1.0
       netmask: 2.0.2
 
-  /private-ip@3.0.0:
-    resolution: {integrity: sha512-HkMBs4nMtrP+cvcw0bDi2BAZIGgiKI4Zq8Oc+dMqNBpHS8iGL4+WO/pRtc8Bwnv9rjnV0QwMDwEBymFtqv7Kww==}
-    engines: {node: '>=14.16'}
-    dependencies:
-      '@chainsafe/is-ip': 2.0.1
-      ip-regex: 5.0.0
-      ipaddr.js: 2.0.1
-      netmask: 2.0.2
-    dev: false
-
   /probe-image-size@7.2.3:
     resolution: {integrity: sha512-HubhG4Rb2UH8YtV4ba0Vp5bQ7L78RTONYu/ujmCu5nBI8wGv24s4E9xSKBi0N1MowRpxk76pFCpJtW0KPzOK0w==}
     dependencies:

From 7bb8c71543a7a41aeab6dad4edbb4088f7ae5126 Mon Sep 17 00:00:00 2001
From: Kagami Sascha Rosylight <saschanaz@outlook.com>
Date: Sun, 25 Jun 2023 01:34:18 +0200
Subject: [PATCH 11/17] chore(backend, misskey-js): add type for signup
 (#11043)

* chore(backend, misskey-js): add type for signup

* rerun
---
 packages/backend/test/e2e/2fa.ts            |  45 ++---
 packages/backend/test/e2e/antennas.ts       |   2 +-
 packages/backend/test/e2e/api-visibility.ts |  11 +-
 packages/backend/test/e2e/api.ts            |   7 +-
 packages/backend/test/e2e/block.ts          |   7 +-
 packages/backend/test/e2e/clips.ts          | 130 ++++++------
 packages/backend/test/e2e/endpoints.ts      |  11 +-
 packages/backend/test/e2e/fetch-resource.ts | 209 ++++++++++----------
 packages/backend/test/e2e/ff-visibility.ts  |   5 +-
 packages/backend/test/e2e/move.ts           |  13 +-
 packages/backend/test/e2e/mute.ts           |   7 +-
 packages/backend/test/e2e/note.ts           |   7 +-
 packages/backend/test/e2e/renote-mute.ts    |   7 +-
 packages/backend/test/e2e/streaming.ts      |  11 +-
 packages/backend/test/e2e/thread-mute.ts    |   7 +-
 packages/backend/test/e2e/user-notes.ts     |   3 +-
 packages/backend/test/e2e/users.ts          |  66 +++----
 packages/backend/test/utils.ts              |  22 +--
 packages/misskey-js/etc/misskey-js.api.md   |  33 +++-
 packages/misskey-js/src/api.types.ts        |  17 +-
 packages/misskey-js/src/entities.ts         |  14 ++
 21 files changed, 354 insertions(+), 280 deletions(-)

diff --git a/packages/backend/test/e2e/2fa.ts b/packages/backend/test/e2e/2fa.ts
index 5da997f28b..04be97ad9d 100644
--- a/packages/backend/test/e2e/2fa.ts
+++ b/packages/backend/test/e2e/2fa.ts
@@ -7,10 +7,11 @@ import * as OTPAuth from 'otpauth';
 import { loadConfig } from '../../src/config.js';
 import { signup, api, post, react, startServer, waitFire } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('2要素認証', () => {
 	let app: INestApplicationContext;
-	let alice: unknown;
+	let alice: misskey.entities.MeSignup;
 
 	const config = loadConfig();
 	const password = 'test';
@@ -68,7 +69,7 @@ describe('2要素認証', () => {
 		]));
 
 		// AuthenticatorAssertionResponse.authenticatorData
-		// https://developer.mozilla.org/en-US/docs/Web/API/AuthenticatorAssertionResponse/authenticatorData 
+		// https://developer.mozilla.org/en-US/docs/Web/API/AuthenticatorAssertionResponse/authenticatorData
 		const credentialIdLength = Buffer.allocUnsafe(2);
 		credentialIdLength.writeUInt16BE(param.credentialId.length);
 		const authData = Buffer.concat([
@@ -80,7 +81,7 @@ describe('2要素認証', () => {
 			param.credentialId,
 			credentialPublicKey,
 		]);
-		
+
 		return {
 			attestationObject: cbor.encode({
 				fmt: 'none',
@@ -98,7 +99,7 @@ describe('2要素認証', () => {
 			name: param.keyName,
 		};
 	};
-	
+
 	const signinParam = (): {
 		username: string,
 		password: string,
@@ -130,7 +131,7 @@ describe('2要素認証', () => {
 		'hcaptcha-response'?: string | null,
 	} => {
 		// AuthenticatorAssertionResponse.authenticatorData
-		// https://developer.mozilla.org/en-US/docs/Web/API/AuthenticatorAssertionResponse/authenticatorData 
+		// https://developer.mozilla.org/en-US/docs/Web/API/AuthenticatorAssertionResponse/authenticatorData
 		const authenticatorData = Buffer.concat([
 			rpIdHash(),
 			Buffer.from([0x05]), // flags(1)
@@ -146,7 +147,7 @@ describe('2要素認証', () => {
 			.update(clientDataJSONBuffer)
 			.digest();
 		const privateKey = crypto.createPrivateKey(pemToSign);
-		const signature = crypto.createSign('SHA256') 
+		const signature = crypto.createSign('SHA256')
 			.update(Buffer.concat([authenticatorData, hashedclientDataJSON]))
 			.sign(privateKey);
 		return {
@@ -186,14 +187,14 @@ describe('2要素認証', () => {
 			token: otpToken(registerResponse.body.secret),
 		}, alice);
 		assert.strictEqual(doneResponse.status, 204);
-		
+
 		const usersShowResponse = await api('/users/show', {
 			username,
 		}, alice);
 		assert.strictEqual(usersShowResponse.status, 200);
 		assert.strictEqual(usersShowResponse.body.twoFactorEnabled, true);
-		
-		const signinResponse = await api('/signin', { 
+
+		const signinResponse = await api('/signin', {
 			...signinParam(),
 			token: otpToken(registerResponse.body.secret),
 		});
@@ -211,7 +212,7 @@ describe('2要素認証', () => {
 			token: otpToken(registerResponse.body.secret),
 		}, alice);
 		assert.strictEqual(doneResponse.status, 204);
-		
+
 		const registerKeyResponse = await api('/i/2fa/register-key', {
 			password,
 		}, alice);
@@ -230,7 +231,7 @@ describe('2要素認証', () => {
 		assert.strictEqual(keyDoneResponse.status, 200);
 		assert.strictEqual(keyDoneResponse.body.id, credentialId.toString('hex'));
 		assert.strictEqual(keyDoneResponse.body.name, keyName);
-		
+
 		const usersShowResponse = await api('/users/show', {
 			username,
 		});
@@ -267,7 +268,7 @@ describe('2要素認証', () => {
 			token: otpToken(registerResponse.body.secret),
 		}, alice);
 		assert.strictEqual(doneResponse.status, 204);
-		
+
 		const registerKeyResponse = await api('/i/2fa/register-key', {
 			password,
 		}, alice);
@@ -282,7 +283,7 @@ describe('2要素認証', () => {
 			credentialId,
 		}), alice);
 		assert.strictEqual(keyDoneResponse.status, 200);
-		
+
 		const passwordLessResponse = await api('/i/2fa/password-less', {
 			value: true,
 		}, alice);
@@ -301,7 +302,7 @@ describe('2要素認証', () => {
 		assert.strictEqual(signinResponse.status, 200);
 		assert.strictEqual(signinResponse.body.i, undefined);
 
-		const signinResponse2 = await api('/signin', { 
+		const signinResponse2 = await api('/signin', {
 			...signinWithSecurityKeyParam({
 				keyName,
 				challengeId: signinResponse.body.challengeId,
@@ -324,7 +325,7 @@ describe('2要素認証', () => {
 			token: otpToken(registerResponse.body.secret),
 		}, alice);
 		assert.strictEqual(doneResponse.status, 204);
-		
+
 		const registerKeyResponse = await api('/i/2fa/register-key', {
 			password,
 		}, alice);
@@ -339,14 +340,14 @@ describe('2要素認証', () => {
 			credentialId,
 		}), alice);
 		assert.strictEqual(keyDoneResponse.status, 200);
-		
+
 		const renamedKey = 'other-key';
 		const updateKeyResponse = await api('/i/2fa/update-key', {
 			name: renamedKey,
 			credentialId: credentialId.toString('hex'),
 		}, alice);
 		assert.strictEqual(updateKeyResponse.status, 200);
-				
+
 		const iResponse = await api('/i', {
 		}, alice);
 		assert.strictEqual(iResponse.status, 200);
@@ -366,7 +367,7 @@ describe('2要素認証', () => {
 			token: otpToken(registerResponse.body.secret),
 		}, alice);
 		assert.strictEqual(doneResponse.status, 204);
-		
+
 		const registerKeyResponse = await api('/i/2fa/register-key', {
 			password,
 		}, alice);
@@ -381,7 +382,7 @@ describe('2要素認証', () => {
 			credentialId,
 		}), alice);
 		assert.strictEqual(keyDoneResponse.status, 200);
-		
+
 		// テストの実行順によっては複数残ってるので全部消す
 		const iResponse = await api('/i', {
 		}, alice);
@@ -400,14 +401,14 @@ describe('2要素認証', () => {
 		assert.strictEqual(usersShowResponse.status, 200);
 		assert.strictEqual(usersShowResponse.body.securityKeys, false);
 
-		const signinResponse = await api('/signin', { 
+		const signinResponse = await api('/signin', {
 			...signinParam(),
 			token: otpToken(registerResponse.body.secret),
 		});
 		assert.strictEqual(signinResponse.status, 200);
 		assert.notEqual(signinResponse.body.i, undefined);
 	});
-	
+
 	test('が設定でき、設定解除できる。(パスワードのみでログインできる。)', async () => {
 		const registerResponse = await api('/i/2fa/register', {
 			password,
@@ -418,7 +419,7 @@ describe('2要素認証', () => {
 			token: otpToken(registerResponse.body.secret),
 		}, alice);
 		assert.strictEqual(doneResponse.status, 204);
-		
+
 		const usersShowResponse = await api('/users/show', {
 			username,
 		});
diff --git a/packages/backend/test/e2e/antennas.ts b/packages/backend/test/e2e/antennas.ts
index dd3b09f85a..cb526669f5 100644
--- a/packages/backend/test/e2e/antennas.ts
+++ b/packages/backend/test/e2e/antennas.ts
@@ -32,7 +32,7 @@ describe('アンテナ', () => {
 	// - srcのenumにgroupが残っている
 	// - userGroupIdが残っている, isActiveがない
 	type Antenna = misskey.entities.Antenna | Packed<'Antenna'>;
-	type User = misskey.entities.MeDetailed & { token: string };
+	type User = misskey.entities.MeSignup;
 	type Note = misskey.entities.Note;
 
 	// アンテナを作成できる最小のパラメタ
diff --git a/packages/backend/test/e2e/api-visibility.ts b/packages/backend/test/e2e/api-visibility.ts
index 3af0d35182..f781559d50 100644
--- a/packages/backend/test/e2e/api-visibility.ts
+++ b/packages/backend/test/e2e/api-visibility.ts
@@ -3,6 +3,7 @@ process.env.NODE_ENV = 'test';
 import * as assert from 'assert';
 import { signup, api, post, startServer } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('API visibility', () => {
 	let app: INestApplicationContext;
@@ -18,15 +19,15 @@ describe('API visibility', () => {
 	describe('Note visibility', () => {
 		//#region vars
 		/** ヒロイン */
-		let alice: any;
+		let alice: misskey.entities.MeSignup;
 		/** フォロワー */
-		let follower: any;
+		let follower: misskey.entities.MeSignup;
 		/** 非フォロワー */
-		let other: any;
+		let other: misskey.entities.MeSignup;
 		/** 非フォロワーでもリプライやメンションをされた人 */
-		let target: any;
+		let target: misskey.entities.MeSignup;
 		/** specified mentionでmentionを飛ばされる人 */
-		let target2: any;
+		let target2: misskey.entities.MeSignup;
 
 		/** public-post */
 		let pub: any;
diff --git a/packages/backend/test/e2e/api.ts b/packages/backend/test/e2e/api.ts
index a46f336a70..194ded7e8b 100644
--- a/packages/backend/test/e2e/api.ts
+++ b/packages/backend/test/e2e/api.ts
@@ -3,12 +3,13 @@ process.env.NODE_ENV = 'test';
 import * as assert from 'assert';
 import { signup, api, startServer } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('API', () => {
 	let app: INestApplicationContext;
-	let alice: any;
-	let bob: any;
-	let carol: any;
+	let alice: misskey.entities.MeSignup;
+	let bob: misskey.entities.MeSignup;
+	let carol: misskey.entities.MeSignup;
 
 	beforeAll(async () => {
 		app = await startServer();
diff --git a/packages/backend/test/e2e/block.ts b/packages/backend/test/e2e/block.ts
index 57a46ab38a..8357884092 100644
--- a/packages/backend/test/e2e/block.ts
+++ b/packages/backend/test/e2e/block.ts
@@ -3,14 +3,15 @@ process.env.NODE_ENV = 'test';
 import * as assert from 'assert';
 import { signup, api, post, startServer } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('Block', () => {
 	let app: INestApplicationContext;
 
 	// alice blocks bob
-	let alice: any;
-	let bob: any;
-	let carol: any;
+	let alice: misskey.entities.MeSignup;
+	let bob: misskey.entities.MeSignup;
+	let carol: misskey.entities.MeSignup;
 
 	beforeAll(async () => {
 		app = await startServer();
diff --git a/packages/backend/test/e2e/clips.ts b/packages/backend/test/e2e/clips.ts
index f35aae9dc6..175f2cac97 100644
--- a/packages/backend/test/e2e/clips.ts
+++ b/packages/backend/test/e2e/clips.ts
@@ -13,12 +13,12 @@ import { paramDef as UnfavoriteParamDef } from '@/server/api/endpoints/clips/unf
 import { paramDef as AddNoteParamDef } from '@/server/api/endpoints/clips/add-note.js';
 import { paramDef as RemoveNoteParamDef } from '@/server/api/endpoints/clips/remove-note.js';
 import { paramDef as NotesParamDef } from '@/server/api/endpoints/clips/notes.js';
-import { 
-	signup, 
-	post, 
-	startServer, 
+import {
+	signup,
+	post,
+	startServer,
 	api,
-	successfulApiCall, 
+	successfulApiCall,
 	failedApiCall,
 	ApiRequest,
 	hiddenNote,
@@ -82,14 +82,14 @@ describe('クリップ', () => {
 	const update = async (parameters: Partial<UpdateParam>, request: Partial<ApiRequest> = {}): Promise<Clip> => {
 		const clip = await successfulApiCall<Clip>({
 			endpoint: '/clips/update',
-			parameters: { 
+			parameters: {
 				name: 'updated',
 				...parameters,
 			},
 			user: alice,
 			...request,
 		});
-		
+
 		// 入力が結果として入っていること。clipIdはidになるので消しておく
 		delete (parameters as { clipId?: string }).clipId;
 		assert.deepStrictEqual(clip, {
@@ -98,7 +98,7 @@ describe('クリップ', () => {
 		});
 		return clip;
 	};
-	
+
 	type DeleteParam = JTDDataType<typeof DeleteParamDef>;
 	const deleteClip = async (parameters: DeleteParam, request: Partial<ApiRequest> = {}): Promise<void> => {
 		return await successfulApiCall<void>({
@@ -129,7 +129,7 @@ describe('クリップ', () => {
 			...request,
 		});
 	};
-	
+
 	const usersClips = async (request: Partial<ApiRequest>): Promise<Clip[]> => {
 		return await successfulApiCall<Clip[]>({
 			endpoint: '/users/clips',
@@ -145,14 +145,14 @@ describe('クリップ', () => {
 		bob = await signup({ username: 'bob' });
 
 		// FIXME: misskey-jsのNoteはoutdatedなので直接変換できない
-		aliceNote = await post(alice, { text: 'test' }) as any; 
-		aliceHomeNote = await post(alice, { text: 'home only', visibility: 'home' }) as any; 
-		aliceFollowersNote = await post(alice, { text: 'followers only', visibility: 'followers' }) as any; 
-		aliceSpecifiedNote = await post(alice, { text: 'specified only', visibility: 'specified' }) as any; 
-		bobNote = await post(bob, { text: 'test' }) as any; 
-		bobHomeNote = await post(bob, { text: 'home only', visibility: 'home' }) as any; 
-		bobFollowersNote = await post(bob, { text: 'followers only', visibility: 'followers' }) as any; 
-		bobSpecifiedNote = await post(bob, { text: 'specified only', visibility: 'specified' }) as any; 
+		aliceNote = await post(alice, { text: 'test' }) as any;
+		aliceHomeNote = await post(alice, { text: 'home only', visibility: 'home' }) as any;
+		aliceFollowersNote = await post(alice, { text: 'followers only', visibility: 'followers' }) as any;
+		aliceSpecifiedNote = await post(alice, { text: 'specified only', visibility: 'specified' }) as any;
+		bobNote = await post(bob, { text: 'test' }) as any;
+		bobHomeNote = await post(bob, { text: 'home only', visibility: 'home' }) as any;
+		bobFollowersNote = await post(bob, { text: 'followers only', visibility: 'followers' }) as any;
+		bobSpecifiedNote = await post(bob, { text: 'specified only', visibility: 'specified' }) as any;
 	}, 1000 * 60 * 2);
 
 	afterAll(async () => {
@@ -172,7 +172,7 @@ describe('クリップ', () => {
 	test('の作成ができる', async () => {
 		const res = await create();
 		// ISO 8601で日付が返ってくること
-		assert.strictEqual(res.createdAt, new Date(res.createdAt).toISOString());	
+		assert.strictEqual(res.createdAt, new Date(res.createdAt).toISOString());
 		assert.strictEqual(res.lastClippedAt, null);
 		assert.strictEqual(res.name, 'test');
 		assert.strictEqual(res.description, null);
@@ -217,7 +217,7 @@ describe('クリップ', () => {
 	];
 	test.each(createClipDenyPattern)('の作成は$labelならできない', async ({ parameters }) => failedApiCall({
 		endpoint: '/clips/create',
-		parameters: { 
+		parameters: {
 			...defaultCreate(),
 			...parameters,
 		},
@@ -229,7 +229,7 @@ describe('クリップ', () => {
 	}));
 
 	test('の更新ができる', async () => {
-		const res = await update({ 
+		const res = await update({
 			clipId: (await create()).id,
 			name: 'updated',
 			description: 'new description',
@@ -237,7 +237,7 @@ describe('クリップ', () => {
 		});
 
 		// ISO 8601で日付が返ってくること
-		assert.strictEqual(res.createdAt, new Date(res.createdAt).toISOString());	
+		assert.strictEqual(res.createdAt, new Date(res.createdAt).toISOString());
 		assert.strictEqual(res.lastClippedAt, null);
 		assert.strictEqual(res.name, 'updated');
 		assert.strictEqual(res.description, 'new description');
@@ -251,7 +251,7 @@ describe('クリップ', () => {
 		name: 'updated',
 		...parameters,
 	}));
-	
+
 	test.each([
 		{ label: 'clipIdがnull', parameters: { clipId: null } },
 		{ label: '存在しないクリップ', parameters: { clipId: 'xxxxxx' }, assertion: {
@@ -265,7 +265,7 @@ describe('クリップ', () => {
 		...createClipDenyPattern as any,
 	])('の更新は$labelならできない', async ({ parameters, user, assertion }) => failedApiCall({
 		endpoint: '/clips/update',
-		parameters: { 
+		parameters: {
 			clipId: (await create({}, { user: (user ?? ((): User => alice))() })).id,
 			name: 'updated',
 			...parameters,
@@ -279,7 +279,7 @@ describe('クリップ', () => {
 	}));
 
 	test('の削除ができる', async () => {
-		await deleteClip({ 
+		await deleteClip({
 			clipId: (await create()).id,
 		});
 		assert.deepStrictEqual(await list({}), []);
@@ -297,7 +297,7 @@ describe('クリップ', () => {
 		} },
 	])('の削除は$labelならできない', async ({ parameters, user, assertion }) => failedApiCall({
 		endpoint: '/clips/delete',
-		parameters: { 
+		parameters: {
 			clipId: (await create({}, { user: (user ?? ((): User => alice))() })).id,
 			...parameters,
 		},
@@ -329,14 +329,14 @@ describe('クリップ', () => {
 	});
 
 	test.each([
-		{ label: 'clipId未指定', parameters: { clipId: undefined } }, 
-		{ label: '存在しないクリップ', parameters: { clipId: 'xxxxxx' }, assetion: { 
+		{ label: 'clipId未指定', parameters: { clipId: undefined } },
+		{ label: '存在しないクリップ', parameters: { clipId: 'xxxxxx' }, assetion: {
 			code: 'NO_SUCH_CLIP',
 			id: 'c3c5fe33-d62c-44d2-9ea5-d997703f5c20',
 		} },
 	])('のID指定取得は$labelならできない', async ({ parameters, assetion }) => failedApiCall({
 		endpoint: '/clips/show',
-		parameters: { 
+		parameters: {
 			...parameters,
 		},
 		user: alice,
@@ -361,14 +361,14 @@ describe('クリップ', () => {
 
 		// 返ってくる配列には順序保障がないのでidでソートして厳密比較
 		assert.deepStrictEqual(
-			res.sort(compareBy(s => s.id)), 
+			res.sort(compareBy(s => s.id)),
 			clips.sort(compareBy(s => s.id)),
 		);
 	});
 
 	test('の一覧が取得できる(空)', async () => {
 		const res = await usersClips({
-			parameters: { 
+			parameters: {
 				userId: alice.id,
 			},
 		});
@@ -381,14 +381,14 @@ describe('クリップ', () => {
 	])('の一覧が$label取得できる', async () => {
 		const clips = await createMany({ isPublic: true });
 		const res = await usersClips({
-			parameters: { 
+			parameters: {
 				userId: alice.id,
 			},
 		});
 
 		// 返ってくる配列には順序保障がないのでidでソートして厳密比較
 		assert.deepStrictEqual(
-			res.sort(compareBy<Clip>(s => s.id)), 
+			res.sort(compareBy<Clip>(s => s.id)),
 			clips.sort(compareBy(s => s.id)));
 
 		// 認証状態で見たときだけisFavoritedが入っている
@@ -421,7 +421,7 @@ describe('クリップ', () => {
 		await create({ isPublic: false });
 		const aliceClip = await create({ isPublic: true });
 		const res = await usersClips({
-			parameters: { 
+			parameters: {
 				userId: alice.id,
 				limit: 2,
 			},
@@ -433,7 +433,7 @@ describe('クリップ', () => {
 		const clips = await createMany({ isPublic: true }, 7);
 		clips.sort(compareBy(s => s.id));
 		const res = await usersClips({
-			parameters: { 
+			parameters: {
 				userId: alice.id,
 				sinceId: clips[1].id,
 				untilId: clips[5].id,
@@ -443,7 +443,7 @@ describe('クリップ', () => {
 
 		// Promise.allで返ってくる配列には順序保障がないのでidでソートして厳密比較
 		assert.deepStrictEqual(
-			res.sort(compareBy<Clip>(s => s.id)), 
+			res.sort(compareBy<Clip>(s => s.id)),
 			[clips[2], clips[3], clips[4]], // sinceIdとuntilId自体は結果に含まれない
 			clips[1].id + ' ... ' + clips[3].id + ' with ' + clips.map(s => s.id) + ' vs. ' + res.map(s => s.id));
 	});
@@ -454,7 +454,7 @@ describe('クリップ', () => {
 		{ label: 'limit最大+1', parameters: { limit: 101 } },
 	])('の一覧は$labelだと取得できない', async ({ parameters }) => failedApiCall({
 		endpoint: '/users/clips',
-		parameters: { 
+		parameters: {
 			userId: alice.id,
 			...parameters,
 		},
@@ -520,7 +520,7 @@ describe('クリップ', () => {
 				...request,
 			});
 		};
-	
+
 		beforeEach(async () => {
 			aliceClip = await create();
 		});
@@ -544,7 +544,7 @@ describe('クリップ', () => {
 			assert.strictEqual(clip2.favoritedCount, 1);
 			assert.strictEqual(clip2.isFavorited, false);
 		});
-		
+
 		test('は1つのクリップに対して複数人が設定できる。', async () => {
 			const publicClip = await create({ isPublic: true });
 			await favorite({ clipId: publicClip.id }, { user: bob });
@@ -552,7 +552,7 @@ describe('クリップ', () => {
 			const clip = await show({ clipId: publicClip.id }, { user: bob });
 			assert.strictEqual(clip.favoritedCount, 2);
 			assert.strictEqual(clip.isFavorited, true);
-			
+
 			const clip2 = await show({ clipId: publicClip.id });
 			assert.strictEqual(clip2.favoritedCount, 2);
 			assert.strictEqual(clip2.isFavorited, true);
@@ -581,7 +581,7 @@ describe('クリップ', () => {
 			await favorite({ clipId: aliceClip.id });
 			await failedApiCall({
 				endpoint: '/clips/favorite',
-				parameters: { 
+				parameters: {
 					clipId: aliceClip.id,
 				},
 				user: alice,
@@ -604,7 +604,7 @@ describe('クリップ', () => {
 			} },
 		])('の設定は$labelならできない', async ({ parameters, user, assertion }) => failedApiCall({
 			endpoint: '/clips/favorite',
-			parameters: { 
+			parameters: {
 				clipId: (await create({}, { user: (user ?? ((): User => alice))() })).id,
 				...parameters,
 			},
@@ -615,7 +615,7 @@ describe('クリップ', () => {
 			id: '3d81ceae-475f-4600-b2a8-2bc116157532',
 			...assertion,
 		}));
-		
+
 		test('を設定解除できる。', async () => {
 			await favorite({ clipId: aliceClip.id });
 			await unfavorite({ clipId: aliceClip.id });
@@ -641,7 +641,7 @@ describe('クリップ', () => {
 			} },
 		])('の設定解除は$labelならできない', async ({ parameters, user, assertion }) => failedApiCall({
 			endpoint: '/clips/unfavorite',
-			parameters: { 
+			parameters: {
 				clipId: (await create({}, { user: (user ?? ((): User => alice))() })).id,
 				...parameters,
 			},
@@ -652,7 +652,7 @@ describe('クリップ', () => {
 			id: '3d81ceae-475f-4600-b2a8-2bc116157532',
 			...assertion,
 		}));
-		
+
 		test('を取得できる。', async () => {
 			await favorite({ clipId: aliceClip.id });
 			const favorited = await myFavorites();
@@ -717,7 +717,7 @@ describe('クリップ', () => {
 			const res = await show({ clipId: aliceClip.id });
 			assert.strictEqual(res.lastClippedAt, new Date(res.lastClippedAt ?? '').toISOString());
 			assert.deepStrictEqual(await notes({ clipId: aliceClip.id }), [aliceNote]);
-			
+
 			// 他人の非公開ノートも突っ込める
 			await addNote({ clipId: aliceClip.id, noteId: bobHomeNote.id });
 			await addNote({ clipId: aliceClip.id, noteId: bobFollowersNote.id });
@@ -728,7 +728,7 @@ describe('クリップ', () => {
 			await addNote({ clipId: aliceClip.id, noteId: aliceNote.id });
 			await failedApiCall({
 				endpoint: '/clips/add-note',
-				parameters: { 
+				parameters: {
 					clipId: aliceClip.id,
 					noteId: aliceNote.id,
 				},
@@ -747,10 +747,10 @@ describe('クリップ', () => {
 				text: `test ${i}`,
 			}) as unknown)) as Note[];
 			await Promise.all(noteList.map(s => addNote({ clipId: aliceClip.id, noteId: s.id })));
-			
+
 			await failedApiCall({
 				endpoint: '/clips/add-note',
-				parameters: { 
+				parameters: {
 					clipId: aliceClip.id,
 					noteId: aliceNote.id,
 				},
@@ -764,7 +764,7 @@ describe('クリップ', () => {
 
 		test('は他人のクリップへ追加できない。', async () => await failedApiCall({
 			endpoint: '/clips/add-note',
-			parameters: { 
+			parameters: {
 				clipId: aliceClip.id,
 				noteId: aliceNote.id,
 			},
@@ -776,9 +776,9 @@ describe('クリップ', () => {
 		}));
 
 		test.each([
-			{ label: 'clipId未指定', parameters: { clipId: undefined } }, 
-			{ label: 'noteId未指定', parameters: { noteId: undefined } }, 
-			{ label: '存在しないクリップ', parameters: { clipId: 'xxxxxx' }, assetion: { 
+			{ label: 'clipId未指定', parameters: { clipId: undefined } },
+			{ label: 'noteId未指定', parameters: { noteId: undefined } },
+			{ label: '存在しないクリップ', parameters: { clipId: 'xxxxxx' }, assetion: {
 				code: 'NO_SUCH_CLIP',
 				id: 'd6e76cc0-a1b5-4c7c-a287-73fa9c716dcf',
 			} },
@@ -792,7 +792,7 @@ describe('クリップ', () => {
 			} },
 		])('の追加は$labelだとできない', async ({ parameters, user, assetion }) => failedApiCall({
 			endpoint: '/clips/add-note',
-			parameters: { 
+			parameters: {
 				clipId: aliceClip.id,
 				noteId: aliceNote.id,
 				...parameters,
@@ -810,11 +810,11 @@ describe('クリップ', () => {
 			await removeNote({ clipId: aliceClip.id, noteId: aliceNote.id });
 			assert.deepStrictEqual(await notes({ clipId: aliceClip.id }), []);
 		});
-		
+
 		test.each([
-			{ label: 'clipId未指定', parameters: { clipId: undefined } }, 
-			{ label: 'noteId未指定', parameters: { noteId: undefined } }, 
-			{ label: '存在しないクリップ', parameters: { clipId: 'xxxxxx' }, assetion: { 
+			{ label: 'clipId未指定', parameters: { clipId: undefined } },
+			{ label: 'noteId未指定', parameters: { noteId: undefined } },
+			{ label: '存在しないクリップ', parameters: { clipId: 'xxxxxx' }, assetion: {
 				code: 'NO_SUCH_CLIP',
 				id: 'b80525c6-97f7-49d7-a42d-ebccd49cfd52', // add-noteと異なる
 			} },
@@ -828,7 +828,7 @@ describe('クリップ', () => {
 			} },
 		])('の削除は$labelだとできない', async ({ parameters, user, assetion }) => failedApiCall({
 			endpoint: '/clips/remove-note',
-			parameters: { 
+			parameters: {
 				clipId: aliceClip.id,
 				noteId: aliceNote.id,
 				...parameters,
@@ -848,12 +848,12 @@ describe('クリップ', () => {
 			}
 
 			const res = await notes({ clipId: aliceClip.id });
-			
+
 			// 自分のノートは非公開でも入れられるし、見える
 			// 他人の非公開ノートは入れられるけど、除外される
 			const expects = [
 				aliceNote, aliceHomeNote, aliceFollowersNote, aliceSpecifiedNote,
-				bobNote, bobHomeNote, 
+				bobNote, bobHomeNote,
 			];
 			assert.deepStrictEqual(
 				res.sort(compareBy(s => s.id)),
@@ -867,7 +867,7 @@ describe('クリップ', () => {
 				await addNote({ clipId: aliceClip.id, noteId: note.id });
 			}
 
-			const res = await notes({ 
+			const res = await notes({
 				clipId: aliceClip.id,
 				sinceId: noteList[2].id,
 				limit: 3,
@@ -892,7 +892,7 @@ describe('クリップ', () => {
 				sinceId: noteList[1].id,
 				untilId: noteList[4].id,
 			});
-			
+
 			// Promise.allで返ってくる配列はID順で並んでないのでソートして厳密比較
 			const expects = [noteList[2], noteList[3]];
 			assert.deepStrictEqual(
@@ -918,7 +918,7 @@ describe('クリップ', () => {
 
 			const res = await notes({ clipId: publicClip.id }, { user: undefined });
 			const expects = [
-				aliceNote, aliceHomeNote, 
+				aliceNote, aliceHomeNote,
 				// 認証なしだと非公開ノートは結果には含むけどhideされる。
 				hiddenNote(aliceFollowersNote), hiddenNote(aliceSpecifiedNote),
 			];
@@ -926,7 +926,7 @@ describe('クリップ', () => {
 				res.sort(compareBy(s => s.id)),
 				expects.sort(compareBy(s => s.id)));
 		});
-		
+
 		test.todo('ブロック、ミュートされたユーザーからの設定&取得etc.');
 
 		test.each([
@@ -947,7 +947,7 @@ describe('クリップ', () => {
 			} },
 		])('は$labelだと取得できない', async ({ parameters, user, assertion }) => failedApiCall({
 			endpoint: '/clips/notes',
-			parameters: { 
+			parameters: {
 				clipId: aliceClip.id,
 				...parameters,
 			},
diff --git a/packages/backend/test/e2e/endpoints.ts b/packages/backend/test/e2e/endpoints.ts
index f885209b7f..a1e89d4833 100644
--- a/packages/backend/test/e2e/endpoints.ts
+++ b/packages/backend/test/e2e/endpoints.ts
@@ -4,17 +4,18 @@ import * as assert from 'assert';
 // node-fetch only supports it's own Blob yet
 // https://github.com/node-fetch/node-fetch/pull/1664
 import { Blob } from 'node-fetch';
+import { User } from '@/models/index.js';
 import { startServer, signup, post, api, uploadFile, simpleGet, initTestDb } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
-import { User } from '@/models/index.js';
+import type * as misskey from 'misskey-js';
 
 describe('Endpoints', () => {
 	let app: INestApplicationContext;
 
-	let alice: any;
-	let bob: any;
-	let carol: any;
-	let dave: any;
+	let alice: misskey.entities.MeSignup;
+	let bob: misskey.entities.MeSignup;
+	let carol: misskey.entities.MeSignup;
+	let dave: misskey.entities.MeSignup;
 
 	beforeAll(async () => {
 		app = await startServer();
diff --git a/packages/backend/test/e2e/fetch-resource.ts b/packages/backend/test/e2e/fetch-resource.ts
index 78ca8b43ba..115945dd3d 100644
--- a/packages/backend/test/e2e/fetch-resource.ts
+++ b/packages/backend/test/e2e/fetch-resource.ts
@@ -4,6 +4,7 @@ import * as assert from 'assert';
 import { startServer, channel, clip, cookie, galleryPost, signup, page, play, post, simpleGet, uploadFile } from '../utils.js';
 import type { SimpleGetResponse } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 // Request Accept
 const ONLY_AP = 'application/activity+json';
@@ -19,7 +20,7 @@ const JSON_UTF8 = 'application/json; charset=utf-8';
 describe('Webリソース', () => {
 	let app: INestApplicationContext;
 
-	let alice: any;
+	let alice: misskey.entities.MeSignup;
 	let aliceUploadedFile: any;
 	let alicesPost: any;
 	let alicePage: any;
@@ -28,8 +29,8 @@ describe('Webリソース', () => {
 	let aliceGalleryPost: any;
 	let aliceChannel: any;
 
-	type Request = { 
-		path: string, 
+	type Request = {
+		path: string,
 		accept?: string,
 		cookie?: string,
 	};
@@ -46,7 +47,7 @@ describe('Webリソース', () => {
 	const notOk = async (param: Request & {
 		status?: number,
 		code?: string,
-	}): Promise<SimpleGetResponse> => {	
+	}): Promise<SimpleGetResponse> => {
 		const { path, accept, cookie, status, code } = param;
 		const res = await simpleGet(path, accept, cookie);
 		assert.notStrictEqual(res.status, 200);
@@ -58,8 +59,8 @@ describe('Webリソース', () => {
 		}
 		return res;
 	};
-	
-	const notFound = async (param: Request): Promise<SimpleGetResponse> => {	
+
+	const notFound = async (param: Request): Promise<SimpleGetResponse> => {
 		return await notOk({
 			...param,
 			status: 404,
@@ -94,23 +95,23 @@ describe('Webリソース', () => {
 		{ path: '/', type: HTML },
 		{ path: '/docs/ja-JP/about', type: HTML }, // "指定されたURLに該当するページはありませんでした。"
 		// fastify-static gives charset=UTF-8 instead of utf-8 and that's okay
-		{ path: '/api-doc', type: 'text/html; charset=UTF-8' }, 
-		{ path: '/api.json', type: JSON_UTF8 }, 
-		{ path: '/api-console', type: HTML }, 
-		{ path: '/_info_card_', type: HTML }, 
-		{ path: '/bios', type: HTML }, 
-		{ path: '/cli', type: HTML }, 
-		{ path: '/flush', type: HTML }, 
+		{ path: '/api-doc', type: 'text/html; charset=UTF-8' },
+		{ path: '/api.json', type: JSON_UTF8 },
+		{ path: '/api-console', type: HTML },
+		{ path: '/_info_card_', type: HTML },
+		{ path: '/bios', type: HTML },
+		{ path: '/cli', type: HTML },
+		{ path: '/flush', type: HTML },
 		{ path: '/robots.txt', type: 'text/plain; charset=UTF-8' },
-		{ path: '/favicon.ico', type: 'image/vnd.microsoft.icon' }, 
+		{ path: '/favicon.ico', type: 'image/vnd.microsoft.icon' },
 		{ path: '/opensearch.xml', type: 'application/opensearchdescription+xml' },
-		{ path: '/apple-touch-icon.png', type: 'image/png' }, 
-		{ path: '/twemoji/2764.svg', type: 'image/svg+xml' }, 
-		{ path: '/twemoji/2764-fe0f-200d-1f525.svg', type: 'image/svg+xml' }, 
-		{ path: '/twemoji-badge/2764.png', type: 'image/png' }, 
+		{ path: '/apple-touch-icon.png', type: 'image/png' },
+		{ path: '/twemoji/2764.svg', type: 'image/svg+xml' },
+		{ path: '/twemoji/2764-fe0f-200d-1f525.svg', type: 'image/svg+xml' },
+		{ path: '/twemoji-badge/2764.png', type: 'image/png' },
 		{ path: '/twemoji-badge/2764-fe0f-200d-1f525.png', type: 'image/png' },
-		{ path: '/fluent-emoji/2764.png', type: 'image/png' }, 
-		{ path: '/fluent-emoji/2764-fe0f-200d-1f525.png', type: 'image/png' }, 
+		{ path: '/fluent-emoji/2764.png', type: 'image/png' },
+		{ path: '/fluent-emoji/2764-fe0f-200d-1f525.png', type: 'image/png' },
 	])('$path', (p) => {
 		test('がGETできる。', async () => await ok({ ...p }));
 
@@ -120,58 +121,58 @@ describe('Webリソース', () => {
 	});
 
 	describe.each([
-		{ path: '/twemoji/2764.png' }, 
-		{ path: '/twemoji/2764-fe0f-200d-1f525.png' }, 
-		{ path: '/twemoji-badge/2764.svg' }, 
+		{ path: '/twemoji/2764.png' },
+		{ path: '/twemoji/2764-fe0f-200d-1f525.png' },
+		{ path: '/twemoji-badge/2764.svg' },
 		{ path: '/twemoji-badge/2764-fe0f-200d-1f525.svg' },
-		{ path: '/fluent-emoji/2764.svg' }, 
-		{ path: '/fluent-emoji/2764-fe0f-200d-1f525.svg' }, 
+		{ path: '/fluent-emoji/2764.svg' },
+		{ path: '/fluent-emoji/2764-fe0f-200d-1f525.svg' },
 	])('$path', ({ path }) => {
 		test('はGETできない。', async () => await notFound({ path }));
 	});
 
 	describe.each([
-		{ ext: 'rss', type: 'application/rss+xml; charset=utf-8' }, 
-		{ ext: 'atom', type: 'application/atom+xml; charset=utf-8' }, 
-		{ ext: 'json', type: 'application/json; charset=utf-8' }, 
+		{ ext: 'rss', type: 'application/rss+xml; charset=utf-8' },
+		{ ext: 'atom', type: 'application/atom+xml; charset=utf-8' },
+		{ ext: 'json', type: 'application/json; charset=utf-8' },
 	])('/@:username.$ext', ({ ext, type }) => {
 		const path = (username: string): string => `/@${username}.${ext}`;
 
-		test('がGETできる。', async () => await ok({ 
+		test('がGETできる。', async () => await ok({
 			path: path(alice.username),
 			type,
 		}));
 
-		test('は存在しないユーザーはGETできない。', async () => await notOk({ 
+		test('は存在しないユーザーはGETできない。', async () => await notOk({
 			path: path('nonexisting'),
-			status: 404, 
+			status: 404,
 		}));
 	});
 
 	describe.each([{ path: '/api/foo' }])('$path', ({ path }) => {
-		test('はGETできない。', async () => await notOk({ 
+		test('はGETできない。', async () => await notOk({
 			path,
-			status: 404, 
+			status: 404,
 			code: 'UNKNOWN_API_ENDPOINT',
 		}));
 	});
 
 	describe.each([{ path: '/queue' }])('$path', ({ path }) => {
-		test('はadminでなければGETできない。', async () => await notOk({ 
+		test('はadminでなければGETできない。', async () => await notOk({
 			path,
 			status: 500, // FIXME? 403ではない。
 		}));
-		
-		test('はadminならGETできる。', async () => await ok({ 
+
+		test('はadminならGETできる。', async () => await ok({
 			path,
 			cookie: cookie(alice),
-		}));	
+		}));
 	});
 
 	describe.each([{ path: '/streaming' }])('$path', ({ path }) => {
-		test('はGETできない。', async () => await notOk({ 
+		test('はGETできない。', async () => await notOk({
 			path,
-			status: 503, 
+			status: 503,
 		}));
 	});
 
@@ -183,21 +184,21 @@ describe('Webリソース', () => {
 			{ accept: UNSPECIFIED },
 		])('(Acceptヘッダ: $accept)', ({ accept }) => {
 			test('はHTMLとしてGETできる。', async () => {
-				const res = await ok({ 
-					path: path(alice.username), 
-					accept, 
+				const res = await ok({
+					path: path(alice.username),
+					accept,
 					type: HTML,
 				});
 				assert.strictEqual(metaTag(res, 'misskey:user-username'), alice.username);
 				assert.strictEqual(metaTag(res, 'misskey:user-id'), alice.id);
-				
+
 				// TODO ogタグの検証
 				// TODO profile.noCrawleの検証
 				// TODO twitter:creatorの検証
 				// TODO <link rel="me" ...>の検証
 			});
-			test('はHTMLとしてGETできる。(存在しないIDでも。)', async () => await ok({ 
-				path: path('xxxxxxxxxx'), 
+			test('はHTMLとしてGETできる。(存在しないIDでも。)', async () => await ok({
+				path: path('xxxxxxxxxx'),
 				type: HTML,
 			}));
 		});
@@ -207,22 +208,22 @@ describe('Webリソース', () => {
 			{ accept: PREFER_AP },
 		])('(Acceptヘッダ: $accept)', ({ accept }) => {
 			test('はActivityPubとしてGETできる。', async () => {
-				const res = await ok({ 
-					path: path(alice.username), 
-					accept, 
+				const res = await ok({
+					path: path(alice.username),
+					accept,
 					type: AP,
 				});
 				assert.strictEqual(res.body.type, 'Person');
 			});
 
-			test('は存在しないIDのときActivityPubとしてGETできない。', async () => await notFound({ 
-				path: path('xxxxxxxxxx'), 
+			test('は存在しないIDのときActivityPubとしてGETできない。', async () => await notFound({
+				path: path('xxxxxxxxxx'),
 				accept,
 			}));
 		});
 	});
 
-	describe.each([ 
+	describe.each([
 		// 実際のハンドルはフロントエンド(index.vue)で行われる
 		{ sub: 'home' },
 		{ sub: 'notes' },
@@ -236,32 +237,32 @@ describe('Webリソース', () => {
 		const path = (username: string): string => `/@${username}/${sub}`;
 
 		test('はHTMLとしてGETできる。', async () => {
-			const res = await ok({ 
-				path: path(alice.username), 
+			const res = await ok({
+				path: path(alice.username),
 			});
 			assert.strictEqual(metaTag(res, 'misskey:user-username'), alice.username);
 			assert.strictEqual(metaTag(res, 'misskey:user-id'), alice.id);
 		});
 	});
-	
+
 	describe('/@:user/pages/:page', () => {
 		const path = (username: string, pagename: string): string => `/@${username}/pages/${pagename}`;
 
 		test('はHTMLとしてGETできる。', async () => {
-			const res = await ok({ 
-				path: path(alice.username, alicePage.name), 
+			const res = await ok({
+				path: path(alice.username, alicePage.name),
 			});
 			assert.strictEqual(metaTag(res, 'misskey:user-username'), alice.username);
 			assert.strictEqual(metaTag(res, 'misskey:user-id'), alice.id);
 			assert.strictEqual(metaTag(res, 'misskey:page-id'), alicePage.id);
-			
+
 			// TODO ogタグの検証
 			// TODO profile.noCrawleの検証
 			// TODO twitter:creatorの検証
 		});
-		
-		test('はGETできる。(存在しないIDでも。)', async () => await ok({ 
-			path: path(alice.username, 'xxxxxxxxxx'), 
+
+		test('はGETできる。(存在しないIDでも。)', async () => await ok({
+			path: path(alice.username, 'xxxxxxxxxx'),
 		}));
 	});
 
@@ -278,7 +279,7 @@ describe('Webリソース', () => {
 				assert.strictEqual(res.location, `/@${alice.username}`);
 			});
 
-			test('は存在しないユーザーはGETできない。', async () => await notFound({ 
+			test('は存在しないユーザーはGETできない。', async () => await notFound({
 				path: path('xxxxxxxx'),
 			}));
 		});
@@ -288,24 +289,24 @@ describe('Webリソース', () => {
 			{ accept: PREFER_AP },
 		])('(Acceptヘッダ: $accept)', ({ accept }) => {
 			test('はActivityPubとしてGETできる。', async () => {
-				const res = await ok({ 
-					path: path(alice.id), 
-					accept, 
+				const res = await ok({
+					path: path(alice.id),
+					accept,
 					type: AP,
 				});
 				assert.strictEqual(res.body.type, 'Person');
 			});
 
-			test('は存在しないIDのときActivityPubとしてGETできない。', async () => await notOk({ 
+			test('は存在しないIDのときActivityPubとしてGETできない。', async () => await notOk({
 				path: path('xxxxxxxx'),
 				accept,
 				status: 404,
 			}));
 		});
 	});
-	
+
 	describe('/users/inbox', () => {
-		test('がGETできる。(POST専用だけど4xx/5xxにならずHTMLが返ってくる)', async () => await ok({ 
+		test('がGETできる。(POST専用だけど4xx/5xxにならずHTMLが返ってくる)', async () => await ok({
 			path: '/inbox',
 		}));
 
@@ -315,7 +316,7 @@ describe('Webリソース', () => {
 	describe('/users/:id/inbox', () => {
 		const path = (id: string): string => `/users/${id}/inbox`;
 
-		test('がGETできる。(POST専用だけど4xx/5xxにならずHTMLが返ってくる)', async () => await ok({ 
+		test('がGETできる。(POST専用だけど4xx/5xxにならずHTMLが返ってくる)', async () => await ok({
 			path: path(alice.id),
 		}));
 
@@ -326,14 +327,14 @@ describe('Webリソース', () => {
 		const path = (id: string): string => `/users/${id}/outbox`;
 
 		test('がGETできる。', async () => {
-			const res = await ok({ 
-				path: path(alice.id), 
+			const res = await ok({
+				path: path(alice.id),
 				type: AP,
 			});
 			assert.strictEqual(res.body.type, 'OrderedCollection');
 		});
 	});
-	
+
 	describe('/notes/:id', () => {
 		const path = (noteId: string): string => `/notes/${noteId}`;
 
@@ -342,22 +343,22 @@ describe('Webリソース', () => {
 			{ accept: UNSPECIFIED },
 		])('(Acceptヘッダ: $accept)', ({ accept }) => {
 			test('はHTMLとしてGETできる。', async () => {
-				const res = await ok({ 
-					path: path(alicesPost.id), 
-					accept, 
+				const res = await ok({
+					path: path(alicesPost.id),
+					accept,
 					type: HTML,
 				});
 				assert.strictEqual(metaTag(res, 'misskey:user-username'), alice.username);
 				assert.strictEqual(metaTag(res, 'misskey:user-id'), alice.id);
-				assert.strictEqual(metaTag(res, 'misskey:note-id'), alicesPost.id);	
-				
+				assert.strictEqual(metaTag(res, 'misskey:note-id'), alicesPost.id);
+
 				// TODO ogタグの検証
 				// TODO profile.noCrawleの検証
 				// TODO twitter:creatorの検証
 			});
 
-			test('はHTMLとしてGETできる。(存在しないIDでも。)', async () => await ok({ 
-				path: path('xxxxxxxxxx'), 
+			test('はHTMLとしてGETできる。(存在しないIDでも。)', async () => await ok({
+				path: path('xxxxxxxxxx'),
 			}));
 		});
 
@@ -366,48 +367,48 @@ describe('Webリソース', () => {
 			{ accept: PREFER_AP },
 		])('(Acceptヘッダ: $accept)', ({ accept }) => {
 			test('はActivityPubとしてGETできる。', async () => {
-				const res = await ok({ 
-					path: path(alicesPost.id), 
+				const res = await ok({
+					path: path(alicesPost.id),
 					accept,
 					type: AP,
 				});
 				assert.strictEqual(res.body.type, 'Note');
 			});
 
-			test('は存在しないIDのときActivityPubとしてGETできない。', async () => await notFound({ 
-				path: path('xxxxxxxxxx'), 
+			test('は存在しないIDのときActivityPubとしてGETできない。', async () => await notFound({
+				path: path('xxxxxxxxxx'),
 				accept,
 			}));
 		});
 	});
-	
+
 	describe('/play/:id', () => {
 		const path = (playid: string): string => `/play/${playid}`;
 
 		test('がGETできる。', async () => {
-			const res = await ok({ 
-				path: path(alicePlay.id), 
+			const res = await ok({
+				path: path(alicePlay.id),
 			});
 			assert.strictEqual(metaTag(res, 'misskey:user-username'), alice.username);
 			assert.strictEqual(metaTag(res, 'misskey:user-id'), alice.id);
 			assert.strictEqual(metaTag(res, 'misskey:flash-id'), alicePlay.id);
-			
+
 			// TODO ogタグの検証
 			// TODO profile.noCrawleの検証
 			// TODO twitter:creatorの検証
 		});
 
-		test('がGETできる。(存在しないIDでも。)', async () => await ok({ 
-			path: path('xxxxxxxxxx'), 
+		test('がGETできる。(存在しないIDでも。)', async () => await ok({
+			path: path('xxxxxxxxxx'),
 		}));
 	});
-	
+
 	describe('/clips/:clip', () => {
 		const path = (clip: string): string => `/clips/${clip}`;
 
 		test('がGETできる。', async () => {
-			const res = await ok({ 
-				path: path(aliceClip.id), 
+			const res = await ok({
+				path: path(aliceClip.id),
 			});
 			assert.strictEqual(metaTag(res, 'misskey:user-username'), alice.username);
 			assert.strictEqual(metaTag(res, 'misskey:user-id'), alice.id);
@@ -416,9 +417,9 @@ describe('Webリソース', () => {
 			// TODO ogタグの検証
 			// TODO profile.noCrawleの検証
 		});
-		
-		test('がGETできる。(存在しないIDでも。)', async () => await ok({ 
-			path: path('xxxxxxxxxx'), 
+
+		test('がGETできる。(存在しないIDでも。)', async () => await ok({
+			path: path('xxxxxxxxxx'),
 		}));
 	});
 
@@ -426,8 +427,8 @@ describe('Webリソース', () => {
 		const path = (post: string): string => `/gallery/${post}`;
 
 		test('がGETできる。', async () => {
-			const res = await ok({ 
-				path: path(aliceGalleryPost.id), 
+			const res = await ok({
+				path: path(aliceGalleryPost.id),
 			});
 			assert.strictEqual(metaTag(res, 'misskey:user-username'), alice.username);
 			assert.strictEqual(metaTag(res, 'misskey:user-id'), alice.id);
@@ -436,26 +437,26 @@ describe('Webリソース', () => {
 			// TODO profile.noCrawleの検証
 			// TODO twitter:creatorの検証
 		});
-		
-		test('がGETできる。(存在しないIDでも。)', async () => await ok({ 
-			path: path('xxxxxxxxxx'), 
+
+		test('がGETできる。(存在しないIDでも。)', async () => await ok({
+			path: path('xxxxxxxxxx'),
 		}));
 	});
-	
+
 	describe('/channels/:channel', () => {
 		const path = (channel: string): string => `/channels/${channel}`;
 
 		test('はGETできる。', async () => {
 			const res = await ok({
-				path: path(aliceChannel.id), 
+				path: path(aliceChannel.id),
 			});
 
 			// FIXME: misskey関連のmetaタグの設定がない
 			// TODO ogタグの検証
 		});
-		
-		test('がGETできる。(存在しないIDでも。)', async () => await ok({ 
-			path: path('xxxxxxxxxx'), 
+
+		test('がGETできる。(存在しないIDでも。)', async () => await ok({
+			path: path('xxxxxxxxxx'),
 		}));
 	});
 });
diff --git a/packages/backend/test/e2e/ff-visibility.ts b/packages/backend/test/e2e/ff-visibility.ts
index 7b75005a39..9082c77f07 100644
--- a/packages/backend/test/e2e/ff-visibility.ts
+++ b/packages/backend/test/e2e/ff-visibility.ts
@@ -3,12 +3,13 @@ process.env.NODE_ENV = 'test';
 import * as assert from 'assert';
 import { signup, api, startServer, simpleGet } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('FF visibility', () => {
 	let app: INestApplicationContext;
 
-	let alice: any;
-	let bob: any;
+	let alice: misskey.entities.MeSignup;
+	let bob: misskey.entities.MeSignup;
 
 	beforeAll(async () => {
 		app = await startServer();
diff --git a/packages/backend/test/e2e/move.ts b/packages/backend/test/e2e/move.ts
index 7d6c646090..cd9459fa52 100644
--- a/packages/backend/test/e2e/move.ts
+++ b/packages/backend/test/e2e/move.ts
@@ -7,6 +7,7 @@ import { User, UsersRepository } from '@/models/index.js';
 import { jobQueue } from '@/boot/common.js';
 import { uploadFile, signup, startServer, initTestDb, api, sleep, successfulApiCall } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('Account Move', () => {
 	let app: INestApplicationContext;
@@ -14,12 +15,12 @@ describe('Account Move', () => {
 	let url: URL;
 
 	let root: any;
-	let alice: any;
-	let bob: any;
-	let carol: any;
-	let dave: any;
-	let eve: any;
-	let frank: any;
+	let alice: misskey.entities.MeSignup;
+	let bob: misskey.entities.MeSignup;
+	let carol: misskey.entities.MeSignup;
+	let dave: misskey.entities.MeSignup;
+	let eve: misskey.entities.MeSignup;
+	let frank: misskey.entities.MeSignup;
 
 	let Users: UsersRepository;
 
diff --git a/packages/backend/test/e2e/mute.ts b/packages/backend/test/e2e/mute.ts
index 25bd532cfb..79e2c90f64 100644
--- a/packages/backend/test/e2e/mute.ts
+++ b/packages/backend/test/e2e/mute.ts
@@ -3,14 +3,15 @@ process.env.NODE_ENV = 'test';
 import * as assert from 'assert';
 import { signup, api, post, react, startServer, waitFire } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('Mute', () => {
 	let app: INestApplicationContext;
 
 	// alice mutes carol
-	let alice: any;
-	let bob: any;
-	let carol: any;
+	let alice: misskey.entities.MeSignup;
+	let bob: misskey.entities.MeSignup;
+	let carol: misskey.entities.MeSignup;
 
 	beforeAll(async () => {
 		app = await startServer();
diff --git a/packages/backend/test/e2e/note.ts b/packages/backend/test/e2e/note.ts
index d2eb8f01d7..33da811a26 100644
--- a/packages/backend/test/e2e/note.ts
+++ b/packages/backend/test/e2e/note.ts
@@ -4,13 +4,14 @@ import * as assert from 'assert';
 import { Note } from '@/models/entities/Note.js';
 import { signup, post, uploadUrl, startServer, initTestDb, api, uploadFile } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('Note', () => {
 	let app: INestApplicationContext;
 	let Notes: any;
 
-	let alice: any;
-	let bob: any;
+	let alice: misskey.entities.MeSignup;
+	let bob: misskey.entities.MeSignup;
 
 	beforeAll(async () => {
 		app = await startServer();
@@ -378,7 +379,7 @@ describe('Note', () => {
 					},
 				},
 			}, alice);
-			
+
 			assert.strictEqual(res.status, 200);
 
 			const assign = await api('admin/roles/assign', {
diff --git a/packages/backend/test/e2e/renote-mute.ts b/packages/backend/test/e2e/renote-mute.ts
index 0f73b8d09f..72fc599aaf 100644
--- a/packages/backend/test/e2e/renote-mute.ts
+++ b/packages/backend/test/e2e/renote-mute.ts
@@ -3,14 +3,15 @@ process.env.NODE_ENV = 'test';
 import * as assert from 'assert';
 import { signup, api, post, react, startServer, waitFire } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('Renote Mute', () => {
 	let app: INestApplicationContext;
 
 	// alice mutes carol
-	let alice: any;
-	let bob: any;
-	let carol: any;
+	let alice: misskey.entities.MeSignup;
+	let bob: misskey.entities.MeSignup;
+	let carol: misskey.entities.MeSignup;
 
 	beforeAll(async () => {
 		app = await startServer();
diff --git a/packages/backend/test/e2e/streaming.ts b/packages/backend/test/e2e/streaming.ts
index d1394ef7a8..2cddafed2e 100644
--- a/packages/backend/test/e2e/streaming.ts
+++ b/packages/backend/test/e2e/streaming.ts
@@ -4,6 +4,7 @@ import * as assert from 'assert';
 import { Following } from '@/models/entities/Following.js';
 import { connectStream, signup, api, post, startServer, initTestDb, waitFire } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('Streaming', () => {
 	let app: INestApplicationContext;
@@ -26,13 +27,13 @@ describe('Streaming', () => {
 
 	describe('Streaming', () => {
 		// Local users
-		let ayano: any;
-		let kyoko: any;
-		let chitose: any;
+		let ayano: misskey.entities.MeSignup;
+		let kyoko: misskey.entities.MeSignup;
+		let chitose: misskey.entities.MeSignup;
 
 		// Remote users
-		let akari: any;
-		let chinatsu: any;
+		let akari: misskey.entities.MeSignup;
+		let chinatsu: misskey.entities.MeSignup;
 
 		let kyokoNote: any;
 		let list: any;
diff --git a/packages/backend/test/e2e/thread-mute.ts b/packages/backend/test/e2e/thread-mute.ts
index 2ae2eb67c1..e01ea90fe0 100644
--- a/packages/backend/test/e2e/thread-mute.ts
+++ b/packages/backend/test/e2e/thread-mute.ts
@@ -3,13 +3,14 @@ process.env.NODE_ENV = 'test';
 import * as assert from 'assert';
 import { signup, api, post, connectStream, startServer } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('Note thread mute', () => {
 	let app: INestApplicationContext;
 
-	let alice: any;
-	let bob: any;
-	let carol: any;
+	let alice: misskey.entities.MeSignup;
+	let bob: misskey.entities.MeSignup;
+	let carol: misskey.entities.MeSignup;
 
 	beforeAll(async () => {
 		app = await startServer();
diff --git a/packages/backend/test/e2e/user-notes.ts b/packages/backend/test/e2e/user-notes.ts
index c11099e7b5..3681456c7e 100644
--- a/packages/backend/test/e2e/user-notes.ts
+++ b/packages/backend/test/e2e/user-notes.ts
@@ -3,11 +3,12 @@ process.env.NODE_ENV = 'test';
 import * as assert from 'assert';
 import { signup, api, post, uploadUrl, startServer } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
+import type * as misskey from 'misskey-js';
 
 describe('users/notes', () => {
 	let app: INestApplicationContext;
 
-	let alice: any;
+	let alice: misskey.entities.MeSignup;
 	let jpgNote: any;
 	let pngNote: any;
 	let jpgPngNote: any;
diff --git a/packages/backend/test/e2e/users.ts b/packages/backend/test/e2e/users.ts
index 02684c93b8..64efaa57cc 100644
--- a/packages/backend/test/e2e/users.ts
+++ b/packages/backend/test/e2e/users.ts
@@ -4,14 +4,14 @@ import * as assert from 'assert';
 import { inspect } from 'node:util';
 import { DEFAULT_POLICIES } from '@/core/RoleService.js';
 import type { Packed } from '@/misc/json-schema.js';
-import { 
-	signup, 
-	post, 
+import {
+	signup,
+	post,
 	page,
 	role,
-	startServer, 
+	startServer,
 	api,
-	successfulApiCall, 
+	successfulApiCall,
 	failedApiCall,
 	uploadFile,
 } from '../utils.js';
@@ -36,19 +36,19 @@ describe('ユーザー', () => {
 		badgeRoles: any[],
 	};
 
-	type UserDetailedNotMe = UserLite & 
+	type UserDetailedNotMe = UserLite &
 	misskey.entities.UserDetailed & {
 		roles: any[],
 	};
 
-	type MeDetailed = UserDetailedNotMe & 
+	type MeDetailed = UserDetailedNotMe &
 		misskey.entities.MeDetailed & {
 		achievements: object[],
 		loggedInDays: number,
 		policies: object,
 	};
-	
-	type User = MeDetailed & { token: string };	
+
+	type User = MeDetailed & { token: string };
 
 	const show = async (id: string, me = root): Promise<MeDetailed | UserDetailedNotMe> => {
 		return successfulApiCall({ endpoint: 'users/show', parameters: { userId: id }, user: me }) as any;
@@ -159,7 +159,7 @@ describe('ユーザー', () => {
 			mutedInstances: user.mutedInstances,
 			mutingNotificationTypes: user.mutingNotificationTypes,
 			emailNotificationTypes: user.emailNotificationTypes,
-			achievements: user.achievements, 
+			achievements: user.achievements,
 			loggedInDays: user.loggedInDays,
 			policies: user.policies,
 			...(security ? {
@@ -222,11 +222,11 @@ describe('ユーザー', () => {
 	beforeAll(async () => {
 		root = await signup({ username: 'root' });
 		alice = await signup({ username: 'alice' });
-		aliceNote = await post(alice, { text: 'test' }) as any; 
+		aliceNote = await post(alice, { text: 'test' }) as any;
 		alicePage = await page(alice);
 		aliceList = (await api('users/list/create', { name: 'aliceList' }, alice)).body;
 		bob = await signup({ username: 'bob' });
-		bobNote = await post(bob, { text: 'test' }) as any; 
+		bobNote = await post(bob, { text: 'test' }) as any;
 		carol = await signup({ username: 'carol' });
 		dave = await signup({ username: 'dave' });
 		ellen = await signup({ username: 'ellen' });
@@ -236,10 +236,10 @@ describe('ユーザー', () => {
 		usersReplying = await [...Array(10)].map((_, i) => i).reduce(async (acc, i) => {
 			const u = await signup({ username: `replying${i}` });
 			for (let j = 0; j < 10 - i; j++) {
-				const p = await post(u, { text: `test${j}` }); 
+				const p = await post(u, { text: `test${j}` });
 				await post(alice, { text: `@${u.username} test${j}`, replyId: p.id });
 			}
-			
+
 			return (await acc).concat(u);
 		}, Promise.resolve([] as User[]));
 
@@ -376,7 +376,7 @@ describe('ユーザー', () => {
 		assert.strictEqual(response.securityKeys, false);
 		assert.deepStrictEqual(response.roles, []);
 		assert.strictEqual(response.memo, null);
-		
+
 		// MeDetailedOnly
 		assert.strictEqual(response.avatarId, null);
 		assert.strictEqual(response.bannerId, null);
@@ -406,7 +406,7 @@ describe('ユーザー', () => {
 		assert.deepStrictEqual(response.emailNotificationTypes, ['follow', 'receiveFollowRequest']);
 		assert.deepStrictEqual(response.achievements, []);
 		assert.deepStrictEqual(response.loggedInDays, 0);
-		assert.deepStrictEqual(response.policies, DEFAULT_POLICIES); 
+		assert.deepStrictEqual(response.policies, DEFAULT_POLICIES);
 		assert.notStrictEqual(response.email, undefined);
 		assert.strictEqual(response.emailVerified, false);
 		assert.deepStrictEqual(response.securityKeysList, []);
@@ -499,8 +499,8 @@ describe('ユーザー', () => {
 		const response = await successfulApiCall({ endpoint: 'i/update', parameters: parameters, user: alice });
 		assert.match(response.avatarUrl ?? '.', /^[-a-zA-Z0-9@:%._\+~#&?=\/]+$/);
 		assert.match(response.avatarBlurhash ?? '.', /[ -~]{54}/);
-		const expected = { 
-			...meDetailed(alice, true), 
+		const expected = {
+			...meDetailed(alice, true),
 			avatarId: aliceFile.id,
 			avatarBlurhash: response.avatarBlurhash,
 			avatarUrl: response.avatarUrl,
@@ -509,8 +509,8 @@ describe('ユーザー', () => {
 
 		const parameters2 = { avatarId: null };
 		const response2 = await successfulApiCall({ endpoint: 'i/update', parameters: parameters2, user: alice });
-		const expected2 = { 
-			...meDetailed(alice, true), 
+		const expected2 = {
+			...meDetailed(alice, true),
 			avatarId: null,
 			avatarBlurhash: null,
 			avatarUrl: alice.avatarUrl, // 解除した場合、identiconになる
@@ -524,8 +524,8 @@ describe('ユーザー', () => {
 		const response = await successfulApiCall({ endpoint: 'i/update', parameters: parameters, user: alice });
 		assert.match(response.bannerUrl ?? '.', /^[-a-zA-Z0-9@:%._\+~#&?=\/]+$/);
 		assert.match(response.bannerBlurhash ?? '.', /[ -~]{54}/);
-		const expected = { 
-			...meDetailed(alice, true), 
+		const expected = {
+			...meDetailed(alice, true),
 			bannerId: aliceFile.id,
 			bannerBlurhash: response.bannerBlurhash,
 			bannerUrl: response.bannerUrl,
@@ -534,8 +534,8 @@ describe('ユーザー', () => {
 
 		const parameters2 = { bannerId: null };
 		const response2 = await successfulApiCall({ endpoint: 'i/update', parameters: parameters2, user: alice });
-		const expected2 = { 
-			...meDetailed(alice, true), 
+		const expected2 = {
+			...meDetailed(alice, true),
 			bannerId: null,
 			bannerBlurhash: null,
 			bannerUrl: null,
@@ -551,7 +551,7 @@ describe('ユーザー', () => {
 		const response = await successfulApiCall({ endpoint: 'i/pin', parameters, user: alice });
 		const expected = { ...meDetailed(alice, false), pinnedNoteIds: [aliceNote.id], pinnedNotes: [aliceNote] };
 		assert.deepStrictEqual(response, expected);
-		
+
 		const response2 = await successfulApiCall({ endpoint: 'i/unpin', parameters, user: alice });
 		const expected2 = meDetailed(alice, false);
 		assert.deepStrictEqual(response2, expected2);
@@ -612,7 +612,7 @@ describe('ユーザー', () => {
 	});
 	test.todo('をリスト形式で取得することができる(リモート, hostname指定)');
 	test.todo('をリスト形式で取得することができる(pagenation)');
-	
+
 	//#endregion
 	//#region ユーザー情報(users/show)
 
@@ -684,9 +684,9 @@ describe('ユーザー', () => {
 		const parameters = { userIds: [bob.id, alice.id, carol.id] };
 		const response = await successfulApiCall({ endpoint: 'users/show', parameters, user: alice });
 		const expected = [
-			await successfulApiCall({ endpoint: 'users/show', parameters: { userId: bob.id }, user: alice }), 
-			await successfulApiCall({ endpoint: 'users/show', parameters: { userId: alice.id }, user: alice }), 
-			await successfulApiCall({ endpoint: 'users/show', parameters: { userId: carol.id }, user: alice }), 
+			await successfulApiCall({ endpoint: 'users/show', parameters: { userId: bob.id }, user: alice }),
+			await successfulApiCall({ endpoint: 'users/show', parameters: { userId: alice.id }, user: alice }),
+			await successfulApiCall({ endpoint: 'users/show', parameters: { userId: carol.id }, user: alice }),
 		];
 		assert.deepStrictEqual(response, expected);
 	});
@@ -701,7 +701,7 @@ describe('ユーザー', () => {
 		// BUG サスペンドユーザーを一般ユーザーから見るとrootユーザーが返ってくる
 		//{ label: 'サスペンドユーザーが(一般ユーザーが見るときは)含まれない', user: (): User => userSuspended, me: (): User => bob, excluded: true },
 		{ label: '削除済ユーザーが含まれる', user: (): User => userDeletedBySelf },
-		{ label: '削除済(byAdmin)ユーザーが含まれる', user: (): User => userDeletedByAdmin },	
+		{ label: '削除済(byAdmin)ユーザーが含まれる', user: (): User => userDeletedByAdmin },
 	] as const)('をID指定のリスト形式で取得することができ、結果に$label', async ({ user, me, excluded }) => {
 		const parameters = { userIds: [user().id] };
 		const response = await successfulApiCall({ endpoint: 'users/show', parameters, user: me?.() ?? alice });
@@ -734,7 +734,7 @@ describe('ユーザー', () => {
 		{ label: 'サイレンスユーザーが含まれる', user: (): User => userSilenced },
 		{ label: 'サスペンドユーザーが含まれない', user: (): User => userSuspended, excluded: true },
 		{ label: '削除済ユーザーが含まれる', user: (): User => userDeletedBySelf },
-		{ label: '削除済(byAdmin)ユーザーが含まれる', user: (): User => userDeletedByAdmin },	
+		{ label: '削除済(byAdmin)ユーザーが含まれる', user: (): User => userDeletedByAdmin },
 	] as const)('を検索することができ、結果に$labelが含まれる', async ({ user, excluded }) => {
 		const parameters = { query: user().username, limit: 1 };
 		const response = await successfulApiCall({ endpoint: 'users/search', parameters, user: alice });
@@ -747,7 +747,7 @@ describe('ユーザー', () => {
 	//#endregion
 	//#region ID指定検索(users/search-by-username-and-host)
 
-	test.each([ 
+	test.each([
 		{ label: '自分', parameters: { username: 'alice' }, user: (): User[] => [alice] },
 		{ label: '自分かつusernameが大文字', parameters: { username: 'ALICE' }, user: (): User[] => [alice] },
 		{ label: 'ローカルのフォロイーでノートなし', parameters: { username: 'userFollowedByAlice' }, user: (): User[] => [userFollowedByAlice] },
@@ -786,7 +786,7 @@ describe('ユーザー', () => {
 	test('がよくリプライをするユーザーのリストを取得できる', async () => {
 		const parameters = { userId: alice.id, limit: 5 };
 		const response = await successfulApiCall({ endpoint: 'users/get-frequently-replied-users', parameters, user: alice });
-		const expected = await Promise.all(usersReplying.slice(0, parameters.limit).map(async (s, i) => ({ 
+		const expected = await Promise.all(usersReplying.slice(0, parameters.limit).map(async (s, i) => ({
 			user: await show(s.id, alice),
 			weight: (usersReplying.length - i) / usersReplying.length,
 		})));
diff --git a/packages/backend/test/utils.ts b/packages/backend/test/utils.ts
index 22f7d81e4e..eeb1b19daa 100644
--- a/packages/backend/test/utils.ts
+++ b/packages/backend/test/utils.ts
@@ -83,7 +83,7 @@ const relativeFetch = async (path: string, init?: RequestInit | undefined) => {
 	return await fetch(new URL(path, `http://127.0.0.1:${port}/`).toString(), init);
 };
 
-export const signup = async (params?: any): Promise<any> => {
+export const signup = async (params?: Partial<misskey.Endpoints['signup']['req']>): Promise<NonNullable<misskey.Endpoints['signup']['res']>> => {
 	const q = Object.assign({
 		username: 'test',
 		password: 'test',
@@ -213,8 +213,8 @@ export const role = async (user: any, role: any = {}, policies: any = {}): Promi
 		isPublic: false,
 		name: 'New Role',
 		target: 'manual',
-		policies: { 
-			...Object.entries(DEFAULT_POLICIES).map(([k, v]) => [k, { 
+		policies: {
+			...Object.entries(DEFAULT_POLICIES).map(([k, v]) => [k, {
 				priority: 0,
 				useDefault: true,
 				value: v,
@@ -351,11 +351,11 @@ export const waitFire = async (user: any, channel: string, trgr: () => any, cond
 	});
 };
 
-export type SimpleGetResponse = { 
-	status: number, 
-	body: any | JSDOM | null, 
-	type: string | null, 
-	location: string | null 
+export type SimpleGetResponse = {
+	status: number,
+	body: any | JSDOM | null,
+	type: string | null,
+	location: string | null
 };
 export const simpleGet = async (path: string, accept = '*/*', cookie: any = undefined): Promise<SimpleGetResponse> => {
 	const res = await relativeFetch(path, {
@@ -374,9 +374,9 @@ export const simpleGet = async (path: string, accept = '*/*', cookie: any = unde
 		'text/html; charset=utf-8',
 	];
 
-	const body = 
-		jsonTypes.includes(res.headers.get('content-type') ?? '')	? await res.json() : 
-		htmlTypes.includes(res.headers.get('content-type') ?? '')	? new JSDOM(await res.text()) : 
+	const body =
+		jsonTypes.includes(res.headers.get('content-type') ?? '')	? await res.json() :
+		htmlTypes.includes(res.headers.get('content-type') ?? '')	? new JSDOM(await res.text()) :
 		null;
 
 	return {
diff --git a/packages/misskey-js/etc/misskey-js.api.md b/packages/misskey-js/etc/misskey-js.api.md
index ca8eee01a1..5f292148ae 100644
--- a/packages/misskey-js/etc/misskey-js.api.md
+++ b/packages/misskey-js/etc/misskey-js.api.md
@@ -1942,6 +1942,19 @@ export type Endpoints = {
         req: TODO;
         res: TODO;
     };
+    'signup': {
+        req: {
+            username: string;
+            password: string;
+            host?: string;
+            invitationCode?: string;
+            emailAddress?: string;
+            'hcaptcha-response'?: string;
+            'g-recaptcha-response'?: string;
+            'turnstile-response'?: string;
+        };
+        res: MeSignup | null;
+    };
     'stats': {
         req: NoParams;
         res: Stats;
@@ -2159,6 +2172,8 @@ declare namespace entities {
         UserGroup,
         UserList,
         MeDetailed,
+        MeDetailedWithSecret,
+        MeSignup,
         DriveFile,
         DriveFolder,
         GalleryPost,
@@ -2374,6 +2389,22 @@ type MeDetailed = UserDetailed & {
     [other: string]: any;
 };
 
+// @public (undocumented)
+type MeDetailedWithSecret = MeDetailed & {
+    email: string;
+    emailVerified: boolean;
+    securityKeysList: {
+        id: string;
+        name: string;
+        lastUsed: string;
+    }[];
+};
+
+// @public (undocumented)
+type MeSignup = MeDetailedWithSecret & {
+    token: string;
+};
+
 // @public (undocumented)
 type MessagingMessage = {
     id: ID;
@@ -2719,7 +2750,7 @@ type UserSorting = '+follower' | '-follower' | '+createdAt' | '-createdAt' | '+u
 //
 // src/api.types.ts:16:32 - (ae-forgotten-export) The symbol "TODO" needs to be exported by the entry point index.d.ts
 // src/api.types.ts:18:25 - (ae-forgotten-export) The symbol "NoParams" needs to be exported by the entry point index.d.ts
-// src/api.types.ts:596:18 - (ae-forgotten-export) The symbol "ShowUserReq" needs to be exported by the entry point index.d.ts
+// src/api.types.ts:611:18 - (ae-forgotten-export) The symbol "ShowUserReq" needs to be exported by the entry point index.d.ts
 // src/streaming.types.ts:33:4 - (ae-forgotten-export) The symbol "FIXME" needs to be exported by the entry point index.d.ts
 
 // (No @packageDocumentation comment for this package)
diff --git a/packages/misskey-js/src/api.types.ts b/packages/misskey-js/src/api.types.ts
index b8c59e7b15..293e0043b7 100644
--- a/packages/misskey-js/src/api.types.ts
+++ b/packages/misskey-js/src/api.types.ts
@@ -2,7 +2,7 @@ import type {
 	Ad, Announcement, Antenna, App, AuthSession, Blocking, Channel, Clip, DateString, DetailedInstanceMetadata, DriveFile, DriveFolder, Following, FollowingFolloweePopulated, FollowingFollowerPopulated, FollowRequest, GalleryPost, Instance,
 	LiteInstanceMetadata,
 	MeDetailed,
-	Note, NoteFavorite, OriginType, Page, ServerInfo, Stats, User, UserDetailed, UserGroup, UserList, UserSorting, Notification, NoteReaction, Signin, MessagingMessage,
+	Note, NoteFavorite, OriginType, Page, ServerInfo, Stats, User, UserDetailed, MeSignup, UserGroup, UserList, UserSorting, Notification, NoteReaction, Signin, MessagingMessage,
 } from './entities.js';
 
 type TODO = Record<string, any> | null;
@@ -549,6 +549,21 @@ export type Endpoints = {
 	'room/show': { req: TODO; res: TODO; };
 	'room/update': { req: TODO; res: TODO; };
 
+	// signup
+	'signup': {
+		req: {
+			username: string;
+			password: string;
+			host?: string;
+			invitationCode?: string;
+			emailAddress?: string;
+			'hcaptcha-response'?: string;
+			'g-recaptcha-response'?: string;
+			'turnstile-response'?: string;
+		};
+		res: MeSignup | null;
+	};
+
 	// stats
 	'stats': { req: NoParams; res: Stats; };
 
diff --git a/packages/misskey-js/src/entities.ts b/packages/misskey-js/src/entities.ts
index 383b17f0b9..e1305452eb 100644
--- a/packages/misskey-js/src/entities.ts
+++ b/packages/misskey-js/src/entities.ts
@@ -107,6 +107,20 @@ export type MeDetailed = UserDetailed & {
 	[other: string]: any;
 };
 
+export type MeDetailedWithSecret = MeDetailed & {
+	email: string;
+	emailVerified: boolean;
+	securityKeysList: {
+		id: string;
+		name: string;
+		lastUsed: string;
+	}[];
+};
+
+export type MeSignup = MeDetailedWithSecret & {
+	token: string;
+};
+
 export type DriveFile = {
 	id: ID;
 	createdAt: DateString;

From ef354e94f20ace67b94faa2859c458a436cdd3f7 Mon Sep 17 00:00:00 2001
From: Kagami Sascha Rosylight <saschanaz@outlook.com>
Date: Sun, 25 Jun 2023 04:04:33 +0200
Subject: [PATCH 12/17] refactor(backend): replace rndstr with secureRndstr
 (#11044)

* refactor(backend): replace rndstr with secureRndstr

* Update pnpm-lock.yaml

* .js
---
 packages/backend/package.json                 |  1 -
 .../src/misc/generate-native-user-token.ts    |  2 +-
 packages/backend/src/misc/secure-rndstr.ts    |  5 ++--
 .../src/server/api/SignupApiService.ts        | 28 ++++++++---------
 .../server/api/endpoints/admin/emoji/add.ts   |  1 -
 .../api/endpoints/admin/reset-password.ts     |  4 +--
 .../src/server/api/endpoints/app/create.ts    |  2 +-
 .../src/server/api/endpoints/auth/accept.ts   |  2 +-
 .../server/api/endpoints/i/update-email.ts    |  4 +--
 .../src/server/api/endpoints/invite.ts        |  7 ++---
 .../server/api/endpoints/miauth/gen-token.ts  |  2 +-
 .../api/endpoints/request-reset-password.ts   |  6 ++--
 packages/backend/test/e2e/move.ts             | 14 ++++-----
 packages/backend/test/unit/RoleService.ts     | 30 +++++++++----------
 packages/backend/test/unit/activitypub.ts     | 10 +++----
 pnpm-lock.yaml                                |  3 --
 16 files changed, 57 insertions(+), 64 deletions(-)

diff --git a/packages/backend/package.json b/packages/backend/package.json
index b9995d8117..c13f292c76 100644
--- a/packages/backend/package.json
+++ b/packages/backend/package.json
@@ -133,7 +133,6 @@
 		"redis-lock": "0.1.4",
 		"reflect-metadata": "0.1.13",
 		"rename": "1.0.4",
-		"rndstr": "1.0.0",
 		"rss-parser": "3.13.0",
 		"rxjs": "7.8.1",
 		"s-age": "1.1.2",
diff --git a/packages/backend/src/misc/generate-native-user-token.ts b/packages/backend/src/misc/generate-native-user-token.ts
index 5d8a4c5378..7292d765a8 100644
--- a/packages/backend/src/misc/generate-native-user-token.ts
+++ b/packages/backend/src/misc/generate-native-user-token.ts
@@ -1,3 +1,3 @@
 import { secureRndstr } from '@/misc/secure-rndstr.js';
 
-export default () => secureRndstr(16, true);
+export default () => secureRndstr(16);
diff --git a/packages/backend/src/misc/secure-rndstr.ts b/packages/backend/src/misc/secure-rndstr.ts
index 8d4fcb1ba9..cde64c8142 100644
--- a/packages/backend/src/misc/secure-rndstr.ts
+++ b/packages/backend/src/misc/secure-rndstr.ts
@@ -1,10 +1,9 @@
 import * as crypto from 'node:crypto';
 
-const L_CHARS = '0123456789abcdefghijklmnopqrstuvwxyz';
+export const L_CHARS = '0123456789abcdefghijklmnopqrstuvwxyz';
 const LU_CHARS = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
 
-export function secureRndstr(length = 32, useLU = true): string {
-	const chars = useLU ? LU_CHARS : L_CHARS;
+export function secureRndstr(length = 32, { chars = LU_CHARS } = {}): string {
 	const chars_len = chars.length;
 
 	let str = '';
diff --git a/packages/backend/src/server/api/SignupApiService.ts b/packages/backend/src/server/api/SignupApiService.ts
index b2bd7d82e7..fc5f3811eb 100644
--- a/packages/backend/src/server/api/SignupApiService.ts
+++ b/packages/backend/src/server/api/SignupApiService.ts
@@ -1,5 +1,4 @@
 import { Inject, Injectable } from '@nestjs/common';
-import rndstr from 'rndstr';
 import bcrypt from 'bcryptjs';
 import { IsNull } from 'typeorm';
 import { DI } from '@/di-symbols.js';
@@ -16,6 +15,7 @@ import { FastifyReplyError } from '@/misc/fastify-reply-error.js';
 import { bindThis } from '@/decorators.js';
 import { SigninService } from './SigninService.js';
 import type { FastifyRequest, FastifyReply } from 'fastify';
+import { L_CHARS, secureRndstr } from '@/misc/secure-rndstr.js';
 
 @Injectable()
 export class SignupApiService {
@@ -67,7 +67,7 @@ export class SignupApiService {
 		const body = request.body;
 
 		const instance = await this.metaService.fetch(true);
-	
+
 		// Verify *Captcha
 		// ただしテスト時はこの機構は障害となるため無効にする
 		if (process.env.NODE_ENV !== 'test') {
@@ -76,7 +76,7 @@ export class SignupApiService {
 					throw new FastifyReplyError(400, err);
 				});
 			}
-	
+
 			if (instance.enableRecaptcha && instance.recaptchaSecretKey) {
 				await this.captchaService.verifyRecaptcha(instance.recaptchaSecretKey, body['g-recaptcha-response']).catch(err => {
 					throw new FastifyReplyError(400, err);
@@ -89,44 +89,44 @@ export class SignupApiService {
 				});
 			}
 		}
-	
+
 		const username = body['username'];
 		const password = body['password'];
 		const host: string | null = process.env.NODE_ENV === 'test' ? (body['host'] ?? null) : null;
 		const invitationCode = body['invitationCode'];
 		const emailAddress = body['emailAddress'];
-	
+
 		if (instance.emailRequiredForSignup) {
 			if (emailAddress == null || typeof emailAddress !== 'string') {
 				reply.code(400);
 				return;
 			}
-	
+
 			const res = await this.emailService.validateEmailForAccount(emailAddress);
 			if (!res.available) {
 				reply.code(400);
 				return;
 			}
 		}
-	
+
 		if (instance.disableRegistration) {
 			if (invitationCode == null || typeof invitationCode !== 'string') {
 				reply.code(400);
 				return;
 			}
-	
+
 			const ticket = await this.registrationTicketsRepository.findOneBy({
 				code: invitationCode,
 			});
-	
+
 			if (ticket == null) {
 				reply.code(400);
 				return;
 			}
-	
+
 			this.registrationTicketsRepository.delete(ticket.id);
 		}
-	
+
 		if (instance.emailRequiredForSignup) {
 			if (await this.usersRepository.findOneBy({ usernameLower: username.toLowerCase(), host: IsNull() })) {
 				throw new FastifyReplyError(400, 'DUPLICATED_USERNAME');
@@ -142,7 +142,7 @@ export class SignupApiService {
 				throw new FastifyReplyError(400, 'DENIED_USERNAME');
 			}
 
-			const code = rndstr('a-z0-9', 16);
+			const code = secureRndstr(16, { chars: L_CHARS });
 
 			// Generate hash of password
 			const salt = await bcrypt.genSalt(8);
@@ -170,12 +170,12 @@ export class SignupApiService {
 				const { account, secret } = await this.signupService.signup({
 					username, password, host,
 				});
-	
+
 				const res = await this.userEntityService.pack(account, account, {
 					detail: true,
 					includeSecrets: true,
 				});
-	
+
 				return {
 					...res,
 					token: secret,
diff --git a/packages/backend/src/server/api/endpoints/admin/emoji/add.ts b/packages/backend/src/server/api/endpoints/admin/emoji/add.ts
index 509224e9c3..2fcf0da3f0 100644
--- a/packages/backend/src/server/api/endpoints/admin/emoji/add.ts
+++ b/packages/backend/src/server/api/endpoints/admin/emoji/add.ts
@@ -1,5 +1,4 @@
 import { Inject, Injectable } from '@nestjs/common';
-import rndstr from 'rndstr';
 import { Endpoint } from '@/server/api/endpoint-base.js';
 import type { DriveFilesRepository } from '@/models/index.js';
 import { DI } from '@/di-symbols.js';
diff --git a/packages/backend/src/server/api/endpoints/admin/reset-password.ts b/packages/backend/src/server/api/endpoints/admin/reset-password.ts
index d263f99f6e..e9c3b0e69f 100644
--- a/packages/backend/src/server/api/endpoints/admin/reset-password.ts
+++ b/packages/backend/src/server/api/endpoints/admin/reset-password.ts
@@ -1,9 +1,9 @@
 import { Inject, Injectable } from '@nestjs/common';
 import bcrypt from 'bcryptjs';
-import rndstr from 'rndstr';
 import { Endpoint } from '@/server/api/endpoint-base.js';
 import type { UsersRepository, UserProfilesRepository } from '@/models/index.js';
 import { DI } from '@/di-symbols.js';
+import { secureRndstr } from '@/misc/secure-rndstr.js';
 
 export const meta = {
 	tags: ['admin'],
@@ -54,7 +54,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 				throw new Error('cannot reset password of root');
 			}
 
-			const passwd = rndstr('a-zA-Z0-9', 8);
+			const passwd = secureRndstr(8);
 
 			// Generate hash of password
 			const hash = bcrypt.hashSync(passwd);
diff --git a/packages/backend/src/server/api/endpoints/app/create.ts b/packages/backend/src/server/api/endpoints/app/create.ts
index c1d0a9dd74..aaef02d03f 100644
--- a/packages/backend/src/server/api/endpoints/app/create.ts
+++ b/packages/backend/src/server/api/endpoints/app/create.ts
@@ -44,7 +44,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 	) {
 		super(meta, paramDef, async (ps, me) => {
 			// Generate secret
-			const secret = secureRndstr(32, true);
+			const secret = secureRndstr(32);
 
 			// for backward compatibility
 			const permission = unique(ps.permission.map(v => v.replace(/^(.+)(\/|-)(read|write)$/, '$3:$1')));
diff --git a/packages/backend/src/server/api/endpoints/auth/accept.ts b/packages/backend/src/server/api/endpoints/auth/accept.ts
index 05842460cf..e69f9c12e2 100644
--- a/packages/backend/src/server/api/endpoints/auth/accept.ts
+++ b/packages/backend/src/server/api/endpoints/auth/accept.ts
@@ -55,7 +55,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 				throw new ApiError(meta.errors.noSuchSession);
 			}
 
-			const accessToken = secureRndstr(32, true);
+			const accessToken = secureRndstr(32);
 
 			// Fetch exist access token
 			const exist = await this.accessTokensRepository.findOneBy({
diff --git a/packages/backend/src/server/api/endpoints/i/update-email.ts b/packages/backend/src/server/api/endpoints/i/update-email.ts
index 4f543a6472..58e056bd37 100644
--- a/packages/backend/src/server/api/endpoints/i/update-email.ts
+++ b/packages/backend/src/server/api/endpoints/i/update-email.ts
@@ -1,5 +1,4 @@
 import { Inject, Injectable } from '@nestjs/common';
-import rndstr from 'rndstr';
 import ms from 'ms';
 import bcrypt from 'bcryptjs';
 import { Endpoint } from '@/server/api/endpoint-base.js';
@@ -9,6 +8,7 @@ import { EmailService } from '@/core/EmailService.js';
 import type { Config } from '@/config.js';
 import { DI } from '@/di-symbols.js';
 import { GlobalEventService } from '@/core/GlobalEventService.js';
+import { L_CHARS, secureRndstr } from '@/misc/secure-rndstr.js';
 import { ApiError } from '../../error.js';
 
 export const meta = {
@@ -94,7 +94,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 			this.globalEventService.publishMainStream(me.id, 'meUpdated', iObj);
 
 			if (ps.email != null) {
-				const code = rndstr('a-z0-9', 16);
+				const code = secureRndstr(16, { chars: L_CHARS });
 
 				await this.userProfilesRepository.update(me.id, {
 					emailVerifyCode: code,
diff --git a/packages/backend/src/server/api/endpoints/invite.ts b/packages/backend/src/server/api/endpoints/invite.ts
index 5d2c479e79..276adcb07f 100644
--- a/packages/backend/src/server/api/endpoints/invite.ts
+++ b/packages/backend/src/server/api/endpoints/invite.ts
@@ -1,9 +1,9 @@
-import rndstr from 'rndstr';
 import { Inject, Injectable } from '@nestjs/common';
 import { Endpoint } from '@/server/api/endpoint-base.js';
 import type { RegistrationTicketsRepository } from '@/models/index.js';
 import { IdService } from '@/core/IdService.js';
 import { DI } from '@/di-symbols.js';
+import { secureRndstr } from '@/misc/secure-rndstr.js';
 
 export const meta = {
 	tags: ['meta'],
@@ -42,9 +42,8 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 		private idService: IdService,
 	) {
 		super(meta, paramDef, async (ps, me) => {
-			const code = rndstr({
-				length: 8,
-				chars: '2-9A-HJ-NP-Z', // [0-9A-Z] w/o [01IO] (32 patterns)
+			const code = secureRndstr(8, {
+				chars: '23456789ABCDEFGHJKLMNPQRSTUVWXYZ', // [0-9A-Z] w/o [01IO] (32 patterns)
 			});
 
 			await this.registrationTicketsRepository.insert({
diff --git a/packages/backend/src/server/api/endpoints/miauth/gen-token.ts b/packages/backend/src/server/api/endpoints/miauth/gen-token.ts
index 97def86262..0ea29f04dc 100644
--- a/packages/backend/src/server/api/endpoints/miauth/gen-token.ts
+++ b/packages/backend/src/server/api/endpoints/miauth/gen-token.ts
@@ -49,7 +49,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 	) {
 		super(meta, paramDef, async (ps, me) => {
 			// Generate access token
-			const accessToken = secureRndstr(32, true);
+			const accessToken = secureRndstr(32);
 
 			const now = new Date();
 
diff --git a/packages/backend/src/server/api/endpoints/request-reset-password.ts b/packages/backend/src/server/api/endpoints/request-reset-password.ts
index 3b6ebfe281..284ed8410d 100644
--- a/packages/backend/src/server/api/endpoints/request-reset-password.ts
+++ b/packages/backend/src/server/api/endpoints/request-reset-password.ts
@@ -1,4 +1,3 @@
-import rndstr from 'rndstr';
 import ms from 'ms';
 import { IsNull } from 'typeorm';
 import { Inject, Injectable } from '@nestjs/common';
@@ -8,6 +7,7 @@ import { IdService } from '@/core/IdService.js';
 import type { Config } from '@/config.js';
 import { DI } from '@/di-symbols.js';
 import { EmailService } from '@/core/EmailService.js';
+import { L_CHARS, secureRndstr } from '@/misc/secure-rndstr.js';
 
 export const meta = {
 	tags: ['reset password'],
@@ -41,7 +41,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 	constructor(
 		@Inject(DI.config)
 		private config: Config,
-		
+
 		@Inject(DI.usersRepository)
 		private usersRepository: UsersRepository,
 
@@ -77,7 +77,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 				return;
 			}
 
-			const token = rndstr('a-z0-9', 64);
+			const token = secureRndstr(64, { chars: L_CHARS });
 
 			await this.passwordResetRequestsRepository.insert({
 				id: this.idService.genId(),
diff --git a/packages/backend/test/e2e/move.ts b/packages/backend/test/e2e/move.ts
index cd9459fa52..2fefcd0f0e 100644
--- a/packages/backend/test/e2e/move.ts
+++ b/packages/backend/test/e2e/move.ts
@@ -1,10 +1,10 @@
 process.env.NODE_ENV = 'test';
 
 import * as assert from 'assert';
-import rndstr from 'rndstr';
 import { loadConfig } from '@/config.js';
 import { User, UsersRepository } from '@/models/index.js';
 import { jobQueue } from '@/boot/common.js';
+import { secureRndstr } from '@/misc/secure-rndstr.js';
 import { uploadFile, signup, startServer, initTestDb, api, sleep, successfulApiCall } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
 import type * as misskey from 'misskey-js';
@@ -163,7 +163,7 @@ describe('Account Move', () => {
 				alsoKnownAs: [`@alice@${url.hostname}`],
 			}, root);
 			const listRoot = await api('/users/lists/create', {
-				name: rndstr('0-9a-z', 8),
+				name: secureRndstr(8),
 			}, root);
 			await api('/users/lists/push', {
 				listId: listRoot.body.id,
@@ -177,9 +177,9 @@ describe('Account Move', () => {
 				userId: eve.id,
 			}, alice);
 			const antenna = await api('/antennas/create', {
-				name: rndstr('0-9a-z', 8),
+				name: secureRndstr(8),
 				src: 'home',
-				keywords: [rndstr('0-9a-z', 8)],
+				keywords: [secureRndstr(8)],
 				excludeKeywords: [],
 				users: [],
 				caseSensitive: false,
@@ -211,7 +211,7 @@ describe('Account Move', () => {
 				userId: dave.id,
 			}, eve);
 			const listEve = await api('/users/lists/create', {
-				name: rndstr('0-9a-z', 8),
+				name: secureRndstr(8),
 			}, eve);
 			await api('/users/lists/push', {
 				listId: listEve.body.id,
@@ -420,9 +420,9 @@ describe('Account Move', () => {
 		test('Prohibit access after moving: /antennas/update', async () => {
 			const res = await api('/antennas/update', {
 				antennaId,
-				name: rndstr('0-9a-z', 8),
+				name: secureRndstr(8),
 				src: 'users',
-				keywords: [rndstr('0-9a-z', 8)],
+				keywords: [secureRndstr(8)],
 				excludeKeywords: [],
 				users: [eve.id],
 				caseSensitive: false,
diff --git a/packages/backend/test/unit/RoleService.ts b/packages/backend/test/unit/RoleService.ts
index 907f1f2edc..6979f23e0c 100644
--- a/packages/backend/test/unit/RoleService.ts
+++ b/packages/backend/test/unit/RoleService.ts
@@ -4,7 +4,6 @@ import { jest } from '@jest/globals';
 import { ModuleMocker } from 'jest-mock';
 import { Test } from '@nestjs/testing';
 import * as lolex from '@sinonjs/fake-timers';
-import rndstr from 'rndstr';
 import { GlobalModule } from '@/GlobalModule.js';
 import { RoleService } from '@/core/RoleService.js';
 import type { Role, RolesRepository, RoleAssignmentsRepository, UsersRepository, User } from '@/models/index.js';
@@ -14,6 +13,7 @@ import { genAid } from '@/misc/id/aid.js';
 import { CacheService } from '@/core/CacheService.js';
 import { IdService } from '@/core/IdService.js';
 import { GlobalEventService } from '@/core/GlobalEventService.js';
+import { secureRndstr } from '@/misc/secure-rndstr.js';
 import { sleep } from '../utils.js';
 import type { TestingModule } from '@nestjs/testing';
 import type { MockFunctionMetadata } from 'jest-mock';
@@ -30,7 +30,7 @@ describe('RoleService', () => {
 	let clock: lolex.InstalledClock;
 
 	function createUser(data: Partial<User> = {}) {
-		const un = rndstr('a-z0-9', 16);
+		const un = secureRndstr(16);
 		return usersRepository.insert({
 			id: genAid(new Date()),
 			createdAt: new Date(),
@@ -106,19 +106,19 @@ describe('RoleService', () => {
 	});
 
 	describe('getUserPolicies', () => {
-		test('instance default policies', async () => {	
+		test('instance default policies', async () => {
 			const user = await createUser();
 			metaService.fetch.mockResolvedValue({
 				policies: {
 					canManageCustomEmojis: false,
 				},
 			} as any);
-	
+
 			const result = await roleService.getUserPolicies(user.id);
-	
+
 			expect(result.canManageCustomEmojis).toBe(false);
 		});
-	
+
 		test('instance default policies 2', async () => {
 			const user = await createUser();
 			metaService.fetch.mockResolvedValue({
@@ -126,12 +126,12 @@ describe('RoleService', () => {
 					canManageCustomEmojis: true,
 				},
 			} as any);
-	
+
 			const result = await roleService.getUserPolicies(user.id);
-	
+
 			expect(result.canManageCustomEmojis).toBe(true);
 		});
-	
+
 		test('with role', async () => {
 			const user = await createUser();
 			const role = await createRole({
@@ -150,9 +150,9 @@ describe('RoleService', () => {
 					canManageCustomEmojis: false,
 				},
 			} as any);
-	
+
 			const result = await roleService.getUserPolicies(user.id);
-	
+
 			expect(result.canManageCustomEmojis).toBe(true);
 		});
 
@@ -185,9 +185,9 @@ describe('RoleService', () => {
 					driveCapacityMb: 50,
 				},
 			} as any);
-	
+
 			const result = await roleService.getUserPolicies(user.id);
-	
+
 			expect(result.driveCapacityMb).toBe(100);
 		});
 
@@ -226,7 +226,7 @@ describe('RoleService', () => {
 					canManageCustomEmojis: false,
 				},
 			} as any);
-	
+
 			const user1Policies = await roleService.getUserPolicies(user1.id);
 			const user2Policies = await roleService.getUserPolicies(user2.id);
 			expect(user1Policies.canManageCustomEmojis).toBe(false);
@@ -251,7 +251,7 @@ describe('RoleService', () => {
 					canManageCustomEmojis: false,
 				},
 			} as any);
-	
+
 			const result = await roleService.getUserPolicies(user.id);
 			expect(result.canManageCustomEmojis).toBe(true);
 
diff --git a/packages/backend/test/unit/activitypub.ts b/packages/backend/test/unit/activitypub.ts
index 146998937e..7cd740a2fa 100644
--- a/packages/backend/test/unit/activitypub.ts
+++ b/packages/backend/test/unit/activitypub.ts
@@ -1,7 +1,6 @@
 process.env.NODE_ENV = 'test';
 
 import * as assert from 'assert';
-import rndstr from 'rndstr';
 import { Test } from '@nestjs/testing';
 import { jest } from '@jest/globals';
 
@@ -13,13 +12,14 @@ import { CoreModule } from '@/core/CoreModule.js';
 import { FederatedInstanceService } from '@/core/FederatedInstanceService.js';
 import { LoggerService } from '@/core/LoggerService.js';
 import type { IActor } from '@/core/activitypub/type.js';
-import { MockResolver } from '../misc/mock-resolver.js';
 import { Note } from '@/models/index.js';
+import { secureRndstr } from '@/misc/secure-rndstr.js';
+import { MockResolver } from '../misc/mock-resolver.js';
 
 const host = 'https://host1.test';
 
 function createRandomActor(): IActor & { id: string } {
-	const preferredUsername = `${rndstr('A-Z', 4)}${rndstr('a-z', 4)}`;
+	const preferredUsername = secureRndstr(8);
 	const actorId = `${host}/users/${preferredUsername.toLowerCase()}`;
 
 	return {
@@ -61,7 +61,7 @@ describe('ActivityPub', () => {
 
 		const post = {
 			'@context': 'https://www.w3.org/ns/activitystreams',
-			id: `${host}/users/${rndstr('0-9a-z', 8)}`,
+			id: `${host}/users/${secureRndstr(8)}`,
 			type: 'Note',
 			attributedTo: actor.id,
 			to: 'https://www.w3.org/ns/activitystreams#Public',
@@ -94,7 +94,7 @@ describe('ActivityPub', () => {
 		test('Truncate long name', async () => {
 			const actor = {
 				...createRandomActor(),
-				name: rndstr('0-9a-z', 129),
+				name: secureRndstr(129),
 			};
 
 			resolver._register(actor.id, actor);
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index 97f9a9583c..893e5409b1 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -314,9 +314,6 @@ importers:
       rename:
         specifier: 1.0.4
         version: 1.0.4
-      rndstr:
-        specifier: 1.0.0
-        version: 1.0.0
       rss-parser:
         specifier: 3.13.0
         version: 3.13.0

From 8099bc24e181790b6bfd267d013aac0713c68f31 Mon Sep 17 00:00:00 2001
From: syuilo <Syuilotan@yahoo.co.jp>
Date: Sun, 25 Jun 2023 21:13:15 +0900
Subject: [PATCH 13/17] refactor(backend): use node16 for moduleResolution
 (#10938)

* refactor(backend): use node16 for moduleResolution

* update deps

* Update tsconfig.json

* :v:

* revive KEYWORD

* restore strict-event-emitter-types dependency

* restore ms dependency

* cancel redundant import reorder

* fix

* Delete ms.ts

* remove rndstr

---------

Co-authored-by: Kagami Sascha Rosylight <saschanaz@outlook.com>
---
 packages/backend/.swcrc                       |  2 +-
 packages/backend/package.json                 |  6 +-
 .../backend/src/core/GlobalEventService.ts    |  2 +-
 packages/backend/src/core/LoggerService.ts    |  2 +-
 .../src/core/PushNotificationService.ts       |  2 +-
 packages/backend/src/core/RoleService.ts      |  2 +-
 .../src/core/entities/UserEntityService.ts    |  3 +-
 packages/backend/src/logger.ts                |  2 +-
 .../ImportAntennasProcessorService.ts         |  4 +-
 .../server/api/StreamingApiServerService.ts   |  2 +-
 .../backend/src/server/api/endpoint-base.ts   |  4 +-
 .../server/api/endpoints/i/import-antennas.ts |  4 +-
 .../server/api/endpoints/i/import-blocking.ts |  2 +-
 .../api/endpoints/i/import-following.ts       |  2 +-
 .../server/api/endpoints/i/import-muting.ts   |  2 +-
 .../api/endpoints/i/import-user-lists.ts      |  2 +-
 .../server/api/endpoints/notes/unrenote.ts    |  2 +-
 .../api/endpoints/users/recommendation.ts     |  2 +-
 .../api/endpoints/users/report-abuse.ts       |  2 +-
 .../backend/src/server/api/stream/channel.ts  |  2 +-
 .../backend/src/server/api/stream/types.ts    |  4 +-
 packages/backend/test/tsconfig.json           |  6 +-
 packages/backend/tsconfig.json                |  6 +-
 packages/frontend/package.json                |  3 -
 packages/frontend/test/tsconfig.json          |  8 +--
 packages/frontend/tsconfig.json               |  4 +-
 packages/misskey-js/tsconfig.json             |  4 +-
 packages/sw/tsconfig.json                     |  8 +--
 pnpm-lock.yaml                                | 64 +++++++------------
 29 files changed, 72 insertions(+), 86 deletions(-)

diff --git a/packages/backend/.swcrc b/packages/backend/.swcrc
index 08d4222d01..0504a2d389 100644
--- a/packages/backend/.swcrc
+++ b/packages/backend/.swcrc
@@ -17,7 +17,7 @@
 		"paths": {
 			"@/*": ["*"]
 		},
-		"target": "es2021"
+		"target": "es2022"
 	},
 	"minify": false
 }
diff --git a/packages/backend/package.json b/packages/backend/package.json
index c13f292c76..6de4e634fd 100644
--- a/packages/backend/package.json
+++ b/packages/backend/package.json
@@ -79,7 +79,7 @@
 		"bcryptjs": "2.4.3",
 		"blurhash": "2.0.5",
 		"bullmq": "4.1.0",
-		"cacheable-lookup": "6.1.0",
+		"cacheable-lookup": "7.0.0",
 		"cbor": "9.0.0",
 		"chalk": "5.2.0",
 		"chalk-template": "0.4.0",
@@ -95,7 +95,7 @@
 		"file-type": "18.5.0",
 		"fluent-ffmpeg": "2.1.2",
 		"form-data": "4.0.0",
-		"got": "12.6.0",
+		"got": "13.0.0",
 		"happy-dom": "9.20.3",
 		"hpagent": "1.2.0",
 		"ioredis": "5.3.2",
@@ -137,7 +137,6 @@
 		"rxjs": "7.8.1",
 		"s-age": "1.1.2",
 		"sanitize-html": "2.11.0",
-		"seedrandom": "3.0.5",
 		"semver": "7.5.3",
 		"sharp": "0.32.1",
 		"sharp-read-bmp": "github:misskey-dev/sharp-read-bmp",
@@ -178,6 +177,7 @@
 		"@types/jsonld": "1.5.9",
 		"@types/jsrsasign": "10.5.8",
 		"@types/mime-types": "2.1.1",
+		"@types/ms": "^0.7.31",
 		"@types/node": "20.3.1",
 		"@types/node-fetch": "3.0.3",
 		"@types/nodemailer": "6.4.8",
diff --git a/packages/backend/src/core/GlobalEventService.ts b/packages/backend/src/core/GlobalEventService.ts
index 0ed5241148..19d9370083 100644
--- a/packages/backend/src/core/GlobalEventService.ts
+++ b/packages/backend/src/core/GlobalEventService.ts
@@ -20,7 +20,7 @@ import type { Packed } from '@/misc/json-schema.js';
 import { DI } from '@/di-symbols.js';
 import type { Config } from '@/config.js';
 import { bindThis } from '@/decorators.js';
-import { Role } from '@/models';
+import { Role } from '@/models/index.js';
 
 @Injectable()
 export class GlobalEventService {
diff --git a/packages/backend/src/core/LoggerService.ts b/packages/backend/src/core/LoggerService.ts
index 441c254f48..14df9aa40c 100644
--- a/packages/backend/src/core/LoggerService.ts
+++ b/packages/backend/src/core/LoggerService.ts
@@ -3,7 +3,7 @@ import { DI } from '@/di-symbols.js';
 import type { Config } from '@/config.js';
 import Logger from '@/logger.js';
 import { bindThis } from '@/decorators.js';
-import type { KEYWORD } from 'color-convert/conversions';
+import type { KEYWORD } from 'color-convert/conversions.js';
 
 @Injectable()
 export class LoggerService {
diff --git a/packages/backend/src/core/PushNotificationService.ts b/packages/backend/src/core/PushNotificationService.ts
index 15a1d74878..9ee83df644 100644
--- a/packages/backend/src/core/PushNotificationService.ts
+++ b/packages/backend/src/core/PushNotificationService.ts
@@ -3,7 +3,7 @@ import push from 'web-push';
 import * as Redis from 'ioredis';
 import { DI } from '@/di-symbols.js';
 import type { Config } from '@/config.js';
-import type { Packed } from '@/misc/json-schema';
+import type { Packed } from '@/misc/json-schema.js';
 import { getNoteSummary } from '@/misc/get-note-summary.js';
 import type { SwSubscription, SwSubscriptionsRepository } from '@/models/index.js';
 import { MetaService } from '@/core/MetaService.js';
diff --git a/packages/backend/src/core/RoleService.ts b/packages/backend/src/core/RoleService.ts
index 79922d0a87..23ecf0157d 100644
--- a/packages/backend/src/core/RoleService.ts
+++ b/packages/backend/src/core/RoleService.ts
@@ -13,7 +13,7 @@ import { UserEntityService } from '@/core/entities/UserEntityService.js';
 import { StreamMessages } from '@/server/api/stream/types.js';
 import { IdService } from '@/core/IdService.js';
 import { GlobalEventService } from '@/core/GlobalEventService.js';
-import type { Packed } from '@/misc/json-schema';
+import type { Packed } from '@/misc/json-schema.js';
 import type { OnApplicationShutdown } from '@nestjs/common';
 
 export type RolePolicies = {
diff --git a/packages/backend/src/core/entities/UserEntityService.ts b/packages/backend/src/core/entities/UserEntityService.ts
index bfd506ea86..f1a4e56c02 100644
--- a/packages/backend/src/core/entities/UserEntityService.ts
+++ b/packages/backend/src/core/entities/UserEntityService.ts
@@ -1,7 +1,7 @@
 import { Inject, Injectable } from '@nestjs/common';
 import { In, Not } from 'typeorm';
 import * as Redis from 'ioredis';
-import Ajv from 'ajv';
+import _Ajv from 'ajv';
 import { ModuleRef } from '@nestjs/core';
 import { DI } from '@/di-symbols.js';
 import type { Config } from '@/config.js';
@@ -31,6 +31,7 @@ type IsMeAndIsUserDetailed<ExpectsMe extends boolean | null, Detailed extends bo
 		Packed<'UserDetailed'> :
 	Packed<'UserLite'>;
 
+const Ajv = _Ajv.default;
 const ajv = new Ajv();
 
 function isLocalUser(user: User): user is LocalUser;
diff --git a/packages/backend/src/logger.ts b/packages/backend/src/logger.ts
index 91039098f1..465b557ce4 100644
--- a/packages/backend/src/logger.ts
+++ b/packages/backend/src/logger.ts
@@ -4,7 +4,7 @@ import { default as convertColor } from 'color-convert';
 import { format as dateFormat } from 'date-fns';
 import { bindThis } from '@/decorators.js';
 import { envOption } from './env.js';
-import type { KEYWORD } from 'color-convert/conversions';
+import type { KEYWORD } from 'color-convert/conversions.js';
 
 type Context = {
 	name: string;
diff --git a/packages/backend/src/queue/processors/ImportAntennasProcessorService.ts b/packages/backend/src/queue/processors/ImportAntennasProcessorService.ts
index 575cad69d5..0c09f2796f 100644
--- a/packages/backend/src/queue/processors/ImportAntennasProcessorService.ts
+++ b/packages/backend/src/queue/processors/ImportAntennasProcessorService.ts
@@ -1,5 +1,5 @@
 import { Injectable, Inject } from '@nestjs/common';
-import Ajv from 'ajv';
+import _Ajv from 'ajv';
 import { IdService } from '@/core/IdService.js';
 import { GlobalEventService } from '@/core/GlobalEventService.js';
 import Logger from '@/logger.js';
@@ -10,6 +10,8 @@ import { QueueLoggerService } from '../QueueLoggerService.js';
 import { DBAntennaImportJobData } from '../types.js';
 import type * as Bull from 'bullmq';
 
+const Ajv = _Ajv.default;
+
 const validate = new Ajv().compile({
 	type: 'object',
 	properties: {
diff --git a/packages/backend/src/server/api/StreamingApiServerService.ts b/packages/backend/src/server/api/StreamingApiServerService.ts
index d1394d6d76..8f2e51d584 100644
--- a/packages/backend/src/server/api/StreamingApiServerService.ts
+++ b/packages/backend/src/server/api/StreamingApiServerService.ts
@@ -10,7 +10,7 @@ import { GlobalEventService } from '@/core/GlobalEventService.js';
 import { NotificationService } from '@/core/NotificationService.js';
 import { bindThis } from '@/decorators.js';
 import { CacheService } from '@/core/CacheService.js';
-import { LocalUser } from '@/models/entities/User';
+import { LocalUser } from '@/models/entities/User.js';
 import { AuthenticateService, AuthenticationError } from './AuthenticateService.js';
 import MainStreamConnection from './stream/index.js';
 import { ChannelsService } from './stream/ChannelsService.js';
diff --git a/packages/backend/src/server/api/endpoint-base.ts b/packages/backend/src/server/api/endpoint-base.ts
index 1555a3ca46..05141854c7 100644
--- a/packages/backend/src/server/api/endpoint-base.ts
+++ b/packages/backend/src/server/api/endpoint-base.ts
@@ -1,11 +1,13 @@
 import * as fs from 'node:fs';
-import Ajv from 'ajv';
+import _Ajv from 'ajv';
 import type { Schema, SchemaType } from '@/misc/json-schema.js';
 import type { LocalUser } from '@/models/entities/User.js';
 import type { AccessToken } from '@/models/entities/AccessToken.js';
 import { ApiError } from './error.js';
 import type { IEndpointMeta } from './endpoints.js';
 
+const Ajv = _Ajv.default;
+
 const ajv = new Ajv({
 	useDefaults: true,
 });
diff --git a/packages/backend/src/server/api/endpoints/i/import-antennas.ts b/packages/backend/src/server/api/endpoints/i/import-antennas.ts
index efb5ce4223..12ec5855d3 100644
--- a/packages/backend/src/server/api/endpoints/i/import-antennas.ts
+++ b/packages/backend/src/server/api/endpoints/i/import-antennas.ts
@@ -54,7 +54,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 	constructor (
 		@Inject(DI.driveFilesRepository)
 		private driveFilesRepository: DriveFilesRepository,
-		
+
 		@Inject(DI.antennasRepository)
 		private antennasRepository: AntennasRepository,
 
@@ -79,6 +79,6 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 			this.queueService.createImportAntennasJob(me, antennas);
 		});
 	}
-} 
+}
 
 export type Antenna = (_Antenna & { userListAccts: string[] | null })[];
diff --git a/packages/backend/src/server/api/endpoints/i/import-blocking.ts b/packages/backend/src/server/api/endpoints/i/import-blocking.ts
index 811971591a..32c16300fb 100644
--- a/packages/backend/src/server/api/endpoints/i/import-blocking.ts
+++ b/packages/backend/src/server/api/endpoints/i/import-blocking.ts
@@ -72,7 +72,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 			const checkMoving = await this.accountMoveService.validateAlsoKnownAs(
 				me,
 				(old, src) => !!src.movedAt && src.movedAt.getTime() + 1000 * 60 * 60 * 2 > (new Date()).getTime(),
-				true
+				true,
 			);
 			if (checkMoving ? file.size > 32 * 1024 * 1024 : file.size > 64 * 1024) throw new ApiError(meta.errors.tooBigFile);
 
diff --git a/packages/backend/src/server/api/endpoints/i/import-following.ts b/packages/backend/src/server/api/endpoints/i/import-following.ts
index 8af278c883..1926a1f503 100644
--- a/packages/backend/src/server/api/endpoints/i/import-following.ts
+++ b/packages/backend/src/server/api/endpoints/i/import-following.ts
@@ -71,7 +71,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 			const checkMoving = await this.accountMoveService.validateAlsoKnownAs(
 				me,
 				(old, src) => !!src.movedAt && src.movedAt.getTime() + 1000 * 60 * 60 * 2 > (new Date()).getTime(),
-				true
+				true,
 			);
 			if (checkMoving ? file.size > 32 * 1024 * 1024 : file.size > 64 * 1024) throw new ApiError(meta.errors.tooBigFile);
 
diff --git a/packages/backend/src/server/api/endpoints/i/import-muting.ts b/packages/backend/src/server/api/endpoints/i/import-muting.ts
index eb0f9ba474..34f2627563 100644
--- a/packages/backend/src/server/api/endpoints/i/import-muting.ts
+++ b/packages/backend/src/server/api/endpoints/i/import-muting.ts
@@ -72,7 +72,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 			const checkMoving = await this.accountMoveService.validateAlsoKnownAs(
 				me,
 				(old, src) => !!src.movedAt && src.movedAt.getTime() + 1000 * 60 * 60 * 2 > (new Date()).getTime(),
-				true
+				true,
 			);
 			if (checkMoving ? file.size > 32 * 1024 * 1024 : file.size > 64 * 1024) throw new ApiError(meta.errors.tooBigFile);
 
diff --git a/packages/backend/src/server/api/endpoints/i/import-user-lists.ts b/packages/backend/src/server/api/endpoints/i/import-user-lists.ts
index 4568e93901..1b3cb5359d 100644
--- a/packages/backend/src/server/api/endpoints/i/import-user-lists.ts
+++ b/packages/backend/src/server/api/endpoints/i/import-user-lists.ts
@@ -71,7 +71,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 			const checkMoving = await this.accountMoveService.validateAlsoKnownAs(
 				me,
 				(old, src) => !!src.movedAt && src.movedAt.getTime() + 1000 * 60 * 60 * 2 > (new Date()).getTime(),
-				true
+				true,
 			);
 			if (checkMoving ? file.size > 32 * 1024 * 1024 : file.size > 64 * 1024) throw new ApiError(meta.errors.tooBigFile);
 
diff --git a/packages/backend/src/server/api/endpoints/notes/unrenote.ts b/packages/backend/src/server/api/endpoints/notes/unrenote.ts
index 74e459b426..e9581beedc 100644
--- a/packages/backend/src/server/api/endpoints/notes/unrenote.ts
+++ b/packages/backend/src/server/api/endpoints/notes/unrenote.ts
@@ -4,8 +4,8 @@ import type { UsersRepository, NotesRepository } from '@/models/index.js';
 import { Endpoint } from '@/server/api/endpoint-base.js';
 import { NoteDeleteService } from '@/core/NoteDeleteService.js';
 import { DI } from '@/di-symbols.js';
-import { ApiError } from '../../error.js';
 import { GetterService } from '@/server/api/GetterService.js';
+import { ApiError } from '../../error.js';
 
 export const meta = {
 	tags: ['notes'],
diff --git a/packages/backend/src/server/api/endpoints/users/recommendation.ts b/packages/backend/src/server/api/endpoints/users/recommendation.ts
index 5498b8c854..6fcc04e2c5 100644
--- a/packages/backend/src/server/api/endpoints/users/recommendation.ts
+++ b/packages/backend/src/server/api/endpoints/users/recommendation.ts
@@ -44,7 +44,7 @@ export default class extends Endpoint<typeof meta, typeof paramDef> {
 
 		@Inject(DI.followingsRepository)
 		private followingsRepository: FollowingsRepository,
-		
+
 		private userEntityService: UserEntityService,
 		private queryService: QueryService,
 	) {
diff --git a/packages/backend/src/server/api/endpoints/users/report-abuse.ts b/packages/backend/src/server/api/endpoints/users/report-abuse.ts
index d19d4007d6..be361e02c4 100644
--- a/packages/backend/src/server/api/endpoints/users/report-abuse.ts
+++ b/packages/backend/src/server/api/endpoints/users/report-abuse.ts
@@ -1,4 +1,4 @@
-import * as sanitizeHtml from 'sanitize-html';
+import sanitizeHtml from 'sanitize-html';
 import { Inject, Injectable } from '@nestjs/common';
 import type { UsersRepository, AbuseUserReportsRepository } from '@/models/index.js';
 import { IdService } from '@/core/IdService.js';
diff --git a/packages/backend/src/server/api/stream/channel.ts b/packages/backend/src/server/api/stream/channel.ts
index e67aec9ecd..94b92e02ef 100644
--- a/packages/backend/src/server/api/stream/channel.ts
+++ b/packages/backend/src/server/api/stream/channel.ts
@@ -1,5 +1,5 @@
 import { bindThis } from '@/decorators.js';
-import type Connection from '.';
+import type Connection from './index.js';
 
 /**
  * Stream channel
diff --git a/packages/backend/src/server/api/stream/types.ts b/packages/backend/src/server/api/stream/types.ts
index d9dba682cd..f239b06637 100644
--- a/packages/backend/src/server/api/stream/types.ts
+++ b/packages/backend/src/server/api/stream/types.ts
@@ -12,7 +12,7 @@ import type { Page } from '@/models/entities/Page.js';
 import type { Packed } from '@/misc/json-schema.js';
 import type { Webhook } from '@/models/entities/Webhook.js';
 import type { Meta } from '@/models/entities/Meta.js';
-import { Role, RoleAssignment } from '@/models';
+import { Role, RoleAssignment } from '@/models/index.js';
 import type Emitter from 'strict-event-emitter-types';
 import type { EventEmitter } from 'events';
 
@@ -233,7 +233,7 @@ export type StreamMessages = {
 
 // API event definitions
 // ストリームごとのEmitterの辞書を用意
-type EventEmitterDictionary = { [x in keyof StreamMessages]: Emitter<EventEmitter, { [y in StreamMessages[x]['name']]: (e: StreamMessages[x]['payload']) => void }> };
+type EventEmitterDictionary = { [x in keyof StreamMessages]: Emitter.default<EventEmitter, { [y in StreamMessages[x]['name']]: (e: StreamMessages[x]['payload']) => void }> };
 // 共用体型を交差型にする型 https://stackoverflow.com/questions/54938141/typescript-convert-union-to-intersection
 type UnionToIntersection<U> = (U extends any ? (k: U) => void : never) extends ((k: infer I) => void) ? I : never;
 // Emitter辞書から共用体型を作り、UnionToIntersectionで交差型にする
diff --git a/packages/backend/test/tsconfig.json b/packages/backend/test/tsconfig.json
index 8a024a678b..21afe1aaf3 100644
--- a/packages/backend/test/tsconfig.json
+++ b/packages/backend/test/tsconfig.json
@@ -9,9 +9,9 @@
 		"noFallthroughCasesInSwitch": true,
 		"declaration": false,
 		"sourceMap": true,
-		"target": "es2021",
+		"target": "ES2022",
 		"module": "es2020",
-		"moduleResolution": "node",
+		"moduleResolution": "node16",
 		"allowSyntheticDefaultImports": true,
 		"removeComments": false,
 		"noLib": false,
@@ -39,6 +39,6 @@
 	"include": [
 		"./**/*.ts",
 		"../src/**/*.test.ts",
-		"../src/@types/**/*.ts",
+		"../src/@types/**/*.ts"
 	]
 }
diff --git a/packages/backend/tsconfig.json b/packages/backend/tsconfig.json
index faadbcdfc6..93944a68d5 100644
--- a/packages/backend/tsconfig.json
+++ b/packages/backend/tsconfig.json
@@ -9,9 +9,9 @@
 		"noFallthroughCasesInSwitch": true,
 		"declaration": false,
 		"sourceMap": false,
-		"target": "es2021",
-		"module": "esnext",
-		"moduleResolution": "node",
+		"target": "ES2022",
+		"module": "ESNext",
+		"moduleResolution": "node16",
 		"allowSyntheticDefaultImports": true,
 		"removeComments": false,
 		"noLib": false,
diff --git a/packages/frontend/package.json b/packages/frontend/package.json
index b9208a566e..898002082c 100644
--- a/packages/frontend/package.json
+++ b/packages/frontend/package.json
@@ -54,12 +54,10 @@
 		"prismjs": "1.29.0",
 		"punycode": "2.3.0",
 		"querystring": "0.2.1",
-		"rndstr": "1.0.0",
 		"rollup": "3.25.1",
 		"s-age": "1.1.2",
 		"sanitize-html": "2.11.0",
 		"sass": "1.63.6",
-		"seedrandom": "3.0.5",
 		"strict-event-emitter-types": "2.0.0",
 		"syuilo-password-strength": "0.0.1",
 		"textarea-caret": "3.1.0",
@@ -107,7 +105,6 @@
 		"@types/node": "20.3.1",
 		"@types/punycode": "2.1.0",
 		"@types/sanitize-html": "2.9.0",
-		"@types/seedrandom": "3.0.5",
 		"@types/testing-library__jest-dom": "^5.14.6",
 		"@types/throttle-debounce": "5.0.0",
 		"@types/tinycolor2": "1.4.3",
diff --git a/packages/frontend/test/tsconfig.json b/packages/frontend/test/tsconfig.json
index 1424fdbdfb..42372eae7d 100644
--- a/packages/frontend/test/tsconfig.json
+++ b/packages/frontend/test/tsconfig.json
@@ -9,9 +9,9 @@
 		"noFallthroughCasesInSwitch": true,
 		"declaration": false,
 		"sourceMap": true,
-		"target": "es2021",
+		"target": "ES2022",
 		"module": "es2020",
-		"moduleResolution": "node",
+		"moduleResolution": "node16",
 		"allowSyntheticDefaultImports": true,
 		"removeComments": false,
 		"noLib": false,
@@ -27,7 +27,7 @@
 			"@/*": ["../src/*"]
 		},
 		"typeRoots": [
-			"../node_modules/@types",
+			"../node_modules/@types"
 		],
 		"lib": [
 			"esnext",
@@ -38,6 +38,6 @@
 	"compileOnSave": false,
 	"include": [
 		"./**/*.ts",
-		"../src/**/*.vue",
+		"../src/**/*.vue"
 	]
 }
diff --git a/packages/frontend/tsconfig.json b/packages/frontend/tsconfig.json
index e02acb6c5a..1dc5beb1a2 100644
--- a/packages/frontend/tsconfig.json
+++ b/packages/frontend/tsconfig.json
@@ -9,9 +9,9 @@
 		"noFallthroughCasesInSwitch": true,
 		"declaration": false,
 		"sourceMap": false,
-		"target": "es2021",
+		"target": "ES2022",
 		"module": "esnext",
-		"moduleResolution": "node",
+		"moduleResolution": "node16",
 		"removeComments": false,
 		"noLib": false,
 		"strict": true,
diff --git a/packages/misskey-js/tsconfig.json b/packages/misskey-js/tsconfig.json
index c679347fea..24e5af4c40 100644
--- a/packages/misskey-js/tsconfig.json
+++ b/packages/misskey-js/tsconfig.json
@@ -1,9 +1,9 @@
 {
 	"$schema": "http://json.schemastore.org/tsconfig",
 	"compilerOptions": {
-		"target": "es2022",
+		"target": "ES2022",
 		"module": "ES2020",
-		"moduleResolution": "node",
+		"moduleResolution": "node16",
 		"declaration": true,
 		"declarationMap": true,
 		"sourceMap": true,
diff --git a/packages/sw/tsconfig.json b/packages/sw/tsconfig.json
index 750aeff969..96e47db961 100644
--- a/packages/sw/tsconfig.json
+++ b/packages/sw/tsconfig.json
@@ -9,9 +9,9 @@
 		"noFallthroughCasesInSwitch": true,
 		"declaration": false,
 		"sourceMap": false,
-		"target": "es2021",
+		"target": "ES2022",
 		"module": "esnext",
-		"moduleResolution": "node",
+		"moduleResolution": "node16",
 		"removeComments": false,
 		"noLib": false,
 		"strict": true,
@@ -21,11 +21,11 @@
 		"isolatedModules": true,
 		"baseUrl": ".",
 		"paths": {
-			"@/*": ["./src/*"],
+			"@/*": ["./src/*"]
 		},
 		"typeRoots": [
 			"node_modules/@types",
-			"@types",
+			"@types"
 		],
 		"lib": [
 			"esnext",
diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml
index 893e5409b1..be9204ad76 100644
--- a/pnpm-lock.yaml
+++ b/pnpm-lock.yaml
@@ -153,8 +153,8 @@ importers:
         specifier: 4.1.0
         version: 4.1.0
       cacheable-lookup:
-        specifier: 6.1.0
-        version: 6.1.0
+        specifier: 7.0.0
+        version: 7.0.0
       cbor:
         specifier: 9.0.0
         version: 9.0.0
@@ -201,8 +201,8 @@ importers:
         specifier: 4.0.0
         version: 4.0.0
       got:
-        specifier: 12.6.0
-        version: 12.6.0
+        specifier: 13.0.0
+        version: 13.0.0
       happy-dom:
         specifier: 9.20.3
         version: 9.20.3
@@ -326,9 +326,6 @@ importers:
       sanitize-html:
         specifier: 2.11.0
         version: 2.11.0
-      seedrandom:
-        specifier: 3.0.5
-        version: 3.0.5
       semver:
         specifier: 7.5.3
         version: 7.5.3
@@ -526,6 +523,9 @@ importers:
       '@types/mime-types':
         specifier: 2.1.1
         version: 2.1.1
+      '@types/ms':
+        specifier: ^0.7.31
+        version: 0.7.31
       '@types/node':
         specifier: 20.3.1
         version: 20.3.1
@@ -748,9 +748,6 @@ importers:
       querystring:
         specifier: 0.2.1
         version: 0.2.1
-      rndstr:
-        specifier: 1.0.0
-        version: 1.0.0
       rollup:
         specifier: 3.25.1
         version: 3.25.1
@@ -763,9 +760,6 @@ importers:
       sass:
         specifier: 1.63.6
         version: 1.63.6
-      seedrandom:
-        specifier: 3.0.5
-        version: 3.0.5
       strict-event-emitter-types:
         specifier: 2.0.0
         version: 2.0.0
@@ -902,9 +896,6 @@ importers:
       '@types/sanitize-html':
         specifier: 2.9.0
         version: 2.9.0
-      '@types/seedrandom':
-        specifier: 3.0.5
-        version: 3.0.5
       '@types/testing-library__jest-dom':
         specifier: ^5.14.6
         version: 5.14.6
@@ -7879,10 +7870,6 @@ packages:
     resolution: {integrity: sha512-AnxLHewubLVzoF/A4qdxBGHCKifw8cY32iro3DQX9TPcetE95zBeVt3jnsvtvAUf1vwzMfwzp4t/L2yqPlnjkQ==}
     dev: false
 
-  /@types/seedrandom@3.0.5:
-    resolution: {integrity: sha512-kopEpYpFQvQdYsZkZVwht/0THHmTFFYXDaqV/lM45eweJ8kcGVDgZHs0RVTolSq55UPZNmjhKc9r7UvLu/mQQg==}
-    dev: true
-
   /@types/semver@7.5.0:
     resolution: {integrity: sha512-G8hZ6XJiHnuhQKR7ZmysCeJWE08o8T0AXtk5darsCaTVsYZhhgUrq53jizaR2FvsoeCwJhlmwTjkXBY5Pn/ZHw==}
     dev: true
@@ -9693,11 +9680,6 @@ packages:
     engines: {node: '>=10.6.0'}
     dev: false
 
-  /cacheable-lookup@6.1.0:
-    resolution: {integrity: sha512-KJ/Dmo1lDDhmW2XDPMo+9oiy/CeqosPguPCrgcVzKyZrL6pM1gU2GmPY/xo6OQPTUaA/c0kwHuywB4E6nmT9ww==}
-    engines: {node: '>=10.6.0'}
-    dev: false
-
   /cacheable-lookup@7.0.0:
     resolution: {integrity: sha512-+qJyx4xiKra8mZrcwhjMRMUhD5NR1R8esPkzIYxX96JiecFoxAXFuz/GpR3+ev4PE1WamHip78wV0vcmPQtp8w==}
     engines: {node: '>=14.16'}
@@ -12914,6 +12896,23 @@ packages:
       p-cancelable: 3.0.0
       responselike: 3.0.0
 
+  /got@13.0.0:
+    resolution: {integrity: sha512-XfBk1CxOOScDcMr9O1yKkNaQyy865NbYs+F7dr4H0LZMVgCj2Le59k6PqbNHoL5ToeaEQUYh6c6yMfVcc6SJxA==}
+    engines: {node: '>=16'}
+    dependencies:
+      '@sindresorhus/is': 5.3.0
+      '@szmarczak/http-timer': 5.0.1
+      cacheable-lookup: 7.0.0
+      cacheable-request: 10.2.8
+      decompress-response: 6.0.0
+      form-data-encoder: 2.1.4
+      get-stream: 6.0.1
+      http2-wrapper: 2.2.0
+      lowercase-keys: 3.0.0
+      p-cancelable: 3.0.0
+      responselike: 3.0.0
+    dev: false
+
   /graceful-fs@4.2.11:
     resolution: {integrity: sha512-RbJ5/jmFcNNCcDV5o9eTnBLJ/HszWV0P73bc+Ff4nS/rJj+YaS6IGyiOL0VoBYX+l1Wrl3k63h/KrH+nhJ0XvQ==}
 
@@ -17634,10 +17633,6 @@ packages:
     engines: {node: '>= 0.6'}
     dev: true
 
-  /rangestr@0.0.1:
-    resolution: {integrity: sha512-9CRCUX/w4+fNMzlYgA8GeJz7BZwBPwaGm3FhAm9Hi50k8wNy2CyiJQa8awygWJay87uVVCV0/FwbLcD6+/A9KQ==}
-    dev: false
-
   /ratelimiter@3.4.1:
     resolution: {integrity: sha512-5FJbRW/Jkkdk29ksedAfWFkQkhbUrMx3QJGwMKAypeIiQf4yrLW+gtPKZiaWt4zPrtw1uGufOjGO7UGM6VllsQ==}
     dev: false
@@ -18299,13 +18294,6 @@ packages:
     dependencies:
       glob: 7.2.3
 
-  /rndstr@1.0.0:
-    resolution: {integrity: sha512-3KN+BHTiHcsyW1qjRw3Xhms8TQfTIN4fUVgqqJpj6FnmuCnto5/lLyppSmGfdTmOiKDWeuXU4XPp58I9fsoWFQ==}
-    dependencies:
-      rangestr: 0.0.1
-      seedrandom: 2.4.2
-    dev: false
-
   /rollup@3.25.1:
     resolution: {integrity: sha512-tywOR+rwIt5m2ZAWSe5AIJcTat8vGlnPFAv15ycCrw33t6iFsXZ6mzHVFh2psSjxQPmI+xgzMZZizUAukBI4aQ==}
     engines: {node: '>=14.18.0', npm: '>=8.0.0'}
@@ -18425,10 +18413,6 @@ packages:
     resolution: {integrity: sha512-6aU+Rwsezw7VR8/nyvKTx8QpWH9FrcYiXXlqC4z5d5XQBDRqtbfsRjnwGyqbi3gddNtWHuEk9OANUotL26qKUw==}
     dev: false
 
-  /seedrandom@2.4.2:
-    resolution: {integrity: sha512-uQ72txMoObtuJooiBLSVs5Yu2e9d/lHQz0boaqHjW8runXB9vR8nFtaZV54wYii613N0C8ZqTBLsfwDhAdpvqQ==}
-    dev: false
-
   /seedrandom@3.0.5:
     resolution: {integrity: sha512-8OwmbklUNzwezjGInmZ+2clQmExQPvomqjL7LFqOYqtmuxRgQYqOD3mHaU+MvZn5FLUeVxVfQjwLZW/n/JFuqg==}
     dev: false

From d23ad8b5117a46067464d1b693ae8898d127d5fc Mon Sep 17 00:00:00 2001
From: Kagami Sascha Rosylight <saschanaz@outlook.com>
Date: Mon, 26 Jun 2023 03:09:12 +0200
Subject: [PATCH 14/17] =?UTF-8?q?fix(backend):=20API=E3=82=A8=E3=83=A9?=
 =?UTF-8?q?=E3=83=BC=E3=81=AEHTTP=20status=20code=E5=A4=89=E6=9B=B4=20(#11?=
 =?UTF-8?q?047)?=
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

---
 .../backend/src/server/api/ApiCallService.ts  |  8 +++-
 packages/backend/test/e2e/api.ts              | 44 ++++++++++++++++++-
 2 files changed, 49 insertions(+), 3 deletions(-)

diff --git a/packages/backend/src/server/api/ApiCallService.ts b/packages/backend/src/server/api/ApiCallService.ts
index dad1a4132a..45fb473763 100644
--- a/packages/backend/src/server/api/ApiCallService.ts
+++ b/packages/backend/src/server/api/ApiCallService.ts
@@ -83,7 +83,7 @@ export class ApiCallService implements OnApplicationShutdown {
 			}
 		}).catch(err => {
 			if (err instanceof AuthenticationError) {
-				this.send(reply, 403, new ApiError({
+				this.send(reply, 401, new ApiError({
 					message: 'Authentication failed. Please ensure your token is correct.',
 					code: 'AUTHENTICATION_FAILED',
 					id: 'b0a7f5f8-dc2f-4171-b91f-de88ad238e14',
@@ -137,7 +137,7 @@ export class ApiCallService implements OnApplicationShutdown {
 			}
 		}).catch(err => {
 			if (err instanceof AuthenticationError) {
-				this.send(reply, 403, new ApiError({
+				this.send(reply, 401, new ApiError({
 					message: 'Authentication failed. Please ensure your token is correct.',
 					code: 'AUTHENTICATION_FAILED',
 					id: 'b0a7f5f8-dc2f-4171-b91f-de88ad238e14',
@@ -278,6 +278,7 @@ export class ApiCallService implements OnApplicationShutdown {
 				throw new ApiError({
 					message: 'You are not assigned to a moderator role.',
 					code: 'ROLE_PERMISSION_DENIED',
+					kind: 'permission',
 					id: 'd33d5333-db36-423d-a8f9-1a2b9549da41',
 				});
 			}
@@ -285,6 +286,7 @@ export class ApiCallService implements OnApplicationShutdown {
 				throw new ApiError({
 					message: 'You are not assigned to an administrator role.',
 					code: 'ROLE_PERMISSION_DENIED',
+					kind: 'permission',
 					id: 'c3d38592-54c0-429d-be96-5636b0431a61',
 				});
 			}
@@ -296,6 +298,7 @@ export class ApiCallService implements OnApplicationShutdown {
 				throw new ApiError({
 					message: 'You are not assigned to a required role.',
 					code: 'ROLE_PERMISSION_DENIED',
+					kind: 'permission',
 					id: '7f86f06f-7e15-4057-8561-f4b6d4ac755a',
 				});
 			}
@@ -305,6 +308,7 @@ export class ApiCallService implements OnApplicationShutdown {
 			throw new ApiError({
 				message: 'Your app does not have the necessary permissions to use this endpoint.',
 				code: 'PERMISSION_DENIED',
+				kind: 'permission',
 				id: '1370e5b7-d4eb-4566-bb1d-7748ee6a1838',
 			});
 		}
diff --git a/packages/backend/test/e2e/api.ts b/packages/backend/test/e2e/api.ts
index 194ded7e8b..4b9167b6b1 100644
--- a/packages/backend/test/e2e/api.ts
+++ b/packages/backend/test/e2e/api.ts
@@ -1,7 +1,7 @@
 process.env.NODE_ENV = 'test';
 
 import * as assert from 'assert';
-import { signup, api, startServer } from '../utils.js';
+import { signup, api, startServer, successfulApiCall, failedApiCall } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
 import type * as misskey from 'misskey-js';
 
@@ -81,4 +81,46 @@ describe('API', () => {
 			assert.strictEqual(res.body.nullableDefault, 'hello');
 		});
 	});
+
+	test('管理者専用のAPIのアクセス制限', async () => {
+		// aliceは管理者、APIを使える
+		await successfulApiCall({
+			endpoint: '/admin/get-index-stats',
+			parameters: {},
+			user: alice,
+		});
+
+		// bobは一般ユーザーだからダメ
+		await failedApiCall({
+			endpoint: '/admin/get-index-stats',
+			parameters: {},
+			user: bob,
+		}, {
+			status: 403,
+			code: 'ROLE_PERMISSION_DENIED',
+			id: 'c3d38592-54c0-429d-be96-5636b0431a61',
+		});
+
+		// publicアクセスももちろんダメ
+		await failedApiCall({
+			endpoint: '/admin/get-index-stats',
+			parameters: {},
+			user: undefined,
+		}, {
+			status: 401,
+			code: 'CREDENTIAL_REQUIRED',
+			id: '1384574d-a912-4b81-8601-c7b1c4085df1',
+		});
+
+		// ごまがしもダメ
+		await failedApiCall({
+			endpoint: '/admin/get-index-stats',
+			parameters: {},
+			user: { token: 'tsukawasete' },
+		}, {
+			status: 401,
+			code: 'AUTHENTICATION_FAILED',
+			id: 'b0a7f5f8-dc2f-4171-b91f-de88ad238e14',
+		});
+	});
 });

From 58a898dfe0631e70e9fcac988c5e207e9bd76346 Mon Sep 17 00:00:00 2001
From: Yuriha <121590760+yuriha-chan@users.noreply.github.com>
Date: Mon, 26 Jun 2023 10:45:14 +0900
Subject: [PATCH 15/17] Fix offscreencanvas undefined (#11017)

* Suppress ReferenceError on some environments (i.e. older iOS)

* fix

* fix

* lint

* adopt suggestion by acid-chicken
---
 packages/frontend/src/workers/test-webgl2.ts | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/packages/frontend/src/workers/test-webgl2.ts b/packages/frontend/src/workers/test-webgl2.ts
index 4769524d9c..8f13c57cae 100644
--- a/packages/frontend/src/workers/test-webgl2.ts
+++ b/packages/frontend/src/workers/test-webgl2.ts
@@ -1,5 +1,5 @@
-const canvas = new OffscreenCanvas(1, 1);
-const gl = canvas.getContext('webgl2');
+const canvas = globalThis.OffscreenCanvas && new OffscreenCanvas(1, 1);
+const gl = canvas?.getContext('webgl2');
 if (gl) {
     postMessage({ result: true });
 } else {

From d48172e9d13cfc907b746760e7ac5f9e902ddcf1 Mon Sep 17 00:00:00 2001
From: Kagami Sascha Rosylight <saschanaz@outlook.com>
Date: Tue, 27 Jun 2023 01:07:20 +0200
Subject: [PATCH 16/17] refactor(backend/test): add `interface UserToken`
 (#11050)

---
 packages/backend/test/utils.ts | 36 ++++++++++++++++++----------------
 1 file changed, 19 insertions(+), 17 deletions(-)

diff --git a/packages/backend/test/utils.ts b/packages/backend/test/utils.ts
index eeb1b19daa..8583f024cb 100644
--- a/packages/backend/test/utils.ts
+++ b/packages/backend/test/utils.ts
@@ -13,14 +13,16 @@ import type * as misskey from 'misskey-js';
 
 export { server as startServer } from '@/boot/common.js';
 
+interface UserToken { token: string }
+
 const config = loadConfig();
 export const port = config.port;
 
-export const cookie = (me: any): string => {
+export const cookie = (me: UserToken): string => {
 	return `token=${me.token};`;
 };
 
-export const api = async (endpoint: string, params: any, me?: any) => {
+export const api = async (endpoint: string, params: any, me?: UserToken) => {
 	const normalized = endpoint.replace(/^\//, '');
 	return await request(`api/${normalized}`, params, me);
 };
@@ -28,7 +30,7 @@ export const api = async (endpoint: string, params: any, me?: any) => {
 export type ApiRequest = {
 	endpoint: string,
 	parameters: object,
-	user: object | undefined,
+	user: UserToken | undefined,
 };
 
 export const successfulApiCall = async <T, >(request: ApiRequest, assertion: {
@@ -55,7 +57,7 @@ export const failedApiCall = async <T, >(request: ApiRequest, assertion: {
 	return res.body;
 };
 
-const request = async (path: string, params: any, me?: any): Promise<{ body: any, status: number }> => {
+const request = async (path: string, params: any, me?: UserToken): Promise<{ body: any, status: number }> => {
 	const auth = me ? {
 		i: me.token,
 	} : {};
@@ -94,7 +96,7 @@ export const signup = async (params?: Partial<misskey.Endpoints['signup']['req']
 	return res.body;
 };
 
-export const post = async (user: any, params?: misskey.Endpoints['notes/create']['req']): Promise<misskey.entities.Note> => {
+export const post = async (user: UserToken, params?: misskey.Endpoints['notes/create']['req']): Promise<misskey.entities.Note> => {
 	const q = params;
 
 	const res = await api('notes/create', q, user);
@@ -117,21 +119,21 @@ export const hiddenNote = (note: any): any => {
 	return temp;
 };
 
-export const react = async (user: any, note: any, reaction: string): Promise<any> => {
+export const react = async (user: UserToken, note: any, reaction: string): Promise<any> => {
 	await api('notes/reactions/create', {
 		noteId: note.id,
 		reaction: reaction,
 	}, user);
 };
 
-export const userList = async (user: any, userList: any = {}): Promise<any> => {
+export const userList = async (user: UserToken, userList: any = {}): Promise<any> => {
 	const res = await api('users/lists/create', {
 		name: 'test',
 	}, user);
 	return res.body;
 };
 
-export const page = async (user: any, page: any = {}): Promise<any> => {
+export const page = async (user: UserToken, page: any = {}): Promise<any> => {
 	const res = await api('pages/create', {
 		alignCenter: false,
 		content: [
@@ -154,7 +156,7 @@ export const page = async (user: any, page: any = {}): Promise<any> => {
 	return res.body;
 };
 
-export const play = async (user: any, play: any = {}): Promise<any> => {
+export const play = async (user: UserToken, play: any = {}): Promise<any> => {
 	const res = await api('flash/create', {
 		permissions: [],
 		script: 'test',
@@ -165,7 +167,7 @@ export const play = async (user: any, play: any = {}): Promise<any> => {
 	return res.body;
 };
 
-export const clip = async (user: any, clip: any = {}): Promise<any> => {
+export const clip = async (user: UserToken, clip: any = {}): Promise<any> => {
 	const res = await api('clips/create', {
 		description: null,
 		isPublic: true,
@@ -175,7 +177,7 @@ export const clip = async (user: any, clip: any = {}): Promise<any> => {
 	return res.body;
 };
 
-export const galleryPost = async (user: any, channel: any = {}): Promise<any> => {
+export const galleryPost = async (user: UserToken, channel: any = {}): Promise<any> => {
 	const res = await api('gallery/posts/create', {
 		description: null,
 		fileIds: [],
@@ -186,7 +188,7 @@ export const galleryPost = async (user: any, channel: any = {}): Promise<any> =>
 	return res.body;
 };
 
-export const channel = async (user: any, channel: any = {}): Promise<any> => {
+export const channel = async (user: UserToken, channel: any = {}): Promise<any> => {
 	const res = await api('channels/create', {
 		bannerId: null,
 		description: null,
@@ -196,7 +198,7 @@ export const channel = async (user: any, channel: any = {}): Promise<any> => {
 	return res.body;
 };
 
-export const role = async (user: any, role: any = {}, policies: any = {}): Promise<any> => {
+export const role = async (user: UserToken, role: any = {}, policies: any = {}): Promise<any> => {
 	const res = await api('admin/roles/create', {
 		asBadge: false,
 		canEditMembersByModerator: false,
@@ -239,7 +241,7 @@ interface UploadOptions {
  * Upload file
  * @param user User
  */
-export const uploadFile = async (user: any, { path, name, blob }: UploadOptions = {}): Promise<any> => {
+export const uploadFile = async (user: UserToken, { path, name, blob }: UploadOptions = {}): Promise<any> => {
 	const absPath = path == null
 		? new URL('resources/Lenna.jpg', import.meta.url)
 		: isAbsolute(path.toString())
@@ -268,7 +270,7 @@ export const uploadFile = async (user: any, { path, name, blob }: UploadOptions
 	};
 };
 
-export const uploadUrl = async (user: any, url: string) => {
+export const uploadUrl = async (user: UserToken, url: string) => {
 	let file: any;
 	const marker = Math.random().toString();
 
@@ -290,7 +292,7 @@ export const uploadUrl = async (user: any, url: string) => {
 	return file;
 };
 
-export function connectStream(user: any, channel: string, listener: (message: Record<string, any>) => any, params?: any): Promise<WebSocket> {
+export function connectStream(user: UserToken, channel: string, listener: (message: Record<string, any>) => any, params?: any): Promise<WebSocket> {
 	return new Promise((res, rej) => {
 		const ws = new WebSocket(`ws://127.0.0.1:${port}/streaming?i=${user.token}`);
 
@@ -317,7 +319,7 @@ export function connectStream(user: any, channel: string, listener: (message: Re
 	});
 }
 
-export const waitFire = async (user: any, channel: string, trgr: () => any, cond: (msg: Record<string, any>) => boolean, params?: any) => {
+export const waitFire = async (user: UserToken, channel: string, trgr: () => any, cond: (msg: Record<string, any>) => boolean, params?: any) => {
 	return new Promise<boolean>(async (res, rej) => {
 		let timer: NodeJS.Timeout | null = null;
 

From 1b1f82a2e26ddabd8bdf400760a817acbf290157 Mon Sep 17 00:00:00 2001
From: Kagami Sascha Rosylight <saschanaz@outlook.com>
Date: Wed, 28 Jun 2023 06:37:13 +0200
Subject: [PATCH 17/17] feat(backend): accept OAuth bearer token (#11052)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

* feat(backend): accept OAuth bearer token

* refactor

* Update packages/backend/src/server/api/ApiCallService.ts

Co-authored-by: Acid Chicken (硫酸鶏) <root@acid-chicken.com>

* Update packages/backend/src/server/api/ApiCallService.ts

Co-authored-by: Acid Chicken (硫酸鶏) <root@acid-chicken.com>

* fix

* kind: permission for account moved error

* also for suspended error

* Update packages/backend/src/server/api/StreamingApiServerService.ts

Co-authored-by: Acid Chicken (硫酸鶏) <root@acid-chicken.com>

---------

Co-authored-by: Acid Chicken (硫酸鶏) <root@acid-chicken.com>
Co-authored-by: syuilo <Syuilotan@yahoo.co.jp>
---
 .../backend/src/server/api/ApiCallService.ts  | 81 +++++++++------
 .../server/api/StreamingApiServerService.ts   | 14 ++-
 packages/backend/test/e2e/api.ts              | 99 ++++++++++++++++++-
 packages/backend/test/utils.ts                | 57 ++++++++---
 packages/misskey-js/etc/misskey-js.api.md     | 12 ++-
 packages/misskey-js/src/api.types.ts          | 11 ++-
 6 files changed, 222 insertions(+), 52 deletions(-)

diff --git a/packages/backend/src/server/api/ApiCallService.ts b/packages/backend/src/server/api/ApiCallService.ts
index 45fb473763..09e3724394 100644
--- a/packages/backend/src/server/api/ApiCallService.ts
+++ b/packages/backend/src/server/api/ApiCallService.ts
@@ -53,44 +53,72 @@ export class ApiCallService implements OnApplicationShutdown {
 		}, 1000 * 60 * 60);
 	}
 
+	#sendApiError(reply: FastifyReply, err: ApiError): void {
+		let statusCode = err.httpStatusCode;
+		if (err.httpStatusCode === 401) {
+			reply.header('WWW-Authenticate', 'Bearer realm="Misskey"');
+		} else if (err.kind === 'client') {
+			reply.header('WWW-Authenticate', `Bearer realm="Misskey", error="invalid_request", error_description="${err.message}"`);
+			statusCode = statusCode ?? 400;
+		} else if (err.kind === 'permission') {
+			// (ROLE_PERMISSION_DENIEDは関係ない)
+			if (err.code === 'PERMISSION_DENIED') {
+				reply.header('WWW-Authenticate', `Bearer realm="Misskey", error="insufficient_scope", error_description="${err.message}"`);
+			}
+			statusCode = statusCode ?? 403;
+		} else if (!statusCode) {
+			statusCode = 500;
+		}
+		this.send(reply, statusCode, err);
+	}
+
+	#sendAuthenticationError(reply: FastifyReply, err: unknown): void {
+		if (err instanceof AuthenticationError) {
+			const message = 'Authentication failed. Please ensure your token is correct.';
+			reply.header('WWW-Authenticate', `Bearer realm="Misskey", error="invalid_token", error_description="${message}"`);
+			this.send(reply, 401, new ApiError({
+				message: 'Authentication failed. Please ensure your token is correct.',
+				code: 'AUTHENTICATION_FAILED',
+				id: 'b0a7f5f8-dc2f-4171-b91f-de88ad238e14',
+			}));
+		} else {
+			this.send(reply, 500, new ApiError());
+		}
+	}
+
 	@bindThis
 	public handleRequest(
 		endpoint: IEndpoint & { exec: any },
 		request: FastifyRequest<{ Body: Record<string, unknown> | undefined, Querystring: Record<string, unknown> }>,
 		reply: FastifyReply,
-	) {
+	): void {
 		const body = request.method === 'GET'
 			? request.query
 			: request.body;
 
-		const token = body?.['i'];
+		// https://datatracker.ietf.org/doc/html/rfc6750.html#section-2.1 (case sensitive)
+		const token = request.headers.authorization?.startsWith('Bearer ')
+			? request.headers.authorization.slice(7)
+			: body?.['i'];
 		if (token != null && typeof token !== 'string') {
 			reply.code(400);
 			return;
 		}
 		this.authenticateService.authenticate(token).then(([user, app]) => {
 			this.call(endpoint, user, app, body, null, request).then((res) => {
-				if (request.method === 'GET' && endpoint.meta.cacheSec && !body?.['i'] && !user) {
+				if (request.method === 'GET' && endpoint.meta.cacheSec && !token && !user) {
 					reply.header('Cache-Control', `public, max-age=${endpoint.meta.cacheSec}`);
 				}
 				this.send(reply, res);
 			}).catch((err: ApiError) => {
-				this.send(reply, err.httpStatusCode ? err.httpStatusCode : err.kind === 'client' ? 400 : err.kind === 'permission' ? 403 : 500, err);
+				this.#sendApiError(reply, err);
 			});
 
 			if (user) {
 				this.logIp(request, user);
 			}
 		}).catch(err => {
-			if (err instanceof AuthenticationError) {
-				this.send(reply, 401, new ApiError({
-					message: 'Authentication failed. Please ensure your token is correct.',
-					code: 'AUTHENTICATION_FAILED',
-					id: 'b0a7f5f8-dc2f-4171-b91f-de88ad238e14',
-				}));
-			} else {
-				this.send(reply, 500, new ApiError());
-			}
+			this.#sendAuthenticationError(reply, err);
 		});
 	}
 
@@ -99,7 +127,7 @@ export class ApiCallService implements OnApplicationShutdown {
 		endpoint: IEndpoint & { exec: any },
 		request: FastifyRequest<{ Body: Record<string, unknown>, Querystring: Record<string, unknown> }>,
 		reply: FastifyReply,
-	) {
+	): Promise<void> {
 		const multipartData = await request.file().catch(() => {
 			/* Fastify throws if the remote didn't send multipart data. Return 400 below. */
 		});
@@ -117,7 +145,10 @@ export class ApiCallService implements OnApplicationShutdown {
 			fields[k] = typeof v === 'object' && 'value' in v ? v.value : undefined;
 		}
 
-		const token = fields['i'];
+		// https://datatracker.ietf.org/doc/html/rfc6750.html#section-2.1 (case sensitive)
+		const token = request.headers.authorization?.startsWith('Bearer ')
+			? request.headers.authorization.slice(7)
+			: fields['i'];
 		if (token != null && typeof token !== 'string') {
 			reply.code(400);
 			return;
@@ -129,22 +160,14 @@ export class ApiCallService implements OnApplicationShutdown {
 			}, request).then((res) => {
 				this.send(reply, res);
 			}).catch((err: ApiError) => {
-				this.send(reply, err.httpStatusCode ? err.httpStatusCode : err.kind === 'client' ? 400 : err.kind === 'permission' ? 403 : 500, err);
+				this.#sendApiError(reply, err);
 			});
 
 			if (user) {
 				this.logIp(request, user);
 			}
 		}).catch(err => {
-			if (err instanceof AuthenticationError) {
-				this.send(reply, 401, new ApiError({
-					message: 'Authentication failed. Please ensure your token is correct.',
-					code: 'AUTHENTICATION_FAILED',
-					id: 'b0a7f5f8-dc2f-4171-b91f-de88ad238e14',
-				}));
-			} else {
-				this.send(reply, 500, new ApiError());
-			}
+			this.#sendAuthenticationError(reply, err);
 		});
 	}
 
@@ -213,7 +236,7 @@ export class ApiCallService implements OnApplicationShutdown {
 		}
 
 		if (ep.meta.limit) {
-		// koa will automatically load the `X-Forwarded-For` header if `proxy: true` is configured in the app.
+			// koa will automatically load the `X-Forwarded-For` header if `proxy: true` is configured in the app.
 			let limitActor: string;
 			if (user) {
 				limitActor = user.id;
@@ -255,8 +278,8 @@ export class ApiCallService implements OnApplicationShutdown {
 				throw new ApiError({
 					message: 'Your account has been suspended.',
 					code: 'YOUR_ACCOUNT_SUSPENDED',
+					kind: 'permission',
 					id: 'a8c724b3-6e9c-4b46-b1a8-bc3ed6258370',
-					httpStatusCode: 403,
 				});
 			}
 		}
@@ -266,8 +289,8 @@ export class ApiCallService implements OnApplicationShutdown {
 				throw new ApiError({
 					message: 'You have moved your account.',
 					code: 'YOUR_ACCOUNT_MOVED',
+					kind: 'permission',
 					id: '56f20ec9-fd06-4fa5-841b-edd6d7d4fa31',
-					httpStatusCode: 403,
 				});
 			}
 		}
@@ -321,7 +344,7 @@ export class ApiCallService implements OnApplicationShutdown {
 					try {
 						data[k] = JSON.parse(data[k]);
 					} catch (e) {
-						throw	new ApiError({
+						throw new ApiError({
 							message: 'Invalid param.',
 							code: 'INVALID_PARAM',
 							id: '0b5f1631-7c1a-41a6-b399-cce335f34d85',
diff --git a/packages/backend/src/server/api/StreamingApiServerService.ts b/packages/backend/src/server/api/StreamingApiServerService.ts
index 8f2e51d584..4a0342d2b4 100644
--- a/packages/backend/src/server/api/StreamingApiServerService.ts
+++ b/packages/backend/src/server/api/StreamingApiServerService.ts
@@ -58,11 +58,21 @@ export class StreamingApiServerService {
 			let user: LocalUser | null = null;
 			let app: AccessToken | null = null;
 
+			// https://datatracker.ietf.org/doc/html/rfc6750.html#section-2.1
+			// Note that the standard WHATWG WebSocket API does not support setting any headers,
+			// but non-browser apps may still be able to set it.
+			const token = request.headers.authorization?.startsWith('Bearer ')
+				? request.headers.authorization.slice(7)
+				: q.get('i');
+
 			try {
-				[user, app] = await this.authenticateService.authenticate(q.get('i'));
+				[user, app] = await this.authenticateService.authenticate(token);
 			} catch (e) {
 				if (e instanceof AuthenticationError) {
-					socket.write('HTTP/1.1 401 Unauthorized\r\n\r\n');
+					socket.write([
+						'HTTP/1.1 401 Unauthorized',
+						'WWW-Authenticate: Bearer realm="Misskey", error="invalid_token", error_description="Failed to authenticate"',
+					].join('\r\n') + '\r\n\r\n');
 				} else {
 					socket.write('HTTP/1.1 500 Internal Server Error\r\n\r\n');
 				}
diff --git a/packages/backend/test/e2e/api.ts b/packages/backend/test/e2e/api.ts
index 4b9167b6b1..c6beec4f88 100644
--- a/packages/backend/test/e2e/api.ts
+++ b/packages/backend/test/e2e/api.ts
@@ -1,9 +1,10 @@
 process.env.NODE_ENV = 'test';
 
 import * as assert from 'assert';
-import { signup, api, startServer, successfulApiCall, failedApiCall } from '../utils.js';
+import { signup, api, startServer, successfulApiCall, failedApiCall, uploadFile, waitFire, connectStream } from '../utils.js';
 import type { INestApplicationContext } from '@nestjs/common';
 import type * as misskey from 'misskey-js';
+import { IncomingMessage } from 'http';
 
 describe('API', () => {
 	let app: INestApplicationContext;
@@ -123,4 +124,100 @@ describe('API', () => {
 			id: 'b0a7f5f8-dc2f-4171-b91f-de88ad238e14',
 		});
 	});
+
+	describe('Authentication header', () => {
+		test('一般リクエスト', async () => {
+			await successfulApiCall({
+				endpoint: '/admin/get-index-stats',
+				parameters: {},
+				user: {
+					token: alice.token,
+					bearer: true,
+				},
+			});
+		});
+
+		test('multipartリクエスト', async () => {
+			const result = await uploadFile({
+				token: alice.token,
+				bearer: true,
+			});
+			assert.strictEqual(result.status, 200);
+		});
+
+		test('streaming', async () => {
+			const fired = await waitFire(
+				{
+					token: alice.token,
+					bearer: true,
+				},
+				'homeTimeline',
+				() => api('notes/create', { text: 'foo' }, alice),
+				msg => msg.type === 'note' && msg.body.text === 'foo',
+			);
+			assert.strictEqual(fired, true);
+		});
+	});
+
+	describe('tokenエラー応答でWWW-Authenticate headerを送る', () => {
+		describe('invalid_token', () => {
+			test('一般リクエスト', async () => {
+				const result = await api('/admin/get-index-stats', {}, {
+					token: 'syuilo',
+					bearer: true,
+				});
+				assert.strictEqual(result.status, 401);
+				assert.ok(result.headers.get('WWW-Authenticate')?.startsWith('Bearer realm="Misskey", error="invalid_token", error_description'));
+			});
+
+			test('multipartリクエスト', async () => {
+				const result = await uploadFile({
+					token: 'syuilo',
+					bearer: true,
+				});
+				assert.strictEqual(result.status, 401);
+				assert.ok(result.headers.get('WWW-Authenticate')?.startsWith('Bearer realm="Misskey", error="invalid_token", error_description'));
+			});
+
+			test('streaming', async () => {
+				await assert.rejects(connectStream(
+					{
+						token: 'syuilo',
+						bearer: true,
+					},
+					'homeTimeline',
+					() => { },
+				), (err: IncomingMessage) => {
+					assert.strictEqual(err.statusCode, 401);
+					assert.ok(err.headers['www-authenticate']?.startsWith('Bearer realm="Misskey", error="invalid_token", error_description'));
+					return true;
+				});
+			});
+		});
+
+		describe('tokenがないとrealmだけおくる', () => {
+			test('一般リクエスト', async () => {
+				const result = await api('/admin/get-index-stats', {});
+				assert.strictEqual(result.status, 401);
+				assert.strictEqual(result.headers.get('WWW-Authenticate'), 'Bearer realm="Misskey"');
+			});
+
+			test('multipartリクエスト', async () => {
+				const result = await uploadFile();
+				assert.strictEqual(result.status, 401);
+				assert.strictEqual(result.headers.get('WWW-Authenticate'), 'Bearer realm="Misskey"');
+			});
+		});
+
+		test('invalid_request', async () => {
+			const result = await api('/notes/create', { text: true }, {
+				token: alice.token,
+				bearer: true,
+			});
+			assert.strictEqual(result.status, 400);
+			assert.ok(result.headers.get('WWW-Authenticate')?.startsWith('Bearer realm="Misskey", error="invalid_request", error_description'));
+		});
+
+		// TODO: insufficient_scope test (authテストが全然なくて書けない)
+	});
 });
diff --git a/packages/backend/test/utils.ts b/packages/backend/test/utils.ts
index 8583f024cb..48947072e3 100644
--- a/packages/backend/test/utils.ts
+++ b/packages/backend/test/utils.ts
@@ -2,7 +2,7 @@ import * as assert from 'node:assert';
 import { readFile } from 'node:fs/promises';
 import { isAbsolute, basename } from 'node:path';
 import { inspect } from 'node:util';
-import WebSocket from 'ws';
+import WebSocket, { ClientOptions } from 'ws';
 import fetch, { Blob, File, RequestInit } from 'node-fetch';
 import { DataSource } from 'typeorm';
 import { JSDOM } from 'jsdom';
@@ -13,7 +13,10 @@ import type * as misskey from 'misskey-js';
 
 export { server as startServer } from '@/boot/common.js';
 
-interface UserToken { token: string }
+interface UserToken {
+	token: string;
+	bearer?: boolean;
+}
 
 const config = loadConfig();
 export const port = config.port;
@@ -57,27 +60,33 @@ export const failedApiCall = async <T, >(request: ApiRequest, assertion: {
 	return res.body;
 };
 
-const request = async (path: string, params: any, me?: UserToken): Promise<{ body: any, status: number }> => {
-	const auth = me ? {
-		i: me.token,
-	} : {};
+const request = async (path: string, params: any, me?: UserToken): Promise<{ status: number, headers: Headers, body: any }> => {
+	const bodyAuth: Record<string, string> = {};
+	const headers: Record<string, string> = {
+		'Content-Type': 'application/json',
+	};
+
+	if (me?.bearer) {
+		headers.Authorization = `Bearer ${me.token}`;
+	} else if (me) {
+		bodyAuth.i = me.token;
+	}
 
 	const res = await relativeFetch(path, {
 		method: 'POST',
-		headers: {
-			'Content-Type': 'application/json',
-		},
-		body: JSON.stringify(Object.assign(auth, params)),
+		headers,
+		body: JSON.stringify(Object.assign(bodyAuth, params)),
 		redirect: 'manual',
 	});
 
-	const status = res.status;
 	const body = res.headers.get('content-type') === 'application/json; charset=utf-8'
 		? await res.json()
 		: null;
 
 	return {
-		body, status,
+		status: res.status,
+		headers: res.headers,
+		body,
 	};
 };
 
@@ -241,7 +250,7 @@ interface UploadOptions {
  * Upload file
  * @param user User
  */
-export const uploadFile = async (user: UserToken, { path, name, blob }: UploadOptions = {}): Promise<any> => {
+export const uploadFile = async (user?: UserToken, { path, name, blob }: UploadOptions = {}): Promise<{ status: number, headers: Headers, body: misskey.Endpoints['drive/files/create']['res'] | null }> => {
 	const absPath = path == null
 		? new URL('resources/Lenna.jpg', import.meta.url)
 		: isAbsolute(path.toString())
@@ -249,7 +258,6 @@ export const uploadFile = async (user: UserToken, { path, name, blob }: UploadOp
 			: new URL(path, new URL('resources/', import.meta.url));
 
 	const formData = new FormData();
-	formData.append('i', user.token);
 	formData.append('file', blob ??
 		new File([await readFile(absPath)], basename(absPath.toString())));
 	formData.append('force', 'true');
@@ -257,15 +265,24 @@ export const uploadFile = async (user: UserToken, { path, name, blob }: UploadOp
 		formData.append('name', name);
 	}
 
+	const headers: Record<string, string> = {};
+	if (user?.bearer) {
+		headers.Authorization = `Bearer ${user.token}`;
+	} else if (user) {
+		formData.append('i', user.token);
+	}
+
 	const res = await relativeFetch('api/drive/files/create', {
 		method: 'POST',
 		body: formData,
+		headers,
 	});
 
-	const body = res.status !== 204 ? await res.json() : null;
+	const body = res.status !== 204 ? await res.json() as misskey.Endpoints['drive/files/create']['res'] : null;
 
 	return {
 		status: res.status,
+		headers: res.headers,
 		body,
 	};
 };
@@ -294,8 +311,16 @@ export const uploadUrl = async (user: UserToken, url: string) => {
 
 export function connectStream(user: UserToken, channel: string, listener: (message: Record<string, any>) => any, params?: any): Promise<WebSocket> {
 	return new Promise((res, rej) => {
-		const ws = new WebSocket(`ws://127.0.0.1:${port}/streaming?i=${user.token}`);
+		const url = new URL(`ws://127.0.0.1:${port}/streaming`);
+		const options: ClientOptions = {};
+		if (user.bearer) {
+			options.headers = { Authorization: `Bearer ${user.token}` };
+		} else {
+			url.searchParams.set('i', user.token);
+		}
+		const ws = new WebSocket(url, options);
 
+		ws.on('unexpected-response', (req, res) => rej(res));
 		ws.on('open', () => {
 			ws.on('message', data => {
 				const msg = JSON.parse(data.toString());
diff --git a/packages/misskey-js/etc/misskey-js.api.md b/packages/misskey-js/etc/misskey-js.api.md
index 5f292148ae..c9b3fd6056 100644
--- a/packages/misskey-js/etc/misskey-js.api.md
+++ b/packages/misskey-js/etc/misskey-js.api.md
@@ -960,8 +960,14 @@ export type Endpoints = {
         res: TODO;
     };
     'drive/files/create': {
-        req: TODO;
-        res: TODO;
+        req: {
+            folderId?: string;
+            name?: string;
+            comment?: string;
+            isSentisive?: boolean;
+            force?: boolean;
+        };
+        res: DriveFile;
     };
     'drive/files/delete': {
         req: {
@@ -2750,7 +2756,7 @@ type UserSorting = '+follower' | '-follower' | '+createdAt' | '-createdAt' | '+u
 //
 // src/api.types.ts:16:32 - (ae-forgotten-export) The symbol "TODO" needs to be exported by the entry point index.d.ts
 // src/api.types.ts:18:25 - (ae-forgotten-export) The symbol "NoParams" needs to be exported by the entry point index.d.ts
-// src/api.types.ts:611:18 - (ae-forgotten-export) The symbol "ShowUserReq" needs to be exported by the entry point index.d.ts
+// src/api.types.ts:620:18 - (ae-forgotten-export) The symbol "ShowUserReq" needs to be exported by the entry point index.d.ts
 // src/streaming.types.ts:33:4 - (ae-forgotten-export) The symbol "FIXME" needs to be exported by the entry point index.d.ts
 
 // (No @packageDocumentation comment for this package)
diff --git a/packages/misskey-js/src/api.types.ts b/packages/misskey-js/src/api.types.ts
index 293e0043b7..93f327e67e 100644
--- a/packages/misskey-js/src/api.types.ts
+++ b/packages/misskey-js/src/api.types.ts
@@ -262,7 +262,16 @@ export type Endpoints = {
 	'drive/files': { req: { folderId?: DriveFolder['id'] | null; type?: DriveFile['type'] | null; limit?: number; sinceId?: DriveFile['id']; untilId?: DriveFile['id']; }; res: DriveFile[]; };
 	'drive/files/attached-notes': { req: TODO; res: TODO; };
 	'drive/files/check-existence': { req: TODO; res: TODO; };
-	'drive/files/create': { req: TODO; res: TODO; };
+	'drive/files/create': {
+		req: {
+			folderId?: string,
+			name?: string,
+			comment?: string,
+			isSentisive?: boolean,
+			force?: boolean,
+		};
+		res: DriveFile;
+	};
 	'drive/files/delete': { req: { fileId: DriveFile['id']; }; res: null; };
 	'drive/files/find-by-hash': { req: TODO; res: TODO; };
 	'drive/files/find': { req: { name: string; folderId?: DriveFolder['id'] | null; }; res: DriveFile[]; };