From ab4c0194062381da65389eba9e67210bd06f79a7 Mon Sep 17 00:00:00 2001 From: Bradley Shellnut Date: Thu, 22 Aug 2024 19:26:22 -0700 Subject: [PATCH] Fixing loading the wishlist and collection on the main landing page and getting your wishlist by id. --- biome.json | 5 +- package.json | 17 +- pnpm-lock.yaml | 463 ++++++++++-------- src/app.d.ts | 9 +- src/hooks.server.ts | 2 +- src/lib/dtos/id-params.dto.ts | 5 + .../api/controllers/collection.controller.ts | 31 ++ .../server/api/controllers/iam.controller.ts | 78 +-- .../server/api/controllers/user.controller.ts | 8 +- .../api/controllers/wishlist.controller.ts | 31 ++ src/lib/server/api/index.ts | 4 + .../server/api/infrastructure/auth/lucia.ts | 8 +- .../database/schemas/collections.schema.ts | 25 + .../database/schemas/users.schemas.ts | 24 + .../database/tables/users.table.ts | 2 +- .../repositories/collections.repository.ts | 26 +- .../api/repositories/wishlists.repository.ts | 28 +- .../api/services/collections.service.ts | 16 + src/lib/server/api/services/iam.service.ts | 17 +- src/lib/server/api/services/users.service.ts | 4 + .../server/api/services/wishlists.service.ts | 8 + src/lib/utils/api.ts | 2 +- src/lib/zodValidation.ts | 2 +- .../(app)/(protected)/profile/+page.server.ts | 44 +- .../{[id] => [cuid]}/+page.server.ts | 28 +- .../wishlists/{[id] => [cuid]}/+page.svelte | 0 src/routes/(app)/+page.server.ts | 38 +- src/routes/(auth)/+layout.svelte | 34 +- src/routes/(auth)/login/+page.server.ts | 162 +++--- src/routes/(auth)/login/+page.svelte | 21 - 30 files changed, 684 insertions(+), 458 deletions(-) create mode 100644 src/lib/dtos/id-params.dto.ts create mode 100644 src/lib/server/api/controllers/collection.controller.ts create mode 100644 src/lib/server/api/controllers/wishlist.controller.ts create mode 100644 src/lib/server/api/infrastructure/database/schemas/collections.schema.ts create mode 100644 src/lib/server/api/infrastructure/database/schemas/users.schemas.ts rename src/routes/(app)/(protected)/wishlists/{[id] => [cuid]}/+page.server.ts (81%) rename src/routes/(app)/(protected)/wishlists/{[id] => [cuid]}/+page.svelte (100%) diff --git a/biome.json b/biome.json index 7eaa0b2..bf6d670 100644 --- a/biome.json +++ b/biome.json @@ -6,7 +6,7 @@ "indentStyle": "tab", "indentWidth": 2, "lineEnding": "lf", - "lineWidth": 100, + "lineWidth": 150, "attributePosition": "auto", "ignore": [ "**/.DS_Store", @@ -34,6 +34,9 @@ "bracketSameLine": false, "quoteStyle": "single", "attributePosition": "auto" + }, + "parser": { + "unsafeParameterDecoratorsEnabled": true } }, "overrides": [ diff --git a/package.json b/package.json index 3829d3f..9cebec6 100644 --- a/package.json +++ b/package.json @@ -30,10 +30,10 @@ "@playwright/test": "^1.46.1", "@sveltejs/adapter-auto": "^3.2.4", "@sveltejs/enhanced-img": "^0.3.3", - "@sveltejs/kit": "^2.5.22", - "@sveltejs/vite-plugin-svelte": "^3.1.1", + "@sveltejs/kit": "^2.5.24", + "@sveltejs/vite-plugin-svelte": "^3.1.2", "@types/cookie": "^0.6.0", - "@types/node": "^20.16.0", + "@types/node": "^20.16.1", "@types/pg": "^8.11.6", "@typescript-eslint/eslint-plugin": "^7.18.0", "@typescript-eslint/parser": "^7.18.0", @@ -57,7 +57,7 @@ "satori": "^0.10.14", "satori-html": "^0.3.2", "svelte": "5.0.0-next.175", - "svelte-check": "^3.8.5", + "svelte-check": "^3.8.6", "svelte-headless-table": "^0.18.2", "svelte-meta-tags": "^3.1.3", "svelte-preprocess": "^6.0.2", @@ -70,13 +70,15 @@ "tslib": "^2.6.3", "tsx": "^4.17.0", "typescript": "^5.5.4", - "vite": "^5.4.1", + "vite": "^5.4.2", "vitest": "^1.6.0", "zod": "^3.23.8" }, "type": "module", "dependencies": { "@fontsource/fira-mono": "^5.0.14", + "@hono/swagger-ui": "^0.4.0", + "@hono/zod-openapi": "^0.15.3", "@hono/zod-validator": "^0.2.2", "@iconify-icons/line-md": "^1.2.30", "@iconify-icons/mdi": "^1.2.48", @@ -93,17 +95,18 @@ "arctic": "^1.9.2", "bits-ui": "^0.21.13", "boardgamegeekclient": "^1.9.1", - "bullmq": "^5.12.9", + "bullmq": "^5.12.10", "class-variance-authority": "^0.7.0", "clsx": "^2.1.1", "cookie": "^0.6.0", "dotenv": "^16.4.5", "dotenv-expand": "^11.0.6", "drizzle-orm": "^0.32.2", + "drizzle-zod": "^0.5.1", "feather-icons": "^4.29.2", "formsnap": "^1.0.1", "handlebars": "^4.7.8", - "hono": "^4.5.6", + "hono": "^4.5.8", "hono-rate-limiter": "^0.4.0", "html-entities": "^2.5.2", "iconify-icon": "^2.1.0", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index f66fdcc..1ffc797 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -11,9 +11,15 @@ importers: '@fontsource/fira-mono': specifier: ^5.0.14 version: 5.0.14 + '@hono/swagger-ui': + specifier: ^0.4.0 + version: 0.4.0(hono@4.5.8) + '@hono/zod-openapi': + specifier: ^0.15.3 + version: 0.15.3(hono@4.5.8)(zod@3.23.8) '@hono/zod-validator': specifier: ^0.2.2 - version: 0.2.2(hono@4.5.6)(zod@3.23.8) + version: 0.2.2(hono@4.5.8)(zod@3.23.8) '@iconify-icons/line-md': specifier: ^1.2.30 version: 1.2.30 @@ -40,10 +46,10 @@ importers: version: 2.6.2 '@sveltejs/adapter-node': specifier: ^5.2.2 - version: 5.2.2(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8))) + version: 5.2.2(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8))) '@sveltejs/adapter-vercel': specifier: ^5.4.3 - version: 5.4.3(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8))) + version: 5.4.3(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8))) '@types/feather-icons': specifier: ^4.29.4 version: 4.29.4 @@ -60,8 +66,8 @@ importers: specifier: ^1.9.1 version: 1.9.1 bullmq: - specifier: ^5.12.9 - version: 5.12.9 + specifier: ^5.12.10 + version: 5.12.10 class-variance-authority: specifier: ^0.7.0 version: 0.7.0 @@ -80,21 +86,24 @@ importers: drizzle-orm: specifier: ^0.32.2 version: 0.32.2(@neondatabase/serverless@0.9.4)(@types/pg@8.11.6)(pg@8.12.0)(postgres@3.4.4) + drizzle-zod: + specifier: ^0.5.1 + version: 0.5.1(drizzle-orm@0.32.2(@neondatabase/serverless@0.9.4)(@types/pg@8.11.6)(pg@8.12.0)(postgres@3.4.4))(zod@3.23.8) feather-icons: specifier: ^4.29.2 version: 4.29.2 formsnap: specifier: ^1.0.1 - version: 1.0.1(svelte@5.0.0-next.175)(sveltekit-superforms@2.17.0(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)) + version: 1.0.1(svelte@5.0.0-next.175)(sveltekit-superforms@2.17.0(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)) handlebars: specifier: ^4.7.8 version: 4.7.8 hono: - specifier: ^4.5.6 - version: 4.5.6 + specifier: ^4.5.8 + version: 4.5.8 hono-rate-limiter: specifier: ^0.4.0 - version: 0.4.0(hono@4.5.6) + version: 0.4.0(hono@4.5.8) html-entities: specifier: ^2.5.2 version: 2.5.2 @@ -148,10 +157,10 @@ importers: version: 2.5.2 tailwind-variants: specifier: ^0.2.1 - version: 0.2.1(tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4))) + version: 0.2.1(tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4))) tailwindcss-animate: specifier: ^1.0.7 - version: 1.0.7(tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4))) + version: 1.0.7(tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4))) tsyringe: specifier: ^4.8.0 version: 4.8.0 @@ -176,22 +185,22 @@ importers: version: 1.46.1 '@sveltejs/adapter-auto': specifier: ^3.2.4 - version: 3.2.4(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8))) + version: 3.2.4(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8))) '@sveltejs/enhanced-img': specifier: ^0.3.3 - version: 0.3.3(rollup@4.18.1)(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + version: 0.3.3(rollup@4.18.1)(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) '@sveltejs/kit': - specifier: ^2.5.22 - version: 2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + specifier: ^2.5.24 + version: 2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) '@sveltejs/vite-plugin-svelte': - specifier: ^3.1.1 - version: 3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + specifier: ^3.1.2 + version: 3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) '@types/cookie': specifier: ^0.6.0 version: 0.6.0 '@types/node': - specifier: ^20.16.0 - version: 20.16.0 + specifier: ^20.16.1 + version: 20.16.1 '@types/pg': specifier: ^8.11.6 version: 8.11.6 @@ -215,7 +224,7 @@ importers: version: 9.1.0(eslint@8.57.0) eslint-plugin-svelte: specifier: ^2.43.0 - version: 2.43.0(eslint@8.57.0)(svelte@5.0.0-next.175)(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)) + version: 2.43.0(eslint@8.57.0)(svelte@5.0.0-next.175)(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)) just-clone: specifier: ^6.2.0 version: 6.2.0 @@ -262,8 +271,8 @@ importers: specifier: 5.0.0-next.175 version: 5.0.0-next.175 svelte-check: - specifier: ^3.8.5 - version: 3.8.5(postcss-load-config@5.1.0(jiti@1.21.6)(postcss@8.4.41)(tsx@4.17.0))(postcss@8.4.41)(sass@1.77.8)(svelte@5.0.0-next.175) + specifier: ^3.8.6 + version: 3.8.6(postcss-load-config@5.1.0(jiti@1.21.6)(postcss@8.4.41)(tsx@4.17.0))(postcss@8.4.41)(sass@1.77.8)(svelte@5.0.0-next.175) svelte-headless-table: specifier: ^0.18.2 version: 0.18.2(svelte@5.0.0-next.175) @@ -278,19 +287,19 @@ importers: version: 2.0.1 sveltekit-flash-message: specifier: ^2.4.4 - version: 2.4.4(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175) + version: 2.4.4(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175) sveltekit-rate-limiter: specifier: ^0.5.2 - version: 0.5.2(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8))) + version: 0.5.2(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8))) sveltekit-superforms: specifier: ^2.17.0 - version: 2.17.0(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175) + version: 2.17.0(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175) tailwindcss: specifier: ^3.4.10 - version: 3.4.10(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)) + version: 3.4.10(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)) ts-node: specifier: ^10.9.2 - version: 10.9.2(@types/node@20.16.0)(typescript@5.5.4) + version: 10.9.2(@types/node@20.16.1)(typescript@5.5.4) tslib: specifier: ^2.6.3 version: 2.6.3 @@ -301,11 +310,11 @@ importers: specifier: ^5.5.4 version: 5.5.4 vite: - specifier: ^5.4.1 - version: 5.4.1(@types/node@20.16.0)(sass@1.77.8) + specifier: ^5.4.2 + version: 5.4.2(@types/node@20.16.1)(sass@1.77.8) vitest: specifier: ^1.6.0 - version: 1.6.0(@types/node@20.16.0)(sass@1.77.8) + version: 1.6.0(@types/node@20.16.1)(sass@1.77.8) zod: specifier: ^3.23.8 version: 3.23.8 @@ -326,6 +335,11 @@ packages: '@ark/util@0.1.0': resolution: {integrity: sha512-qCLYICQoCy3kEKDVwirQp8qvxhY7NJd8BhhoHaj1l3wCFAk9NUbcDsxAkPStZEMdPI/d7NcbGJe8SWZuRG2twQ==} + '@asteasolutions/zod-to-openapi@7.1.1': + resolution: {integrity: sha512-lF0d1gAc0lYLO9/BAGivwTwE2Sh9h6CHuDcbk5KnGBfIuAsAkDC+Fdat4dkQY3CS/zUWKHRmFEma0B7X132Ymw==} + peerDependencies: + zod: ^3.20.2 + '@babel/runtime@7.24.8': resolution: {integrity: sha512-5F7SDGs1T72ZczbRwbGO9lQi0NLjQxzl6i4lJxLxfW9U5UluCSyEJeniWvnhl3/euNiqQVbo8zruhsDfid0esA==} engines: {node: '>=6.9.0'} @@ -1256,6 +1270,18 @@ packages: '@hapi/topo@5.1.0': resolution: {integrity: sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==} + '@hono/swagger-ui@0.4.0': + resolution: {integrity: sha512-8lF+dexzgV2HRM1R/gf49E5djroq4jVMYMSwLkSF9pT0I6sYhuqirFDCRFrBtbbLCBsKzw6f2MF5rS+WY3d7Nw==} + peerDependencies: + hono: '*' + + '@hono/zod-openapi@0.15.3': + resolution: {integrity: sha512-9oc4Bbs+L5oGjUOCrApCrx8BSWa5ctOBjRcwxplxkWPYFPhyOhdkMg47QKenGkESfFz0K6zb4F/c0LGPEmR62g==} + engines: {node: '>=16.0.0'} + peerDependencies: + hono: '>=4.3.6' + zod: 3.* + '@hono/zod-validator@0.2.2': resolution: {integrity: sha512-dSDxaPV70Py8wuIU2QNpoVEIOSzSXZ/6/B/h4xA7eOMz7+AarKTSGV8E6QwrdcCbBLkpqfJ4Q2TmBO0eP1tCBQ==} peerDependencies: @@ -1830,19 +1856,14 @@ packages: rollup: optional: true - '@rollup/rollup-android-arm-eabi@4.17.2': - resolution: {integrity: sha512-NM0jFxY8bB8QLkoKxIQeObCaDlJKewVlIEkuyYKm5An1tdVZ966w2+MPQ2l8LBZLjR+SgyV+nRkTIunzOYBMLQ==} - cpu: [arm] - os: [android] - '@rollup/rollup-android-arm-eabi@4.18.1': resolution: {integrity: sha512-lncuC4aHicncmbORnx+dUaAgzee9cm/PbIqgWz1PpXuwc+sa1Ct83tnqUDy/GFKleLiN7ZIeytM6KJ4cAn1SxA==} cpu: [arm] os: [android] - '@rollup/rollup-android-arm64@4.17.2': - resolution: {integrity: sha512-yeX/Usk7daNIVwkq2uGoq2BYJKZY1JfyLTaHO/jaiSwi/lsf8fTFoQW/n6IdAsx5tx+iotu2zCJwz8MxI6D/Bw==} - cpu: [arm64] + '@rollup/rollup-android-arm-eabi@4.21.0': + resolution: {integrity: sha512-WTWD8PfoSAJ+qL87lE7votj3syLavxunWhzCnx3XFxFiI/BA/r3X7MUM8dVrH8rb2r4AiO8jJsr3ZjdaftmnfA==} + cpu: [arm] os: [android] '@rollup/rollup-android-arm64@4.18.1': @@ -1850,19 +1871,19 @@ packages: cpu: [arm64] os: [android] - '@rollup/rollup-darwin-arm64@4.17.2': - resolution: {integrity: sha512-kcMLpE6uCwls023+kknm71ug7MZOrtXo+y5p/tsg6jltpDtgQY1Eq5sGfHcQfb+lfuKwhBmEURDga9N0ol4YPw==} + '@rollup/rollup-android-arm64@4.21.0': + resolution: {integrity: sha512-a1sR2zSK1B4eYkiZu17ZUZhmUQcKjk2/j9Me2IDjk1GHW7LB5Z35LEzj9iJch6gtUfsnvZs1ZNyDW2oZSThrkA==} cpu: [arm64] - os: [darwin] + os: [android] '@rollup/rollup-darwin-arm64@4.18.1': resolution: {integrity: sha512-vk+ma8iC1ebje/ahpxpnrfVQJibTMyHdWpOGZ3JpQ7Mgn/3QNHmPq7YwjZbIE7km73dH5M1e6MRRsnEBW7v5CQ==} cpu: [arm64] os: [darwin] - '@rollup/rollup-darwin-x64@4.17.2': - resolution: {integrity: sha512-AtKwD0VEx0zWkL0ZjixEkp5tbNLzX+FCqGG1SvOu993HnSz4qDI6S4kGzubrEJAljpVkhRSlg5bzpV//E6ysTQ==} - cpu: [x64] + '@rollup/rollup-darwin-arm64@4.21.0': + resolution: {integrity: sha512-zOnKWLgDld/svhKO5PD9ozmL6roy5OQ5T4ThvdYZLpiOhEGY+dp2NwUmxK0Ld91LrbjrvtNAE0ERBwjqhZTRAA==} + cpu: [arm64] os: [darwin] '@rollup/rollup-darwin-x64@4.18.1': @@ -1870,18 +1891,18 @@ packages: cpu: [x64] os: [darwin] - '@rollup/rollup-linux-arm-gnueabihf@4.17.2': - resolution: {integrity: sha512-3reX2fUHqN7sffBNqmEyMQVj/CKhIHZd4y631duy0hZqI8Qoqf6lTtmAKvJFYa6bhU95B1D0WgzHkmTg33In0A==} - cpu: [arm] - os: [linux] + '@rollup/rollup-darwin-x64@4.21.0': + resolution: {integrity: sha512-7doS8br0xAkg48SKE2QNtMSFPFUlRdw9+votl27MvT46vo44ATBmdZdGysOevNELmZlfd+NEa0UYOA8f01WSrg==} + cpu: [x64] + os: [darwin] '@rollup/rollup-linux-arm-gnueabihf@4.18.1': resolution: {integrity: sha512-P9bSiAUnSSM7EmyRK+e5wgpqai86QOSv8BwvkGjLwYuOpaeomiZWifEos517CwbG+aZl1T4clSE1YqqH2JRs+g==} cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm-musleabihf@4.17.2': - resolution: {integrity: sha512-uSqpsp91mheRgw96xtyAGP9FW5ChctTFEoXP0r5FAzj/3ZRv3Uxjtc7taRQSaQM/q85KEKjKsZuiZM3GyUivRg==} + '@rollup/rollup-linux-arm-gnueabihf@4.21.0': + resolution: {integrity: sha512-pWJsfQjNWNGsoCq53KjMtwdJDmh/6NubwQcz52aEwLEuvx08bzcy6tOUuawAOncPnxz/3siRtd8hiQ32G1y8VA==} cpu: [arm] os: [linux] @@ -1890,9 +1911,9 @@ packages: cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm64-gnu@4.17.2': - resolution: {integrity: sha512-EMMPHkiCRtE8Wdk3Qhtciq6BndLtstqZIroHiiGzB3C5LDJmIZcSzVtLRbwuXuUft1Cnv+9fxuDtDxz3k3EW2A==} - cpu: [arm64] + '@rollup/rollup-linux-arm-musleabihf@4.21.0': + resolution: {integrity: sha512-efRIANsz3UHZrnZXuEvxS9LoCOWMGD1rweciD6uJQIx2myN3a8Im1FafZBzh7zk1RJ6oKcR16dU3UPldaKd83w==} + cpu: [arm] os: [linux] '@rollup/rollup-linux-arm64-gnu@4.18.1': @@ -1900,8 +1921,8 @@ packages: cpu: [arm64] os: [linux] - '@rollup/rollup-linux-arm64-musl@4.17.2': - resolution: {integrity: sha512-NMPylUUZ1i0z/xJUIx6VUhISZDRT+uTWpBcjdv0/zkp7b/bQDF+NfnfdzuTiB1G6HTodgoFa93hp0O1xl+/UbA==} + '@rollup/rollup-linux-arm64-gnu@4.21.0': + resolution: {integrity: sha512-ZrPhydkTVhyeGTW94WJ8pnl1uroqVHM3j3hjdquwAcWnmivjAwOYjTEAuEDeJvGX7xv3Z9GAvrBkEzCgHq9U1w==} cpu: [arm64] os: [linux] @@ -1910,9 +1931,9 @@ packages: cpu: [arm64] os: [linux] - '@rollup/rollup-linux-powerpc64le-gnu@4.17.2': - resolution: {integrity: sha512-T19My13y8uYXPw/L/k0JYaX1fJKFT/PWdXiHr8mTbXWxjVF1t+8Xl31DgBBvEKclw+1b00Chg0hxE2O7bTG7GQ==} - cpu: [ppc64] + '@rollup/rollup-linux-arm64-musl@4.21.0': + resolution: {integrity: sha512-cfaupqd+UEFeURmqNP2eEvXqgbSox/LHOyN9/d2pSdV8xTrjdg3NgOFJCtc1vQ/jEke1qD0IejbBfxleBPHnPw==} + cpu: [arm64] os: [linux] '@rollup/rollup-linux-powerpc64le-gnu@4.18.1': @@ -1920,9 +1941,9 @@ packages: cpu: [ppc64] os: [linux] - '@rollup/rollup-linux-riscv64-gnu@4.17.2': - resolution: {integrity: sha512-BOaNfthf3X3fOWAB+IJ9kxTgPmMqPPH5f5k2DcCsRrBIbWnaJCgX2ll77dV1TdSy9SaXTR5iDXRL8n7AnoP5cg==} - cpu: [riscv64] + '@rollup/rollup-linux-powerpc64le-gnu@4.21.0': + resolution: {integrity: sha512-ZKPan1/RvAhrUylwBXC9t7B2hXdpb/ufeu22pG2psV7RN8roOfGurEghw1ySmX/CmDDHNTDDjY3lo9hRlgtaHg==} + cpu: [ppc64] os: [linux] '@rollup/rollup-linux-riscv64-gnu@4.18.1': @@ -1930,9 +1951,9 @@ packages: cpu: [riscv64] os: [linux] - '@rollup/rollup-linux-s390x-gnu@4.17.2': - resolution: {integrity: sha512-W0UP/x7bnn3xN2eYMql2T/+wpASLE5SjObXILTMPUBDB/Fg/FxC+gX4nvCfPBCbNhz51C+HcqQp2qQ4u25ok6g==} - cpu: [s390x] + '@rollup/rollup-linux-riscv64-gnu@4.21.0': + resolution: {integrity: sha512-H1eRaCwd5E8eS8leiS+o/NqMdljkcb1d6r2h4fKSsCXQilLKArq6WS7XBLDu80Yz+nMqHVFDquwcVrQmGr28rg==} + cpu: [riscv64] os: [linux] '@rollup/rollup-linux-s390x-gnu@4.18.1': @@ -1940,9 +1961,9 @@ packages: cpu: [s390x] os: [linux] - '@rollup/rollup-linux-x64-gnu@4.17.2': - resolution: {integrity: sha512-Hy7pLwByUOuyaFC6mAr7m+oMC+V7qyifzs/nW2OJfC8H4hbCzOX07Ov0VFk/zP3kBsELWNFi7rJtgbKYsav9QQ==} - cpu: [x64] + '@rollup/rollup-linux-s390x-gnu@4.21.0': + resolution: {integrity: sha512-zJ4hA+3b5tu8u7L58CCSI0A9N1vkfwPhWd/puGXwtZlsB5bTkwDNW/+JCU84+3QYmKpLi+XvHdmrlwUwDA6kqw==} + cpu: [s390x] os: [linux] '@rollup/rollup-linux-x64-gnu@4.18.1': @@ -1950,8 +1971,8 @@ packages: cpu: [x64] os: [linux] - '@rollup/rollup-linux-x64-musl@4.17.2': - resolution: {integrity: sha512-h1+yTWeYbRdAyJ/jMiVw0l6fOOm/0D1vNLui9iPuqgRGnXA0u21gAqOyB5iHjlM9MMfNOm9RHCQ7zLIzT0x11Q==} + '@rollup/rollup-linux-x64-gnu@4.21.0': + resolution: {integrity: sha512-e2hrvElFIh6kW/UNBQK/kzqMNY5mO+67YtEh9OA65RM5IJXYTWiXjX6fjIiPaqOkBthYF1EqgiZ6OXKcQsM0hg==} cpu: [x64] os: [linux] @@ -1960,19 +1981,19 @@ packages: cpu: [x64] os: [linux] - '@rollup/rollup-win32-arm64-msvc@4.17.2': - resolution: {integrity: sha512-tmdtXMfKAjy5+IQsVtDiCfqbynAQE/TQRpWdVataHmhMb9DCoJxp9vLcCBjEQWMiUYxO1QprH/HbY9ragCEFLA==} - cpu: [arm64] - os: [win32] + '@rollup/rollup-linux-x64-musl@4.21.0': + resolution: {integrity: sha512-1vvmgDdUSebVGXWX2lIcgRebqfQSff0hMEkLJyakQ9JQUbLDkEaMsPTLOmyccyC6IJ/l3FZuJbmrBw/u0A0uCQ==} + cpu: [x64] + os: [linux] '@rollup/rollup-win32-arm64-msvc@4.18.1': resolution: {integrity: sha512-W2ZNI323O/8pJdBGil1oCauuCzmVd9lDmWBBqxYZcOqWD6aWqJtVBQ1dFrF4dYpZPks6F+xCZHfzG5hYlSHZ6g==} cpu: [arm64] os: [win32] - '@rollup/rollup-win32-ia32-msvc@4.17.2': - resolution: {integrity: sha512-7II/QCSTAHuE5vdZaQEwJq2ZACkBpQDOmQsE6D6XUbnBHW8IAhm4eTufL6msLJorzrHDFv3CF8oCA/hSIRuZeQ==} - cpu: [ia32] + '@rollup/rollup-win32-arm64-msvc@4.21.0': + resolution: {integrity: sha512-s5oFkZ/hFcrlAyBTONFY1TWndfyre1wOMwU+6KCpm/iatybvrRgmZVM+vCFwxmC5ZhdlgfE0N4XorsDpi7/4XQ==} + cpu: [arm64] os: [win32] '@rollup/rollup-win32-ia32-msvc@4.18.1': @@ -1980,9 +2001,9 @@ packages: cpu: [ia32] os: [win32] - '@rollup/rollup-win32-x64-msvc@4.17.2': - resolution: {integrity: sha512-TGGO7v7qOq4CYmSBVEYpI1Y5xDuCEnbVC5Vth8mOsW0gDSzxNrVERPc790IGHsrT2dQSimgMr9Ub3Y1Jci5/8w==} - cpu: [x64] + '@rollup/rollup-win32-ia32-msvc@4.21.0': + resolution: {integrity: sha512-G9+TEqRnAA6nbpqyUqgTiopmnfgnMkR3kMukFBDsiyy23LZvUCpiUwjTRx6ezYCjJODXrh52rBR9oXvm+Fp5wg==} + cpu: [ia32] os: [win32] '@rollup/rollup-win32-x64-msvc@4.18.1': @@ -1990,6 +2011,11 @@ packages: cpu: [x64] os: [win32] + '@rollup/rollup-win32-x64-msvc@4.21.0': + resolution: {integrity: sha512-2jsCDZwtQvRhejHLfZ1JY6w6kEuEtfF9nzYsZxzSlNVKDX+DpsDJ+Rbjkm74nvg2rdx0gwBS+IMdvwJuq3S9pQ==} + cpu: [x64] + os: [win32] + '@shuding/opentype.js@1.4.0-beta.0': resolution: {integrity: sha512-3NgmNyH3l/Hv6EvsWJbsvpcpUba6R8IREQ83nH83cyakCw7uM1arZKNfHwv1Wz6jgqrF/j4x5ELvR6PnK9nTcA==} engines: {node: '>= 8.0.0'} @@ -2034,12 +2060,12 @@ packages: svelte: ^4.0.0 || ^5.0.0-next.0 vite: '>= 5.0.0' - '@sveltejs/kit@2.5.22': - resolution: {integrity: sha512-PQ98baF2WzvG5yiO4cZKJZJG60XjHTZD1jyho3u9Kmthx2ytdGYyVPPvKXgKXpKSq4wwctD9dl0d2blSbJMcOg==} + '@sveltejs/kit@2.5.24': + resolution: {integrity: sha512-Nr2oxsCsDfEkdS/zzQQQbsPYTbu692Qs3/iE3L7VHzCVjG2+WujF9oMUozWI7GuX98KxYSoPMlAsfmDLSg44hQ==} engines: {node: '>=18.13'} hasBin: true peerDependencies: - '@sveltejs/vite-plugin-svelte': ^3.0.0 + '@sveltejs/vite-plugin-svelte': ^3.0.0 || ^4.0.0-next.1 svelte: ^4.0.0 || ^5.0.0-next.0 vite: ^5.0.3 @@ -2051,8 +2077,8 @@ packages: svelte: ^4.0.0 || ^5.0.0-next.0 vite: ^5.0.0 - '@sveltejs/vite-plugin-svelte@3.1.1': - resolution: {integrity: sha512-rimpFEAboBBHIlzISibg94iP09k/KYdHgVhJlcsTfn7KMBhc70jFX/GRWkRdFCc2fdnk+4+Bdfej23cMDnJS6A==} + '@sveltejs/vite-plugin-svelte@3.1.2': + resolution: {integrity: sha512-Txsm1tJvtiYeLUVRNqxZGKR/mI+CzuIQuc2gn+YCs9rMTowpNZ2Nqt53JdL8KF9bLhAf2ruR/dr9eZCwdTriRA==} engines: {node: ^18.0.0 || >=20} peerDependencies: svelte: ^4.0.0 || ^5.0.0-next.0 @@ -2088,8 +2114,8 @@ packages: '@types/json-schema@7.0.15': resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==} - '@types/node@20.16.0': - resolution: {integrity: sha512-vDxceJcoZhIVh67S568bm1UGZO0DX0hpplJZxzeXMKwIPLn190ec5RRxQ69BKhX44SUGIxxgMdDY557lGLKprQ==} + '@types/node@20.16.1': + resolution: {integrity: sha512-zJDo7wEadFtSyNz5QITDfRcrhqDvQI1xQNQ0VoizPjM/dVAODqqIUWbJPkvsxmTI0MYRGRikcdjMPhOssnPejQ==} '@types/pg@8.11.6': resolution: {integrity: sha512-/2WmmBXHLsfRqzfHW7BNZ8SbYzE8OSk7i3WjFYvfgRHj7S1xj+16Je5fUKv3lVdVzk/zn9TXOqf+avFCFIE0yQ==} @@ -2376,8 +2402,8 @@ packages: resolution: {integrity: sha512-zhaCDicdLuWN5UbN5IMnFqNMhNfo919sH85y2/ea+5Yg9TsTkeZxpL+JLbp6cgYFS4sRLp3YV4S6yDuqVWHYOw==} engines: {node: '>=6'} - bullmq@5.12.9: - resolution: {integrity: sha512-34YW4NaC6IfuAtwdllNkBSEP9/sq9bjpvlvbdSv1JXQUzqbey1+DZTvecM8SdewsNKa0RxuwYx/KATe7iXvH7A==} + bullmq@5.12.10: + resolution: {integrity: sha512-lXH8Caj+FvYHiBS0QBEpQOq57RcVuEPziBC5cBlWguCVNfn1UMSri22bRrynDKuof8o9XB43ctmYASUpoa0DeQ==} bytes@3.1.2: resolution: {integrity: sha512-/Nf7TyzTx6S3yRJObOAV7956r8cr2+Oj8AC5dt8wSP3BQAoeX58NoHyCU8P8zGkNXStjTSi6fzO6F0pBdcYbEg==} @@ -2778,6 +2804,12 @@ packages: sqlite3: optional: true + drizzle-zod@0.5.1: + resolution: {integrity: sha512-C/8bvzUH/zSnVfwdSibOgFjLhtDtbKYmkbPbUCq46QZyZCH6kODIMSOgZ8R7rVjoI+tCj3k06MRJMDqsIeoS4A==} + peerDependencies: + drizzle-orm: '>=0.23.13' + zod: '*' + eastasianwidth@0.2.0: resolution: {integrity: sha512-I88TYZWc9XiYHRQ4/3c5rjjfgkjhLyW2luGIheGERbNQ6OY7yTybanSpDXZa8y7VUP9YmDcYa+eyq4ca7iLqWA==} @@ -3146,8 +3178,8 @@ packages: peerDependencies: hono: ^4.1.1 - hono@4.5.6: - resolution: {integrity: sha512-9SuUC/zLQv8YAcnIxJko0KCeLI0Q6menPsDWuJ9jaH+r8ZkVXeLqeLs1QJXCPKKbURAWj9x0SJBSFh803EnAUw==} + hono@4.5.8: + resolution: {integrity: sha512-pqpSlcdqGkpTTRpLYU1PnCz52gVr0zVR9H5GzMyJWuKQLLEBQxh96q45QizJ2PPX8NATtz2mu31/PKW/Jt+90Q==} engines: {node: '>=16.0.0'} html-entities@2.5.2: @@ -3638,6 +3670,9 @@ packages: open-props@1.7.5: resolution: {integrity: sha512-DajjLQDJgIa0i+QdB2q5M8lNLo2ICk+DbDh4TsqNsT1tAO8Zm8F7dndSkLMQkobT98lbvDMMpJWO8NT0ibjrjA==} + openapi3-ts@4.3.3: + resolution: {integrity: sha512-LKkzBGJcZ6wdvkKGMoSvpK+0cbN5Xc3XuYkJskO+vjEQWJgs1kgtyUk0pjf8KwPuysv323Er62F5P17XQl96Qg==} + optionator@0.9.4: resolution: {integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==} engines: {node: '>= 0.8.0'} @@ -4211,13 +4246,13 @@ packages: resolution: {integrity: sha512-JZkJMZkAGFFPP2YqXZXPbMlMBgsxzE8ILs4lMIX/2o0L9UBw9O/Y3o6wFw/i9YLapcUJWwqbi3kdxIPdC62TIA==} hasBin: true - rollup@4.17.2: - resolution: {integrity: sha512-/9ClTJPByC0U4zNLowV1tMBe8yMEAxewtR3cUNX5BoEpGH3dQEWpJLr6CLp0fPdYRF/fzVOgvDb1zXuakwF5kQ==} + rollup@4.18.1: + resolution: {integrity: sha512-Elx2UT8lzxxOXMpy5HWQGZqkrQOtrVDDa/bm9l10+U4rQnVzbL/LgZ4NOM1MPIDyHk69W4InuYDF5dzRh4Kw1A==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} hasBin: true - rollup@4.18.1: - resolution: {integrity: sha512-Elx2UT8lzxxOXMpy5HWQGZqkrQOtrVDDa/bm9l10+U4rQnVzbL/LgZ4NOM1MPIDyHk69W4InuYDF5dzRh4Kw1A==} + rollup@4.21.0: + resolution: {integrity: sha512-vo+S/lfA2lMS7rZ2Qoubi6I5hwZwzXeUIctILZLbHI+laNtvhhOIon2S1JksA5UEDQ7l3vberd0fxK44lTYjbQ==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} hasBin: true @@ -4419,8 +4454,8 @@ packages: resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} engines: {node: '>= 0.4'} - svelte-check@3.8.5: - resolution: {integrity: sha512-3OGGgr9+bJ/+1nbPgsvulkLC48xBsqsgtc8Wam281H4G9F5v3mYGa2bHRsPuwHC5brKl4AxJH95QF73kmfihGQ==} + svelte-check@3.8.6: + resolution: {integrity: sha512-ij0u4Lw/sOTREP13BdWZjiXD/BlHE6/e2e34XzmVmsp5IN4kVa3PWP65NM32JAgwjZlwBg/+JtiNV1MM8khu0Q==} hasBin: true peerDependencies: svelte: ^3.55.0 || ^4.0.0-next.0 || ^4.0.0 || ^5.0.0-next.0 @@ -4803,8 +4838,8 @@ packages: engines: {node: ^18.0.0 || >=20.0.0} hasBin: true - vite@5.4.1: - resolution: {integrity: sha512-1oE6yuNXssjrZdblI9AfBbHCC41nnyoVoEZxQnID6yvQZAFBzxxkqoFLtHUMkYunL8hwOLEjgTuxpkRxvba3kA==} + vite@5.4.2: + resolution: {integrity: sha512-dDrQTRHp5C1fTFzcSaMxjk6vdpKvT+2/mIdE07Gw2ykehT49O0z/VHS3zZ8iV/Gh8BJJKHWOe5RjaNrW5xf/GA==} engines: {node: ^18.0.0 || >=20.0.0} hasBin: true peerDependencies: @@ -4935,6 +4970,11 @@ packages: engines: {node: '>= 14'} hasBin: true + yaml@2.5.0: + resolution: {integrity: sha512-2wWLbGbYDiSqqIKoPjar3MPgB94ErzCtrNE1FdqGuaO0pi2JGjmE8aW8TDZwzU7vuxcGRdL/4gPQwQ7hD5AMSw==} + engines: {node: '>= 14'} + hasBin: true + yargs-parser@18.1.3: resolution: {integrity: sha512-o50j0JeToy/4K6OZcaQmW6lyXXKhq7csREXcDwk2omFPJEwUNOVtJKvmDr9EI1fAJZUyZcRF7kxGBWmRXudrCQ==} engines: {node: '>=6'} @@ -4989,6 +5029,11 @@ snapshots: '@ark/util@0.1.0': optional: true + '@asteasolutions/zod-to-openapi@7.1.1(zod@3.23.8)': + dependencies: + openapi3-ts: 4.3.3 + zod: 3.23.8 + '@babel/runtime@7.24.8': dependencies: regenerator-runtime: 0.14.1 @@ -5647,9 +5692,20 @@ snapshots: '@hapi/hoek': 9.3.0 optional: true - '@hono/zod-validator@0.2.2(hono@4.5.6)(zod@3.23.8)': + '@hono/swagger-ui@0.4.0(hono@4.5.8)': dependencies: - hono: 4.5.6 + hono: 4.5.8 + + '@hono/zod-openapi@0.15.3(hono@4.5.8)(zod@3.23.8)': + dependencies: + '@asteasolutions/zod-to-openapi': 7.1.1(zod@3.23.8) + '@hono/zod-validator': 0.2.2(hono@4.5.8)(zod@3.23.8) + hono: 4.5.8 + zod: 3.23.8 + + '@hono/zod-validator@0.2.2(hono@4.5.8)(zod@3.23.8)': + dependencies: + hono: 4.5.8 zod: 3.23.8 '@humanwhocodes/config-array@0.11.14': @@ -6119,102 +6175,102 @@ snapshots: optionalDependencies: rollup: 4.18.1 - '@rollup/rollup-android-arm-eabi@4.17.2': - optional: true - '@rollup/rollup-android-arm-eabi@4.18.1': optional: true - '@rollup/rollup-android-arm64@4.17.2': + '@rollup/rollup-android-arm-eabi@4.21.0': optional: true '@rollup/rollup-android-arm64@4.18.1': optional: true - '@rollup/rollup-darwin-arm64@4.17.2': + '@rollup/rollup-android-arm64@4.21.0': optional: true '@rollup/rollup-darwin-arm64@4.18.1': optional: true - '@rollup/rollup-darwin-x64@4.17.2': + '@rollup/rollup-darwin-arm64@4.21.0': optional: true '@rollup/rollup-darwin-x64@4.18.1': optional: true - '@rollup/rollup-linux-arm-gnueabihf@4.17.2': + '@rollup/rollup-darwin-x64@4.21.0': optional: true '@rollup/rollup-linux-arm-gnueabihf@4.18.1': optional: true - '@rollup/rollup-linux-arm-musleabihf@4.17.2': + '@rollup/rollup-linux-arm-gnueabihf@4.21.0': optional: true '@rollup/rollup-linux-arm-musleabihf@4.18.1': optional: true - '@rollup/rollup-linux-arm64-gnu@4.17.2': + '@rollup/rollup-linux-arm-musleabihf@4.21.0': optional: true '@rollup/rollup-linux-arm64-gnu@4.18.1': optional: true - '@rollup/rollup-linux-arm64-musl@4.17.2': + '@rollup/rollup-linux-arm64-gnu@4.21.0': optional: true '@rollup/rollup-linux-arm64-musl@4.18.1': optional: true - '@rollup/rollup-linux-powerpc64le-gnu@4.17.2': + '@rollup/rollup-linux-arm64-musl@4.21.0': optional: true '@rollup/rollup-linux-powerpc64le-gnu@4.18.1': optional: true - '@rollup/rollup-linux-riscv64-gnu@4.17.2': + '@rollup/rollup-linux-powerpc64le-gnu@4.21.0': optional: true '@rollup/rollup-linux-riscv64-gnu@4.18.1': optional: true - '@rollup/rollup-linux-s390x-gnu@4.17.2': + '@rollup/rollup-linux-riscv64-gnu@4.21.0': optional: true '@rollup/rollup-linux-s390x-gnu@4.18.1': optional: true - '@rollup/rollup-linux-x64-gnu@4.17.2': + '@rollup/rollup-linux-s390x-gnu@4.21.0': optional: true '@rollup/rollup-linux-x64-gnu@4.18.1': optional: true - '@rollup/rollup-linux-x64-musl@4.17.2': + '@rollup/rollup-linux-x64-gnu@4.21.0': optional: true '@rollup/rollup-linux-x64-musl@4.18.1': optional: true - '@rollup/rollup-win32-arm64-msvc@4.17.2': + '@rollup/rollup-linux-x64-musl@4.21.0': optional: true '@rollup/rollup-win32-arm64-msvc@4.18.1': optional: true - '@rollup/rollup-win32-ia32-msvc@4.17.2': + '@rollup/rollup-win32-arm64-msvc@4.21.0': optional: true '@rollup/rollup-win32-ia32-msvc@4.18.1': optional: true - '@rollup/rollup-win32-x64-msvc@4.17.2': + '@rollup/rollup-win32-ia32-msvc@4.21.0': optional: true '@rollup/rollup-win32-x64-msvc@4.18.1': optional: true + '@rollup/rollup-win32-x64-msvc@4.21.0': + optional: true + '@shuding/opentype.js@1.4.0-beta.0': dependencies: fflate: 0.7.4 @@ -6239,41 +6295,41 @@ snapshots: '@sodaru/yup-to-json-schema@2.0.1': optional: true - '@sveltejs/adapter-auto@3.2.4(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))': + '@sveltejs/adapter-auto@3.2.4(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))': dependencies: - '@sveltejs/kit': 2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + '@sveltejs/kit': 2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) import-meta-resolve: 4.1.0 - '@sveltejs/adapter-node@5.2.2(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))': + '@sveltejs/adapter-node@5.2.2(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))': dependencies: '@rollup/plugin-commonjs': 26.0.1(rollup@4.18.1) '@rollup/plugin-json': 6.1.0(rollup@4.18.1) '@rollup/plugin-node-resolve': 15.2.3(rollup@4.18.1) - '@sveltejs/kit': 2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + '@sveltejs/kit': 2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) rollup: 4.18.1 - '@sveltejs/adapter-vercel@5.4.3(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))': + '@sveltejs/adapter-vercel@5.4.3(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))': dependencies: - '@sveltejs/kit': 2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + '@sveltejs/kit': 2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) '@vercel/nft': 0.27.2 esbuild: 0.21.5 transitivePeerDependencies: - encoding - supports-color - '@sveltejs/enhanced-img@0.3.3(rollup@4.18.1)(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8))': + '@sveltejs/enhanced-img@0.3.3(rollup@4.18.1)(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8))': dependencies: magic-string: 0.30.10 svelte: 5.0.0-next.175 svelte-parse-markup: 0.1.5(svelte@5.0.0-next.175) - vite: 5.4.1(@types/node@20.16.0)(sass@1.77.8) + vite: 5.4.2(@types/node@20.16.1)(sass@1.77.8) vite-imagetools: 7.0.2(rollup@4.18.1) transitivePeerDependencies: - rollup - '@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8))': + '@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8))': dependencies: - '@sveltejs/vite-plugin-svelte': 3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + '@sveltejs/vite-plugin-svelte': 3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) '@types/cookie': 0.6.0 cookie: 0.6.0 devalue: 5.0.0 @@ -6287,28 +6343,28 @@ snapshots: sirv: 2.0.4 svelte: 5.0.0-next.175 tiny-glob: 0.2.9 - vite: 5.4.1(@types/node@20.16.0)(sass@1.77.8) + vite: 5.4.2(@types/node@20.16.1)(sass@1.77.8) - '@sveltejs/vite-plugin-svelte-inspector@2.1.0(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8))': + '@sveltejs/vite-plugin-svelte-inspector@2.1.0(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8))': dependencies: - '@sveltejs/vite-plugin-svelte': 3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + '@sveltejs/vite-plugin-svelte': 3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) debug: 4.3.4 svelte: 5.0.0-next.175 - vite: 5.4.1(@types/node@20.16.0)(sass@1.77.8) + vite: 5.4.2(@types/node@20.16.1)(sass@1.77.8) transitivePeerDependencies: - supports-color - '@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8))': + '@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8))': dependencies: - '@sveltejs/vite-plugin-svelte-inspector': 2.1.0(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + '@sveltejs/vite-plugin-svelte-inspector': 2.1.0(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) debug: 4.3.4 deepmerge: 4.3.1 kleur: 4.1.5 magic-string: 0.30.10 svelte: 5.0.0-next.175 svelte-hmr: 0.16.0(svelte@5.0.0-next.175) - vite: 5.4.1(@types/node@20.16.0)(sass@1.77.8) - vitefu: 0.2.5(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + vite: 5.4.2(@types/node@20.16.1)(sass@1.77.8) + vitefu: 0.2.5(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) transitivePeerDependencies: - supports-color @@ -6338,13 +6394,13 @@ snapshots: '@types/json-schema@7.0.15': optional: true - '@types/node@20.16.0': + '@types/node@20.16.1': dependencies: undici-types: 6.19.6 '@types/pg@8.11.6': dependencies: - '@types/node': 20.16.0 + '@types/node': 20.16.1 pg-protocol: 1.6.1 pg-types: 4.0.2 @@ -6691,7 +6747,7 @@ snapshots: builtin-modules@3.3.0: {} - bullmq@5.12.9: + bullmq@5.12.10: dependencies: cron-parser: 4.9.0 ioredis: 5.4.1 @@ -6969,6 +7025,11 @@ snapshots: pg: 8.12.0 postgres: 3.4.4 + drizzle-zod@0.5.1(drizzle-orm@0.32.2(@neondatabase/serverless@0.9.4)(@types/pg@8.11.6)(pg@8.12.0)(postgres@3.4.4))(zod@3.23.8): + dependencies: + drizzle-orm: 0.32.2(@neondatabase/serverless@0.9.4)(@types/pg@8.11.6)(pg@8.12.0)(postgres@3.4.4) + zod: 3.23.8 + eastasianwidth@0.2.0: {} ee-first@1.1.1: {} @@ -7126,7 +7187,7 @@ snapshots: dependencies: eslint: 8.57.0 - eslint-plugin-svelte@2.43.0(eslint@8.57.0)(svelte@5.0.0-next.175)(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)): + eslint-plugin-svelte@2.43.0(eslint@8.57.0)(svelte@5.0.0-next.175)(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)): dependencies: '@eslint-community/eslint-utils': 4.4.0(eslint@8.57.0) '@jridgewell/sourcemap-codec': 1.4.15 @@ -7135,7 +7196,7 @@ snapshots: esutils: 2.0.3 known-css-properties: 0.34.0 postcss: 8.4.41 - postcss-load-config: 3.1.4(postcss@8.4.41)(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)) + postcss-load-config: 3.1.4(postcss@8.4.41)(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)) postcss-safe-parser: 6.0.0(postcss@8.4.41) postcss-selector-parser: 6.1.0 semver: 7.6.2 @@ -7362,11 +7423,11 @@ snapshots: cross-spawn: 7.0.3 signal-exit: 4.1.0 - formsnap@1.0.1(svelte@5.0.0-next.175)(sveltekit-superforms@2.17.0(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)): + formsnap@1.0.1(svelte@5.0.0-next.175)(sveltekit-superforms@2.17.0(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)): dependencies: nanoid: 5.0.7 svelte: 5.0.0-next.175 - sveltekit-superforms: 2.17.0(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175) + sveltekit-superforms: 2.17.0(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175) forwarded@0.2.0: {} @@ -7498,11 +7559,11 @@ snapshots: hex-rgb@4.3.0: {} - hono-rate-limiter@0.4.0(hono@4.5.6): + hono-rate-limiter@0.4.0(hono@4.5.8): dependencies: - hono: 4.5.6 + hono: 4.5.8 - hono@4.5.6: {} + hono@4.5.8: {} html-entities@2.5.2: {} @@ -7941,6 +8002,10 @@ snapshots: open-props@1.7.5: {} + openapi3-ts@4.3.3: + dependencies: + yaml: 2.5.0 + optionator@0.9.4: dependencies: deep-is: 0.1.4 @@ -8217,21 +8282,21 @@ snapshots: '@csstools/utilities': 1.0.0(postcss@8.4.41) postcss: 8.4.41 - postcss-load-config@3.1.4(postcss@8.4.41)(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)): + postcss-load-config@3.1.4(postcss@8.4.41)(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)): dependencies: lilconfig: 2.1.0 yaml: 1.10.2 optionalDependencies: postcss: 8.4.41 - ts-node: 10.9.2(@types/node@20.16.0)(typescript@5.5.4) + ts-node: 10.9.2(@types/node@20.16.1)(typescript@5.5.4) - postcss-load-config@4.0.2(postcss@8.4.41)(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)): + postcss-load-config@4.0.2(postcss@8.4.41)(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)): dependencies: lilconfig: 3.1.1 yaml: 2.4.3 optionalDependencies: postcss: 8.4.41 - ts-node: 10.9.2(@types/node@20.16.0)(typescript@5.5.4) + ts-node: 10.9.2(@types/node@20.16.1)(typescript@5.5.4) postcss-load-config@5.1.0(jiti@1.21.6)(postcss@8.4.41)(tsx@4.17.0): dependencies: @@ -8517,28 +8582,6 @@ snapshots: dependencies: glob: 7.2.3 - rollup@4.17.2: - dependencies: - '@types/estree': 1.0.5 - optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.17.2 - '@rollup/rollup-android-arm64': 4.17.2 - '@rollup/rollup-darwin-arm64': 4.17.2 - '@rollup/rollup-darwin-x64': 4.17.2 - '@rollup/rollup-linux-arm-gnueabihf': 4.17.2 - '@rollup/rollup-linux-arm-musleabihf': 4.17.2 - '@rollup/rollup-linux-arm64-gnu': 4.17.2 - '@rollup/rollup-linux-arm64-musl': 4.17.2 - '@rollup/rollup-linux-powerpc64le-gnu': 4.17.2 - '@rollup/rollup-linux-riscv64-gnu': 4.17.2 - '@rollup/rollup-linux-s390x-gnu': 4.17.2 - '@rollup/rollup-linux-x64-gnu': 4.17.2 - '@rollup/rollup-linux-x64-musl': 4.17.2 - '@rollup/rollup-win32-arm64-msvc': 4.17.2 - '@rollup/rollup-win32-ia32-msvc': 4.17.2 - '@rollup/rollup-win32-x64-msvc': 4.17.2 - fsevents: 2.3.3 - rollup@4.18.1: dependencies: '@types/estree': 1.0.5 @@ -8561,6 +8604,28 @@ snapshots: '@rollup/rollup-win32-x64-msvc': 4.18.1 fsevents: 2.3.3 + rollup@4.21.0: + dependencies: + '@types/estree': 1.0.5 + optionalDependencies: + '@rollup/rollup-android-arm-eabi': 4.21.0 + '@rollup/rollup-android-arm64': 4.21.0 + '@rollup/rollup-darwin-arm64': 4.21.0 + '@rollup/rollup-darwin-x64': 4.21.0 + '@rollup/rollup-linux-arm-gnueabihf': 4.21.0 + '@rollup/rollup-linux-arm-musleabihf': 4.21.0 + '@rollup/rollup-linux-arm64-gnu': 4.21.0 + '@rollup/rollup-linux-arm64-musl': 4.21.0 + '@rollup/rollup-linux-powerpc64le-gnu': 4.21.0 + '@rollup/rollup-linux-riscv64-gnu': 4.21.0 + '@rollup/rollup-linux-s390x-gnu': 4.21.0 + '@rollup/rollup-linux-x64-gnu': 4.21.0 + '@rollup/rollup-linux-x64-musl': 4.21.0 + '@rollup/rollup-win32-arm64-msvc': 4.21.0 + '@rollup/rollup-win32-ia32-msvc': 4.21.0 + '@rollup/rollup-win32-x64-msvc': 4.21.0 + fsevents: 2.3.3 + run-parallel@1.2.0: dependencies: queue-microtask: 1.2.3 @@ -8810,7 +8875,7 @@ snapshots: supports-preserve-symlinks-flag@1.0.0: {} - svelte-check@3.8.5(postcss-load-config@5.1.0(jiti@1.21.6)(postcss@8.4.41)(tsx@4.17.0))(postcss@8.4.41)(sass@1.77.8)(svelte@5.0.0-next.175): + svelte-check@3.8.6(postcss-load-config@5.1.0(jiti@1.21.6)(postcss@8.4.41)(tsx@4.17.0))(postcss@8.4.41)(sass@1.77.8)(svelte@5.0.0-next.175): dependencies: '@jridgewell/trace-mapping': 0.3.25 chokidar: 3.6.0 @@ -8947,19 +9012,19 @@ snapshots: magic-string: 0.30.10 zimmerframe: 1.1.2 - sveltekit-flash-message@2.4.4(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175): + sveltekit-flash-message@2.4.4(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175): dependencies: - '@sveltejs/kit': 2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + '@sveltejs/kit': 2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) svelte: 5.0.0-next.175 - sveltekit-rate-limiter@0.5.2(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8))): + sveltekit-rate-limiter@0.5.2(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8))): dependencies: '@isaacs/ttlcache': 1.4.1 - '@sveltejs/kit': 2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + '@sveltejs/kit': 2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) - sveltekit-superforms@2.17.0(@sveltejs/kit@2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175): + sveltekit-superforms@2.17.0(@sveltejs/kit@2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175): dependencies: - '@sveltejs/kit': 2.5.22(@sveltejs/vite-plugin-svelte@3.1.1(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)) + '@sveltejs/kit': 2.5.24(@sveltejs/vite-plugin-svelte@3.1.2(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)))(svelte@5.0.0-next.175)(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)) devalue: 5.0.0 just-clone: 6.2.0 memoize-weak: 1.0.2 @@ -8984,16 +9049,16 @@ snapshots: tailwind-merge@2.5.2: {} - tailwind-variants@0.2.1(tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4))): + tailwind-variants@0.2.1(tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4))): dependencies: tailwind-merge: 2.5.2 - tailwindcss: 3.4.10(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)) + tailwindcss: 3.4.10(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)) - tailwindcss-animate@1.0.7(tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4))): + tailwindcss-animate@1.0.7(tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4))): dependencies: - tailwindcss: 3.4.10(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)) + tailwindcss: 3.4.10(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)) - tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)): + tailwindcss@3.4.10(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)): dependencies: '@alloc/quick-lru': 5.2.0 arg: 5.0.2 @@ -9012,7 +9077,7 @@ snapshots: postcss: 8.4.41 postcss-import: 15.1.0(postcss@8.4.41) postcss-js: 4.0.1(postcss@8.4.41) - postcss-load-config: 4.0.2(postcss@8.4.41)(ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4)) + postcss-load-config: 4.0.2(postcss@8.4.41)(ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4)) postcss-nested: 6.0.1(postcss@8.4.41) postcss-selector-parser: 6.1.0 resolve: 1.22.8 @@ -9079,14 +9144,14 @@ snapshots: ts-interface-checker@0.1.13: {} - ts-node@10.9.2(@types/node@20.16.0)(typescript@5.5.4): + ts-node@10.9.2(@types/node@20.16.1)(typescript@5.5.4): dependencies: '@cspotcode/source-map-support': 0.8.1 '@tsconfig/node10': 1.0.11 '@tsconfig/node12': 1.0.11 '@tsconfig/node14': 1.0.3 '@tsconfig/node16': 1.0.4 - '@types/node': 20.16.0 + '@types/node': 20.16.1 acorn: 8.11.3 acorn-walk: 8.3.2 arg: 4.1.3 @@ -9193,13 +9258,13 @@ snapshots: transitivePeerDependencies: - rollup - vite-node@1.6.0(@types/node@20.16.0)(sass@1.77.8): + vite-node@1.6.0(@types/node@20.16.1)(sass@1.77.8): dependencies: cac: 6.7.14 debug: 4.3.4 pathe: 1.1.2 picocolors: 1.0.0 - vite: 5.4.1(@types/node@20.16.0)(sass@1.77.8) + vite: 5.4.2(@types/node@20.16.1)(sass@1.77.8) transitivePeerDependencies: - '@types/node' - less @@ -9211,21 +9276,21 @@ snapshots: - supports-color - terser - vite@5.4.1(@types/node@20.16.0)(sass@1.77.8): + vite@5.4.2(@types/node@20.16.1)(sass@1.77.8): dependencies: esbuild: 0.21.5 postcss: 8.4.41 - rollup: 4.17.2 + rollup: 4.21.0 optionalDependencies: - '@types/node': 20.16.0 + '@types/node': 20.16.1 fsevents: 2.3.3 sass: 1.77.8 - vitefu@0.2.5(vite@5.4.1(@types/node@20.16.0)(sass@1.77.8)): + vitefu@0.2.5(vite@5.4.2(@types/node@20.16.1)(sass@1.77.8)): optionalDependencies: - vite: 5.4.1(@types/node@20.16.0)(sass@1.77.8) + vite: 5.4.2(@types/node@20.16.1)(sass@1.77.8) - vitest@1.6.0(@types/node@20.16.0)(sass@1.77.8): + vitest@1.6.0(@types/node@20.16.1)(sass@1.77.8): dependencies: '@vitest/expect': 1.6.0 '@vitest/runner': 1.6.0 @@ -9244,11 +9309,11 @@ snapshots: strip-literal: 2.1.0 tinybench: 2.8.0 tinypool: 0.8.4 - vite: 5.4.1(@types/node@20.16.0)(sass@1.77.8) - vite-node: 1.6.0(@types/node@20.16.0)(sass@1.77.8) + vite: 5.4.2(@types/node@20.16.1)(sass@1.77.8) + vite-node: 1.6.0(@types/node@20.16.1)(sass@1.77.8) why-is-node-running: 2.2.2 optionalDependencies: - '@types/node': 20.16.0 + '@types/node': 20.16.1 transitivePeerDependencies: - less - lightningcss @@ -9317,6 +9382,8 @@ snapshots: yaml@2.4.3: {} + yaml@2.5.0: {} + yargs-parser@18.1.3: dependencies: camelcase: 5.3.1 diff --git a/src/app.d.ts b/src/app.d.ts index 731a21d..6ab483d 100644 --- a/src/app.d.ts +++ b/src/app.d.ts @@ -1,6 +1,6 @@ -import { ApiClient } from './lib/server/api'; import type { User } from 'lucia'; -import { parseApiResponse } from '$lib/utils/api'; +import type { ApiClient } from '$lib/server/api'; +import type { parseApiResponse } from '$lib/utils/api'; // See https://kit.svelte.dev/docs/types#app // for information about these interfaces @@ -41,9 +41,12 @@ declare global { interface Document { // eslint-disable-next-line @typescript-eslint/no-explicit-any - startViewTransition: (callback: any) => void; // Add your custom property/method here + // biome-ignore lint/suspicious/noExplicitAny: + startViewTransition: (callback: never) => void; // Add your custom property/method here } } // THIS IS IMPORTANT!!! +// biome-ignore lint/complexity/noUselessEmptyExport: +// biome-ignore lint/style/useExportType: export {}; diff --git a/src/hooks.server.ts b/src/hooks.server.ts index 295a8f4..6b91f8b 100644 --- a/src/hooks.server.ts +++ b/src/hooks.server.ts @@ -28,7 +28,7 @@ const apiClient: Handle = async ({ event, resolve }) => { /* ----------------------------- Auth functions ----------------------------- */ async function getAuthedUser() { const { data } = await api.user.$get().then(parseApiResponse) - return data && data.user; + return data?.user; } async function getAuthedUserOrThrow() { diff --git a/src/lib/dtos/id-params.dto.ts b/src/lib/dtos/id-params.dto.ts new file mode 100644 index 0000000..8a4aa50 --- /dev/null +++ b/src/lib/dtos/id-params.dto.ts @@ -0,0 +1,5 @@ +import { z } from "zod"; + +export const IdParamsDto = z.object({ + id: z.trim().number(), +}); \ No newline at end of file diff --git a/src/lib/server/api/controllers/collection.controller.ts b/src/lib/server/api/controllers/collection.controller.ts new file mode 100644 index 0000000..7bc8379 --- /dev/null +++ b/src/lib/server/api/controllers/collection.controller.ts @@ -0,0 +1,31 @@ +import 'reflect-metadata'; +import { Hono } from 'hono'; +import { inject, injectable } from 'tsyringe'; +import { requireAuth } from "../middleware/auth.middleware"; +import type { HonoTypes } from '../types'; +import type { Controller } from '../interfaces/controller.interface'; +import {CollectionsService} from "$lib/server/api/services/collections.service"; + +@injectable() +export class CollectionController implements Controller { + controller = new Hono(); + + constructor( + @inject(CollectionsService) private readonly collectionsService: CollectionsService, + ) { } + + routes() { + return this.controller + .get('/', requireAuth, async (c) => { + const user = c.var.user; + const collections = await this.collectionsService.findAllByUserId(user.id); + console.log('collections service', collections) + return c.json({ collections }); + }) + .get('/:cuid', requireAuth, async (c) => { + const cuid = c.req.param('cuid'); + const user = await this.collectionsService.findOneByCuid(cuid); + return c.json({ user }); + }); + } +} diff --git a/src/lib/server/api/controllers/iam.controller.ts b/src/lib/server/api/controllers/iam.controller.ts index a830e3b..2cd0a08 100644 --- a/src/lib/server/api/controllers/iam.controller.ts +++ b/src/lib/server/api/controllers/iam.controller.ts @@ -1,48 +1,54 @@ -import { Hono } from 'hono'; -import { inject, injectable } from 'tsyringe'; -import { setCookie } from 'hono/cookie'; -import { zValidator } from '@hono/zod-validator'; -import type { HonoTypes } from '../types'; -import { requireAuth } from "../middleware/auth.middleware"; -import type { Controller } from '../interfaces/controller.interface'; -import {IamService} from "$lib/server/api/services/iam.service"; -import {LuciaProvider} from "$lib/server/api/providers"; -import {limiter} from "$lib/server/api/middleware/rate-limiter.middleware"; -import {updateProfileDto} from "$lib/dtos/update-profile.dto"; -import {updateEmailDto} from "$lib/dtos/update-email.dto"; +import { Hono } from 'hono' +import { inject, injectable } from 'tsyringe' +import { setCookie } from 'hono/cookie' +import { zValidator } from '@hono/zod-validator' +import type { HonoTypes } from '../types' +import { requireAuth } from '../middleware/auth.middleware' +import type { Controller } from '$lib/server/api/interfaces/controller.interface' +import { IamService } from '$lib/server/api/services/iam.service' +import { LuciaProvider } from '$lib/server/api/providers' +import { limiter } from '$lib/server/api/middleware/rate-limiter.middleware' +import { updateProfileDto } from '$lib/dtos/update-profile.dto' +import { updateEmailDto } from '$lib/dtos/update-email.dto' +import { StatusCodes } from '$lib/constants/status-codes' @injectable() export class IamController implements Controller { - controller = new Hono(); + controller = new Hono() constructor( - @inject(IamService) private readonly iamService: IamService, - @inject(LuciaProvider) private lucia: LuciaProvider - ) { } + @inject(IamService) private readonly iamService: IamService, + @inject(LuciaProvider) private lucia: LuciaProvider, + ) {} routes() { return this.controller - .get('/me', requireAuth, async (c) => { - const user = c.var.user; - return c.json({ user }); + .get('/', requireAuth, async (c) => { + const user = c.var.user + return c.json({ user }) }) - .post('/update/profile', requireAuth, zValidator('json', updateProfileDto), limiter({ limit: 10, minutes: 60 }), async (c) => { - const user = c.var.user; - console.log('user id', user.id); - const { firstName, lastName, username } = c.req.valid('json'); - const updatedUser = await this.iamService.updateProfile(user.id, { firstName, lastName, username }); - return c.json({ status: 'success' }); + .put('/update/profile', requireAuth, zValidator('json', updateProfileDto), limiter({ limit: 30, minutes: 60 }), async (c) => { + const user = c.var.user + const { firstName, lastName, username } = c.req.valid('json') + const updatedUser = await this.iamService.updateProfile(user.id, { firstName, lastName, username }) + if (!updatedUser) { + return c.json("Username already in use", StatusCodes.BAD_REQUEST); + } + return c.json({ user: updatedUser }, StatusCodes.OK) }) .post('/update/email', requireAuth, zValidator('json', updateEmailDto), limiter({ limit: 10, minutes: 60 }), async (c) => { - const user = c.var.user; - const { email } = c.req.valid('json'); - await this.iamService.updateEmail(user.id, { email }); - return c.json({ status: 'success' }); + const user = c.var.user + const { email } = c.req.valid('json') + const updatedUser = await this.iamService.updateEmail(user.id, { email }) + if (!updatedUser) { + return c.json("Email already in use", StatusCodes.BAD_REQUEST); + } + return c.json({ user: updatedUser }, StatusCodes.OK) }) .post('/logout', requireAuth, async (c) => { - const sessionId = c.var.session.id; - await this.iamService.logout(sessionId); - const sessionCookie = this.lucia.createBlankSessionCookie(); + const sessionId = c.var.session.id + await this.iamService.logout(sessionId) + const sessionCookie = this.lucia.createBlankSessionCookie() setCookie(c, sessionCookie.name, sessionCookie.value, { path: sessionCookie.attributes.path, maxAge: sessionCookie.attributes.maxAge, @@ -50,9 +56,9 @@ export class IamController implements Controller { sameSite: sessionCookie.attributes.sameSite as any, secure: sessionCookie.attributes.secure, httpOnly: sessionCookie.attributes.httpOnly, - expires: sessionCookie.attributes.expires - }); - return c.json({ status: 'success' }); - }); + expires: sessionCookie.attributes.expires, + }) + return c.json({ status: 'success' }) + }) } } diff --git a/src/lib/server/api/controllers/user.controller.ts b/src/lib/server/api/controllers/user.controller.ts index 45de16c..90a0cc8 100644 --- a/src/lib/server/api/controllers/user.controller.ts +++ b/src/lib/server/api/controllers/user.controller.ts @@ -1,15 +1,17 @@ import 'reflect-metadata'; import { Hono } from 'hono'; -import { injectable } from 'tsyringe'; +import { inject, injectable } from 'tsyringe'; import { requireAuth } from "../middleware/auth.middleware"; import type { HonoTypes } from '../types'; import type { Controller } from '../interfaces/controller.interface'; +import {UsersService} from "$lib/server/api/services/users.service"; @injectable() export class UserController implements Controller { controller = new Hono(); constructor( + @inject(UsersService) private readonly usersService: UsersService ) { } routes() { @@ -20,12 +22,12 @@ export class UserController implements Controller { }) .get('/:id', requireAuth, async (c) => { const id = c.req.param('id'); - const user = c.var.user; + const user = await this.usersService.findOneById(id); return c.json({ user }); }) .get('/username/:userName', requireAuth, async (c) => { const userName = c.req.param('userName'); - const user = c.var.user; + const user = await this.usersService.findOneByUsername(userName); return c.json({ user }); }); } diff --git a/src/lib/server/api/controllers/wishlist.controller.ts b/src/lib/server/api/controllers/wishlist.controller.ts new file mode 100644 index 0000000..3a8dbb7 --- /dev/null +++ b/src/lib/server/api/controllers/wishlist.controller.ts @@ -0,0 +1,31 @@ +import 'reflect-metadata'; +import { Hono } from 'hono'; +import { inject, injectable } from 'tsyringe'; +import { requireAuth } from "../middleware/auth.middleware"; +import type { HonoTypes } from '../types'; +import type { Controller } from '../interfaces/controller.interface'; +import {WishlistsService} from "$lib/server/api/services/wishlists.service"; + +@injectable() +export class WishlistController implements Controller { + controller = new Hono(); + + constructor( + @inject(WishlistsService) private readonly wishlistsService: WishlistsService + ) { } + + routes() { + return this.controller + .get('/', requireAuth, async (c) => { + const user = c.var.user; + const wishlists = await this.wishlistsService.findAllByUserId(user.id); + return c.json({ wishlists }); + }) + .get('/:cuid', requireAuth, async (c) => { + const cuid = c.req.param('cuid') + console.log(cuid) + const wishlist = await this.wishlistsService.findOneByCuid(cuid) + return c.json({ wishlist }); + }); + } +} diff --git a/src/lib/server/api/index.ts b/src/lib/server/api/index.ts index 24fd321..9c22833 100644 --- a/src/lib/server/api/index.ts +++ b/src/lib/server/api/index.ts @@ -10,6 +10,8 @@ import { IamController } from './controllers/iam.controller'; import { LoginController } from './controllers/login.controller'; import {UserController} from "$lib/server/api/controllers/user.controller"; import {SignupController} from "$lib/server/api/controllers/signup.controller"; +import {WishlistController} from "$lib/server/api/controllers/wishlist.controller"; +import {CollectionController} from "$lib/server/api/controllers/collection.controller"; /* ----------------------------------- Api ---------------------------------- */ const app = new Hono().basePath('/api'); @@ -40,6 +42,8 @@ const routes = app .route('/user', container.resolve(UserController).routes()) .route('/login', container.resolve(LoginController).routes()) .route('/signup', container.resolve(SignupController).routes()) + .route('/wishlists', container.resolve(WishlistController).routes()) + .route('/collections', container.resolve(CollectionController).routes()) .get('/', (c) => c.json({ message: 'Server is healthy' })); /* -------------------------------------------------------------------------- */ diff --git a/src/lib/server/api/infrastructure/auth/lucia.ts b/src/lib/server/api/infrastructure/auth/lucia.ts index 63a758c..9fb1eb9 100644 --- a/src/lib/server/api/infrastructure/auth/lucia.ts +++ b/src/lib/server/api/infrastructure/auth/lucia.ts @@ -21,8 +21,8 @@ export const lucia = new Lucia(adapter, { // ...attributes, username: attributes.username, email: attributes.email, - firstName: attributes.firstName, - lastName: attributes.lastName, + firstName: attributes.first_name, + lastName: attributes.last_name, theme: attributes.theme, }; }, @@ -54,8 +54,8 @@ declare module 'lucia' { interface DatabaseUserAttributes { username: string; email: string; - firstName: string; - lastName: string; + first_name: string; + last_name: string; theme: string; } } diff --git a/src/lib/server/api/infrastructure/database/schemas/collections.schema.ts b/src/lib/server/api/infrastructure/database/schemas/collections.schema.ts new file mode 100644 index 0000000..84d7ecc --- /dev/null +++ b/src/lib/server/api/infrastructure/database/schemas/collections.schema.ts @@ -0,0 +1,25 @@ +import { createInsertSchema, createSelectSchema } from 'drizzle-zod' +import type { z } from 'zod' +import { collections } from '$lib/server/api/infrastructure/database/tables' + +export const InsertCollectionSchema = createInsertSchema(collections, { + name: (schema) => schema.name.trim() + .min(3, { message: 'Must be at least 3 characters' }) + .max(64, { message: 'Must be less than 64 characters' }).optional(), +}).omit({ + id: true, + cuid: true, + createdAt: true, + updatedAt: true, +}) + +export type InsertCollectionSchema = z.infer + +export const SelectCollectionSchema = createSelectSchema(collections).omit({ + id: true, + user_id: true, + createdAt: true, + updatedAt: true, +}) + +export type SelectUserSchema = z.infer diff --git a/src/lib/server/api/infrastructure/database/schemas/users.schemas.ts b/src/lib/server/api/infrastructure/database/schemas/users.schemas.ts new file mode 100644 index 0000000..96564a5 --- /dev/null +++ b/src/lib/server/api/infrastructure/database/schemas/users.schemas.ts @@ -0,0 +1,24 @@ +import { createInsertSchema, createSelectSchema } from 'drizzle-zod' +import type { z } from 'zod' +import { usersTable } from '$lib/server/api/infrastructure/database/tables' + +export const InsertUserSchema = createInsertSchema(usersTable, { + email: (schema) => schema.email.max(64).email().optional(), + username: (schema) => + schema.username.min(3, { message: 'Must be at least 3 characters' }).max(50, { message: 'Must be less than 50 characters' }).optional(), + first_name: (schema) => + schema.first_name.trim().min(3, { message: 'Must be at least 3 characters' }).max(64, { message: 'Must be less than 64 characters' }).optional(), + last_name: (schema) => + schema.last_name.trim().min(3, { message: 'Must be at least 3 characters' }).max(64, { message: 'Must be less than 64 characters' }).optional(), +}).omit({ + id: true, + cuid: true, + createdAt: true, + updatedAt: true, +}) + +export type InsertUserSchema = z.infer + +export const SelectUserSchema = createSelectSchema(usersTable) + +export type SelectUserSchema = z.infer diff --git a/src/lib/server/api/infrastructure/database/tables/users.table.ts b/src/lib/server/api/infrastructure/database/tables/users.table.ts index 77224f4..83f6fef 100644 --- a/src/lib/server/api/infrastructure/database/tables/users.table.ts +++ b/src/lib/server/api/infrastructure/database/tables/users.table.ts @@ -1,6 +1,6 @@ import { boolean, pgTable, text, uuid } from 'drizzle-orm/pg-core'; -import { createId as cuid2 } from '@paralleldrive/cuid2'; import { type InferSelectModel, relations } from 'drizzle-orm'; +import { createId as cuid2 } from '@paralleldrive/cuid2'; import { timestamps } from '../utils'; import {user_roles} from './userRoles'; diff --git a/src/lib/server/api/repositories/collections.repository.ts b/src/lib/server/api/repositories/collections.repository.ts index e1fd4f1..72db342 100644 --- a/src/lib/server/api/repositories/collections.repository.ts +++ b/src/lib/server/api/repositories/collections.repository.ts @@ -17,12 +17,36 @@ export class CollectionsRepository { async findOneById(id: string) { return this.db.query.collections.findFirst({ - where: eq(collections.id, id) + where: eq(collections.id, id), + columns: { + cuid: true, + name: true + } + }) + } + + async findOneByCuid(cuid: string) { + return this.db.query.collections.findFirst({ + where: eq(collections.cuid, cuid), + columns: { + cuid: true, + name: true + } }) } async findOneByUserId(userId: string) { return this.db.query.collections.findFirst({ + where: eq(collections.user_id, userId), + columns: { + cuid: true, + name: true + } + }) + } + + async findAllByUserId(userId: string) { + return this.db.query.collections.findMany({ where: eq(collections.user_id, userId) }) } diff --git a/src/lib/server/api/repositories/wishlists.repository.ts b/src/lib/server/api/repositories/wishlists.repository.ts index ffa0c95..4ea4076 100644 --- a/src/lib/server/api/repositories/wishlists.repository.ts +++ b/src/lib/server/api/repositories/wishlists.repository.ts @@ -17,19 +17,41 @@ export class WishlistsRepository { async findOneById(id: string) { return this.db.query.wishlists.findFirst({ - where: eq(wishlists.id, id) + where: eq(wishlists.id, id), + columns: { + cuid: true, + name: true + } + }) + } + + async findOneByCuid(cuid: string) { + return this.db.query.wishlists.findFirst({ + where: eq(wishlists.cuid, cuid), + columns: { + cuid: true, + name: true + } }) } async findOneByUserId(userId: string) { return this.db.query.wishlists.findFirst({ - where: eq(wishlists.user_id, userId) + where: eq(wishlists.user_id, userId), + columns: { + cuid: true, + name: true + } }) } async findAllByUserId(userId: string) { return this.db.query.wishlists.findMany({ - where: eq(wishlists.user_id, userId) + where: eq(wishlists.user_id, userId), + columns: { + cuid: true, + name: true + } }) } diff --git a/src/lib/server/api/services/collections.service.ts b/src/lib/server/api/services/collections.service.ts index fb39773..4e0a009 100644 --- a/src/lib/server/api/services/collections.service.ts +++ b/src/lib/server/api/services/collections.service.ts @@ -8,6 +8,22 @@ export class CollectionsService { @inject(CollectionsRepository) private readonly collectionsRepository: CollectionsRepository ) { } + async findOneByUserId(userId: string) { + return this.collectionsRepository.findOneByUserId(userId); + } + + async findAllByUserId(userId: string) { + return this.collectionsRepository.findAllByUserId(userId); + } + + async findOneById(id: string) { + return this.collectionsRepository.findOneById(id); + } + + async findOneByCuid(cuid: string) { + return this.collectionsRepository.findOneByCuid(cuid); + } + async createEmptyNoName(userId: string) { return this.createEmpty(userId, null); } diff --git a/src/lib/server/api/services/iam.service.ts b/src/lib/server/api/services/iam.service.ts index 0c37952..3455b4f 100644 --- a/src/lib/server/api/services/iam.service.ts +++ b/src/lib/server/api/services/iam.service.ts @@ -1,8 +1,8 @@ +import type { UpdateEmailDto } from "$lib/dtos/update-email.dto"; +import type { UpdateProfileDto } from "$lib/dtos/update-profile.dto"; +import { UsersService } from "$lib/server/api/services/users.service"; import { inject, injectable } from 'tsyringe'; -import { LuciaProvider } from '../providers/lucia.provider'; -import {UsersService} from "$lib/server/api/services/users.service"; -import type {UpdateProfileDto} from "$lib/dtos/update-profile.dto"; -import type {UpdateEmailDto} from "$lib/dtos/update-email.dto"; +import { LuciaProvider } from '$lib/server/api/providers'; /* -------------------------------------------------------------------------- */ /* Service */ @@ -55,8 +55,15 @@ export class IamService { } async updateEmail(userId: string, data: UpdateEmailDto) { + const { email } = data; + + const existingUserEmail = await this.usersService.findOneByEmail(email); + if (existingUserEmail && existingUserEmail.id !== userId) { + return null; + } + return this.usersService.updateUser(userId, { - email: data.email + email, }); } } diff --git a/src/lib/server/api/services/users.service.ts b/src/lib/server/api/services/users.service.ts index e22bad9..a898040 100644 --- a/src/lib/server/api/services/users.service.ts +++ b/src/lib/server/api/services/users.service.ts @@ -61,6 +61,10 @@ export class UsersService { return this.usersRepository.findOneByUsername(username); } + async findOneByEmail(email: string) { + return this.usersRepository.findOneByEmail(email); + } + async findOneById(id: string) { return this.usersRepository.findOneById(id); } diff --git a/src/lib/server/api/services/wishlists.service.ts b/src/lib/server/api/services/wishlists.service.ts index 47aa57a..f7326a1 100644 --- a/src/lib/server/api/services/wishlists.service.ts +++ b/src/lib/server/api/services/wishlists.service.ts @@ -13,6 +13,14 @@ export class WishlistsService { return this.wishlistsRepository.findAllByUserId(userId); } + async findOneById(id: string) { + return this.wishlistsRepository.findOneById(id); + } + + async findOneByCuid(cuid: string) { + return this.wishlistsRepository.findOneByCuid(cuid); + } + async createEmptyNoName(userId: string) { return this.createEmpty(userId, null); } diff --git a/src/lib/utils/api.ts b/src/lib/utils/api.ts index 79c142b..12fb9c5 100644 --- a/src/lib/utils/api.ts +++ b/src/lib/utils/api.ts @@ -4,7 +4,7 @@ export async function parseApiResponse(response: ClientResponse) { if (response.status === 204 || response.headers.get('Content-Length') === '0') { return response.ok ? { data: null, error: null, response } - : { data: null, error: 'An unknown error has occured', response }; + : { data: null, error: 'An unknown error has occurred', response }; } if (response.ok) { diff --git a/src/lib/zodValidation.ts b/src/lib/zodValidation.ts index da79b49..3a5fe0d 100644 --- a/src/lib/zodValidation.ts +++ b/src/lib/zodValidation.ts @@ -28,7 +28,7 @@ export function IntegerString> return z.preprocess( (value) => typeof value === 'string' - ? parseInt(value, 10) + ? Number.parseInt(value, 10) : typeof value === 'number' ? value : undefined, diff --git a/src/routes/(app)/(protected)/profile/+page.server.ts b/src/routes/(app)/(protected)/profile/+page.server.ts index 6c692fc..69c6bc8 100644 --- a/src/routes/(app)/(protected)/profile/+page.server.ts +++ b/src/routes/(app)/(protected)/profile/+page.server.ts @@ -20,18 +20,19 @@ export const load: PageServerLoad = async (event) => { if (!authedUser) { throw redirect(302, '/login', notSignedInMessage, event); } + + console.log('authedUser', authedUser); // if (userNotAuthenticated(user, session)) { // redirect(302, '/login', notSignedInMessage, event); // } - // // const dbUser = await db.query.usersTable.findFirst({ // where: eq(usersTable.id, user!.id!), // }); const profileForm = await superValidate(zod(profileSchema), { defaults: { - firstName: authedUser?.first_name ?? '', - lastName: authedUser?.last_name ?? '', + firstName: authedUser?.firstName ?? '', + lastName: authedUser?.lastName ?? '', username: authedUser?.username ?? '', }, }); @@ -72,8 +73,11 @@ export const actions: Actions = { const form = await superValidate(event, zod(updateProfileDto)); - const { error } = await locals.api.user.$post({ json: form.data }).then(locals.parseApiResponse); - if (error) return setError(form, 'username', error); + const { error } = await locals.api.me.update.profile.$put({ json: form.data }).then(locals.parwseApiResponse); + console.log('data from profile update', error); + if (error) { + return setError(form, 'username', error); + } if (!form.valid) { return fail(400, { @@ -81,36 +85,6 @@ export const actions: Actions = { }); } - try { - console.log('updating profile'); - - const user = event.locals.user; - const newUsername = form.data.username; - const existingUser = await db.query.usersTable.findFirst({ - where: eq(usersTable.username, newUsername), - }); - - if (existingUser && existingUser.id !== user.id) { - return setError(form, 'username', 'That username is already taken'); - } - - await db - .update(usersTable) - .set({ - first_name: form.data.firstName, - last_name: form.data.lastName, - username: form.data.username, - }) - .where(eq(usersTable.id, user.id)); - } catch (e) { - // @ts-expect-error - if (e.message === `AUTH_INVALID_USER_ID`) { - // invalid user id - console.error(e); - } - return setError(form, 'There was a problem updating your profile.'); - } - console.log('profile updated successfully'); return message(form, { type: 'success', message: 'Profile updated successfully!' }); }, diff --git a/src/routes/(app)/(protected)/wishlists/[id]/+page.server.ts b/src/routes/(app)/(protected)/wishlists/[cuid]/+page.server.ts similarity index 81% rename from src/routes/(app)/(protected)/wishlists/[id]/+page.server.ts rename to src/routes/(app)/(protected)/wishlists/[cuid]/+page.server.ts index 7d5f996..abaf1d3 100644 --- a/src/routes/(app)/(protected)/wishlists/[id]/+page.server.ts +++ b/src/routes/(app)/(protected)/wishlists/[cuid]/+page.server.ts @@ -4,23 +4,33 @@ import { zod } from 'sveltekit-superforms/adapters'; import { superValidate } from 'sveltekit-superforms/server'; import { redirect } from 'sveltekit-flash-message/server'; import { modifyListGameSchema } from '$lib/validations/zod-schemas'; -import db from '../../../../../db'; +import { db } from '$lib/server/api/infrastructure/database'; import { notSignedInMessage } from '$lib/flashMessages.js'; -import { games, wishlist_items, wishlists } from '$db/schema'; +import { games, wishlist_items, wishlists } from '$lib/server/api/infrastructure/database/tables'; import { userNotAuthenticated } from '$lib/server/auth-utils'; export async function load(event) { const { params, locals } = event; - const { user, session } = locals; - const { id } = params; - if (userNotAuthenticated(user, session)) { - redirect(302, '/login', notSignedInMessage, event); + const { cuid } = params; + + const authedUser = await locals.getAuthedUser(); + if (!authedUser) { + throw redirect(302, '/login', notSignedInMessage, event); } try { - const wishlist = await db.query.wishlists.findMany({ - where: and(eq(wishlists.user_id, user!.id!), eq(wishlists.cuid, id)), - }); + const { data, errors } = await locals.api.wishlists[':cuid'].$get({ + param: { cuid } + }).then(locals.parseApiResponse); + // const wishlist = await db.query.wishlists.findMany({ + // where: and(eq(wishlists.user_id, authedUser.id), eq(wishlists.cuid, cuid)), + // }); + if (errors) { + return error(500, 'Failed to fetch wishlist'); + } + console.log('data', data); + const { wishlist } = data; + console.log('wishlist', wishlist); if (!wishlist) { redirect(302, '/404'); diff --git a/src/routes/(app)/(protected)/wishlists/[id]/+page.svelte b/src/routes/(app)/(protected)/wishlists/[cuid]/+page.svelte similarity index 100% rename from src/routes/(app)/(protected)/wishlists/[id]/+page.svelte rename to src/routes/(app)/(protected)/wishlists/[cuid]/+page.svelte diff --git a/src/routes/(app)/+page.server.ts b/src/routes/(app)/+page.server.ts index d554b67..2e54d8b 100644 --- a/src/routes/(app)/+page.server.ts +++ b/src/routes/(app)/+page.server.ts @@ -1,3 +1,4 @@ +import { fail } from '@sveltejs/kit'; import type { MetaTagsProps } from 'svelte-meta-tags'; import { eq } from 'drizzle-orm'; import type { PageServerLoad } from './$types'; @@ -43,37 +44,24 @@ export const load: PageServerLoad = async (event) => { }); if (authedUser) { - const dbUser = await db.query.usersTable.findFirst({ - where: eq(usersTable.id, authedUser!.id!), - }); + const { data: wishlistsData, error: wishlistsError } = await locals.api.wishlists.$get().then(locals.parseApiResponse); + const { data: collectionsData, error: collectionsError } = await locals.api.collections.$get().then(locals.parseApiResponse); - console.log('Sending back user details'); - const userWishlists = await db.query.wishlists.findMany({ - columns: { - cuid: true, - name: true, - }, - where: eq(wishlists.user_id, authedUser!.id!), - }); - const userCollection = await db.query.collections.findMany({ - columns: { - cuid: true, - name: true, - }, - where: eq(collections.user_id, authedUser!.id!), - }); + if (wishlistsError || collectionsError) { + return fail(500, 'Failed to fetch wishlists or collections'); + } - console.log('Wishlists', userWishlists); - console.log('Collections', userCollection); + console.log('Wishlists', wishlistsData.wishlists); + console.log('Collections', collectionsData.collections); return { metaTagsChild: metaTags, user: { - firstName: dbUser?.first_name, - lastName: dbUser?.last_name, - username: dbUser?.username, + firstName: authedUser?.firstName, + lastName: authedUser?.lastName, + username: authedUser?.username, }, - wishlists: userWishlists, - collections: userCollection, + wishlists: wishlistsData.wishlists, + collections: collectionsData.collections, }; } diff --git a/src/routes/(auth)/+layout.svelte b/src/routes/(auth)/+layout.svelte index 929065e..5524879 100644 --- a/src/routes/(auth)/+layout.svelte +++ b/src/routes/(auth)/+layout.svelte @@ -1,7 +1,7 @@