Adding flash message to login redirects.

This commit is contained in:
Bradley Shellnut 2024-02-29 17:11:07 -08:00
parent 3596a5dcd6
commit bc95947fd1
15 changed files with 169 additions and 106 deletions

View file

@ -27,14 +27,14 @@
"devDependencies": { "devDependencies": {
"@melt-ui/pp": "^0.3.0", "@melt-ui/pp": "^0.3.0",
"@melt-ui/svelte": "^0.74.3", "@melt-ui/svelte": "^0.74.3",
"@playwright/test": "^1.41.2", "@playwright/test": "^1.42.0",
"@resvg/resvg-js": "^2.6.0", "@resvg/resvg-js": "^2.6.0",
"@sveltejs/adapter-auto": "^3.1.1", "@sveltejs/adapter-auto": "^3.1.1",
"@sveltejs/enhanced-img": "^0.1.8", "@sveltejs/enhanced-img": "^0.1.8",
"@sveltejs/kit": "^2.5.2", "@sveltejs/kit": "^2.5.2",
"@sveltejs/vite-plugin-svelte": "^3.0.2", "@sveltejs/vite-plugin-svelte": "^3.0.2",
"@types/cookie": "^0.6.0", "@types/cookie": "^0.6.0",
"@types/node": "^20.11.20", "@types/node": "^20.11.24",
"@types/pg": "^8.11.2", "@types/pg": "^8.11.2",
"@typescript-eslint/eslint-plugin": "^6.21.0", "@typescript-eslint/eslint-plugin": "^6.21.0",
"@typescript-eslint/parser": "^6.21.0", "@typescript-eslint/parser": "^6.21.0",
@ -51,13 +51,13 @@
"postcss-load-config": "^5.0.3", "postcss-load-config": "^5.0.3",
"postcss-preset-env": "^9.4.0", "postcss-preset-env": "^9.4.0",
"prettier": "^3.2.5", "prettier": "^3.2.5",
"prettier-plugin-svelte": "^3.2.1", "prettier-plugin-svelte": "^3.2.2",
"prisma": "^5.9.1", "prisma": "^5.9.1",
"sass": "^1.71.1", "sass": "^1.71.1",
"satori": "^0.10.13", "satori": "^0.10.13",
"satori-html": "^0.3.2", "satori-html": "^0.3.2",
"svelte": "^4.2.12", "svelte": "^4.2.12",
"svelte-check": "^3.6.5", "svelte-check": "^3.6.6",
"svelte-meta-tags": "^3.1.0", "svelte-meta-tags": "^3.1.0",
"svelte-preprocess": "^5.1.3", "svelte-preprocess": "^5.1.3",
"svelte-sequential-preprocessor": "^2.0.1", "svelte-sequential-preprocessor": "^2.0.1",
@ -106,7 +106,7 @@
"just-kebab-case": "^4.2.0", "just-kebab-case": "^4.2.0",
"loader": "^2.1.1", "loader": "^2.1.1",
"lucia": "3.0.1", "lucia": "3.0.1",
"lucide-svelte": "^0.341.0", "lucide-svelte": "^0.343.0",
"mysql2": "^3.9.2", "mysql2": "^3.9.2",
"nanoid": "^5.0.6", "nanoid": "^5.0.6",
"open-props": "^1.6.20", "open-props": "^1.6.20",

View file

@ -87,8 +87,8 @@ dependencies:
specifier: 3.0.1 specifier: 3.0.1
version: 3.0.1 version: 3.0.1
lucide-svelte: lucide-svelte:
specifier: ^0.341.0 specifier: ^0.343.0
version: 0.341.0(svelte@4.2.12) version: 0.343.0(svelte@4.2.12)
mysql2: mysql2:
specifier: ^3.9.2 specifier: ^3.9.2
version: 3.9.2 version: 3.9.2
@ -137,8 +137,8 @@ devDependencies:
specifier: ^0.74.3 specifier: ^0.74.3
version: 0.74.3(svelte@4.2.12) version: 0.74.3(svelte@4.2.12)
'@playwright/test': '@playwright/test':
specifier: ^1.41.2 specifier: ^1.42.0
version: 1.41.2 version: 1.42.0
'@resvg/resvg-js': '@resvg/resvg-js':
specifier: ^2.6.0 specifier: ^2.6.0
version: 2.6.0 version: 2.6.0
@ -158,8 +158,8 @@ devDependencies:
specifier: ^0.6.0 specifier: ^0.6.0
version: 0.6.0 version: 0.6.0
'@types/node': '@types/node':
specifier: ^20.11.20 specifier: ^20.11.24
version: 20.11.20 version: 20.11.24
'@types/pg': '@types/pg':
specifier: ^8.11.2 specifier: ^8.11.2
version: 8.11.2 version: 8.11.2
@ -209,8 +209,8 @@ devDependencies:
specifier: ^3.2.5 specifier: ^3.2.5
version: 3.2.5 version: 3.2.5
prettier-plugin-svelte: prettier-plugin-svelte:
specifier: ^3.2.1 specifier: ^3.2.2
version: 3.2.1(prettier@3.2.5)(svelte@4.2.12) version: 3.2.2(prettier@3.2.5)(svelte@4.2.12)
prisma: prisma:
specifier: ^5.9.1 specifier: ^5.9.1
version: 5.9.1 version: 5.9.1
@ -227,8 +227,8 @@ devDependencies:
specifier: ^4.2.12 specifier: ^4.2.12
version: 4.2.12 version: 4.2.12
svelte-check: svelte-check:
specifier: ^3.6.5 specifier: ^3.6.6
version: 3.6.5(postcss-load-config@5.0.3)(postcss@8.4.35)(sass@1.71.1)(svelte@4.2.12) version: 3.6.6(postcss-load-config@5.0.3)(postcss@8.4.35)(sass@1.71.1)(svelte@4.2.12)
svelte-meta-tags: svelte-meta-tags:
specifier: ^3.1.0 specifier: ^3.1.0
version: 3.1.0(svelte@4.2.12)(typescript@5.3.3) version: 3.1.0(svelte@4.2.12)(typescript@5.3.3)
@ -252,7 +252,7 @@ devDependencies:
version: 3.4.1(ts-node@10.9.2) version: 3.4.1(ts-node@10.9.2)
ts-node: ts-node:
specifier: ^10.9.2 specifier: ^10.9.2
version: 10.9.2(@types/node@20.11.20)(typescript@5.3.3) version: 10.9.2(@types/node@20.11.24)(typescript@5.3.3)
tslib: tslib:
specifier: ^2.6.1 specifier: ^2.6.1
version: 2.6.2 version: 2.6.2
@ -264,10 +264,10 @@ devDependencies:
version: 5.3.3 version: 5.3.3
vite: vite:
specifier: ^5.1.4 specifier: ^5.1.4
version: 5.1.4(@types/node@20.11.20)(sass@1.71.1) version: 5.1.4(@types/node@20.11.24)(sass@1.71.1)
vitest: vitest:
specifier: ^1.3.1 specifier: ^1.3.1
version: 1.3.1(@types/node@20.11.20)(sass@1.71.1) version: 1.3.1(@types/node@20.11.24)(sass@1.71.1)
zod: zod:
specifier: ^3.22.4 specifier: ^3.22.4
version: 3.22.4 version: 3.22.4
@ -2660,12 +2660,12 @@ packages:
engines: {node: '>=16'} engines: {node: '>=16'}
dev: false dev: false
/@playwright/test@1.41.2: /@playwright/test@1.42.0:
resolution: {integrity: sha512-qQB9h7KbibJzrDpkXkYvsmiDJK14FULCCZgEcoe2AvFAS64oCirWTwzTlAYEbKaRxWs5TFesE1Na6izMv3HfGg==} resolution: {integrity: sha512-2k1HzC28Fs+HiwbJOQDUwrWMttqSLUVdjCqitBOjdCD0svWOMQUVqrXX6iFD7POps6xXAojsX/dGBpKnjZctLA==}
engines: {node: '>=16'} engines: {node: '>=16'}
hasBin: true hasBin: true
dependencies: dependencies:
playwright: 1.41.2 playwright: 1.42.0
dev: true dev: true
/@polka/url@1.0.0-next.24: /@polka/url@1.0.0-next.24:
@ -3264,7 +3264,7 @@ packages:
sirv: 2.0.4 sirv: 2.0.4
svelte: 4.2.12 svelte: 4.2.12
tiny-glob: 0.2.9 tiny-glob: 0.2.9
vite: 5.1.4(@types/node@20.11.20)(sass@1.71.1) vite: 5.1.4(@types/node@20.11.24)(sass@1.71.1)
/@sveltejs/vite-plugin-svelte-inspector@2.0.0(@sveltejs/vite-plugin-svelte@3.0.2)(svelte@4.2.12)(vite@5.1.4): /@sveltejs/vite-plugin-svelte-inspector@2.0.0(@sveltejs/vite-plugin-svelte@3.0.2)(svelte@4.2.12)(vite@5.1.4):
resolution: {integrity: sha512-gjr9ZFg1BSlIpfZ4PRewigrvYmHWbDrq2uvvPB1AmTWKuM+dI1JXQSUu2pIrYLb/QncyiIGkFDFKTwJ0XqQZZg==} resolution: {integrity: sha512-gjr9ZFg1BSlIpfZ4PRewigrvYmHWbDrq2uvvPB1AmTWKuM+dI1JXQSUu2pIrYLb/QncyiIGkFDFKTwJ0XqQZZg==}
@ -3277,7 +3277,7 @@ packages:
'@sveltejs/vite-plugin-svelte': 3.0.2(svelte@4.2.12)(vite@5.1.4) '@sveltejs/vite-plugin-svelte': 3.0.2(svelte@4.2.12)(vite@5.1.4)
debug: 4.3.4 debug: 4.3.4
svelte: 4.2.12 svelte: 4.2.12
vite: 5.1.4(@types/node@20.11.20)(sass@1.71.1) vite: 5.1.4(@types/node@20.11.24)(sass@1.71.1)
transitivePeerDependencies: transitivePeerDependencies:
- supports-color - supports-color
@ -3295,7 +3295,7 @@ packages:
magic-string: 0.30.5 magic-string: 0.30.5
svelte: 4.2.12 svelte: 4.2.12
svelte-hmr: 0.15.3(svelte@4.2.12) svelte-hmr: 0.15.3(svelte@4.2.12)
vite: 5.1.4(@types/node@20.11.20)(sass@1.71.1) vite: 5.1.4(@types/node@20.11.24)(sass@1.71.1)
vitefu: 0.2.5(vite@5.1.4) vitefu: 0.2.5(vite@5.1.4)
transitivePeerDependencies: transitivePeerDependencies:
- supports-color - supports-color
@ -3338,22 +3338,22 @@ packages:
/@types/json-schema@7.0.15: /@types/json-schema@7.0.15:
resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==} resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==}
/@types/node@20.11.20: /@types/node@20.11.24:
resolution: {integrity: sha512-7/rR21OS+fq8IyHTgtLkDK949uzsa6n8BkziAKtPVpugIkO6D+/ooXMvzXxDnZrmtXVfjb1bKQafYpb8s89LOg==} resolution: {integrity: sha512-Kza43ewS3xoLgCEpQrsT+xRo/EJej1y0kVYGiLFE1NEODXGzTfwiC6tXTLMQskn1X4/Rjlh0MQUvx9W+L9long==}
dependencies: dependencies:
undici-types: 5.26.5 undici-types: 5.26.5
/@types/pg@8.11.2: /@types/pg@8.11.2:
resolution: {integrity: sha512-G2Mjygf2jFMU/9hCaTYxJrwdObdcnuQde1gndooZSOHsNSaCehAuwc7EIuSA34Do8Jx2yZ19KtvW8P0j4EuUXw==} resolution: {integrity: sha512-G2Mjygf2jFMU/9hCaTYxJrwdObdcnuQde1gndooZSOHsNSaCehAuwc7EIuSA34Do8Jx2yZ19KtvW8P0j4EuUXw==}
dependencies: dependencies:
'@types/node': 20.11.20 '@types/node': 20.11.24
pg-protocol: 1.6.0 pg-protocol: 1.6.0
pg-types: 4.0.2 pg-types: 4.0.2
/@types/pg@8.6.6: /@types/pg@8.6.6:
resolution: {integrity: sha512-O2xNmXebtwVekJDD+02udOncjVcMZQuTEQEMpKJ0ZRf5E7/9JJX3izhKUcUifBkyKpljyUM6BTgy2trmviKlpw==} resolution: {integrity: sha512-O2xNmXebtwVekJDD+02udOncjVcMZQuTEQEMpKJ0ZRf5E7/9JJX3izhKUcUifBkyKpljyUM6BTgy2trmviKlpw==}
dependencies: dependencies:
'@types/node': 20.11.20 '@types/node': 20.11.24
pg-protocol: 1.6.0 pg-protocol: 1.6.0
pg-types: 2.2.0 pg-types: 2.2.0
dev: false dev: false
@ -5494,8 +5494,8 @@ packages:
oslo: 1.0.1 oslo: 1.0.1
dev: false dev: false
/lucide-svelte@0.341.0(svelte@4.2.12): /lucide-svelte@0.343.0(svelte@4.2.12):
resolution: {integrity: sha512-RdLUlxgm97pKGS5dKchdhLuxmYBpwpcLvZ5XQH3HPO5rZZU8JvfzFs8vnbZH/tsDeA0UeSzdzZyOYbWkOAbarA==} resolution: {integrity: sha512-TkNQBnKU2+4gJFKZJtYmYt+uSIzqwCJf3x/MemMJyv/1WGW+1sej2aYuxoiIwqy5+0txw+OcGeNJF5sbHd6nxA==}
peerDependencies: peerDependencies:
svelte: ^3 || ^4 || ^5.0.0-next.42 svelte: ^3 || ^4 || ^5.0.0-next.42
dependencies: dependencies:
@ -6066,18 +6066,18 @@ packages:
pathe: 1.1.2 pathe: 1.1.2
dev: true dev: true
/playwright-core@1.41.2: /playwright-core@1.42.0:
resolution: {integrity: sha512-VaTvwCA4Y8kxEe+kfm2+uUUw5Lubf38RxF7FpBxLPmGe5sdNkSg5e3ChEigaGrX7qdqT3pt2m/98LiyvU2x6CA==} resolution: {integrity: sha512-0HD9y8qEVlcbsAjdpBaFjmaTHf+1FeIddy8VJLeiqwhcNqGCBe4Wp2e8knpqiYbzxtxarxiXyNDw2cG8sCaNMQ==}
engines: {node: '>=16'} engines: {node: '>=16'}
hasBin: true hasBin: true
dev: true dev: true
/playwright@1.41.2: /playwright@1.42.0:
resolution: {integrity: sha512-v0bOa6H2GJChDL8pAeLa/LZC4feoAMbSQm1/jF/ySsWWoaNItvrMP7GEkvEEFyCTUYKMxjQKaTSg5up7nR6/8A==} resolution: {integrity: sha512-Ko7YRUgj5xBHbntrgt4EIw/nE//XBHOKVKnBjO1KuZkmkhlbgyggTe5s9hjqQ1LpN+Xg+kHsQyt5Pa0Bw5XpvQ==}
engines: {node: '>=16'} engines: {node: '>=16'}
hasBin: true hasBin: true
dependencies: dependencies:
playwright-core: 1.41.2 playwright-core: 1.42.0
optionalDependencies: optionalDependencies:
fsevents: 2.3.2 fsevents: 2.3.2
dev: true dev: true
@ -6308,7 +6308,7 @@ packages:
dependencies: dependencies:
lilconfig: 2.1.0 lilconfig: 2.1.0
postcss: 8.4.35 postcss: 8.4.35
ts-node: 10.9.2(@types/node@20.11.20)(typescript@5.3.3) ts-node: 10.9.2(@types/node@20.11.24)(typescript@5.3.3)
yaml: 1.10.2 yaml: 1.10.2
dev: true dev: true
@ -6326,7 +6326,7 @@ packages:
dependencies: dependencies:
lilconfig: 3.0.0 lilconfig: 3.0.0
postcss: 8.4.35 postcss: 8.4.35
ts-node: 10.9.2(@types/node@20.11.20)(typescript@5.3.3) ts-node: 10.9.2(@types/node@20.11.24)(typescript@5.3.3)
yaml: 2.3.4 yaml: 2.3.4
/postcss-load-config@5.0.3(postcss@8.4.35): /postcss-load-config@5.0.3(postcss@8.4.35):
@ -6607,8 +6607,8 @@ packages:
engines: {node: '>= 0.8.0'} engines: {node: '>= 0.8.0'}
dev: true dev: true
/prettier-plugin-svelte@3.2.1(prettier@3.2.5)(svelte@4.2.12): /prettier-plugin-svelte@3.2.2(prettier@3.2.5)(svelte@4.2.12):
resolution: {integrity: sha512-ENAPbIxASf2R79IZwgkG5sBdeNA9kLRlXVvKKmTXh79zWTy0KKoT86XO2pHrTitUPINd+iXWy12MRmgzKGVckA==} resolution: {integrity: sha512-ZzzE/wMuf48/1+Lf2Ffko0uDa6pyCfgHV6+uAhtg2U0AAXGrhCSW88vEJNAkAxW5qyrFY1y1zZ4J8TgHrjW++Q==}
peerDependencies: peerDependencies:
prettier: ^3.0.0 prettier: ^3.0.0
svelte: ^3.2.0 || ^4.0.0-next.0 || ^5.0.0-next.0 svelte: ^3.2.0 || ^4.0.0-next.0 || ^5.0.0-next.0
@ -7106,8 +7106,8 @@ packages:
resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==}
engines: {node: '>= 0.4'} engines: {node: '>= 0.4'}
/svelte-check@3.6.5(postcss-load-config@5.0.3)(postcss@8.4.35)(sass@1.71.1)(svelte@4.2.12): /svelte-check@3.6.6(postcss-load-config@5.0.3)(postcss@8.4.35)(sass@1.71.1)(svelte@4.2.12):
resolution: {integrity: sha512-5aLgoQEdadvp8ypvKQ2avhnQ+V9YPQQaWrTFlXFw5g/v8xIQBvo+X/WqxTyD+V/ItDqXg3+abUA53rdDHgUjCA==} resolution: {integrity: sha512-b9q9rOHOMYF3U8XllK7LmXTq1LeWQ98waGfEJzrFutViadkNl1tgdEtxIQ8yuPx+VQ4l7YrknYol+0lfZocaZw==}
hasBin: true hasBin: true
peerDependencies: peerDependencies:
svelte: ^3.55.0 || ^4.0.0-next.0 || ^4.0.0 || ^5.0.0-next.0 svelte: ^3.55.0 || ^4.0.0-next.0 || ^4.0.0 || ^5.0.0-next.0
@ -7491,7 +7491,7 @@ packages:
/ts-interface-checker@0.1.13: /ts-interface-checker@0.1.13:
resolution: {integrity: sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==} resolution: {integrity: sha512-Y/arvbn+rrz3JCKl9C4kVNfTfSm2/mEp5FSz5EsZSANGPSlQrpRI5M4PKF+mJnE52jOO90PnPSc3Ur3bTQw0gA==}
/ts-node@10.9.2(@types/node@20.11.20)(typescript@5.3.3): /ts-node@10.9.2(@types/node@20.11.24)(typescript@5.3.3):
resolution: {integrity: sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==} resolution: {integrity: sha512-f0FFpIdcHgn8zcPSbf1dRevwt047YMnaiJM3u2w2RewrB+fob/zePZcrOyQoLMMO7aBIddLcQIEK5dYjkLnGrQ==}
hasBin: true hasBin: true
peerDependencies: peerDependencies:
@ -7510,7 +7510,7 @@ packages:
'@tsconfig/node12': 1.0.11 '@tsconfig/node12': 1.0.11
'@tsconfig/node14': 1.0.3 '@tsconfig/node14': 1.0.3
'@tsconfig/node16': 1.0.4 '@tsconfig/node16': 1.0.4
'@types/node': 20.11.20 '@types/node': 20.11.24
acorn: 8.11.2 acorn: 8.11.2
acorn-walk: 8.3.0 acorn-walk: 8.3.0
arg: 4.1.3 arg: 4.1.3
@ -7670,7 +7670,7 @@ packages:
- rollup - rollup
dev: true dev: true
/vite-node@1.3.1(@types/node@20.11.20)(sass@1.71.1): /vite-node@1.3.1(@types/node@20.11.24)(sass@1.71.1):
resolution: {integrity: sha512-azbRrqRxlWTJEVbzInZCTchx0X69M/XPTCz4H+TLvlTcR/xH/3hkRqhOakT41fMJCMzXTu4UvegkZiEoJAWvng==} resolution: {integrity: sha512-azbRrqRxlWTJEVbzInZCTchx0X69M/XPTCz4H+TLvlTcR/xH/3hkRqhOakT41fMJCMzXTu4UvegkZiEoJAWvng==}
engines: {node: ^18.0.0 || >=20.0.0} engines: {node: ^18.0.0 || >=20.0.0}
hasBin: true hasBin: true
@ -7679,7 +7679,7 @@ packages:
debug: 4.3.4 debug: 4.3.4
pathe: 1.1.2 pathe: 1.1.2
picocolors: 1.0.0 picocolors: 1.0.0
vite: 5.1.4(@types/node@20.11.20)(sass@1.71.1) vite: 5.1.4(@types/node@20.11.24)(sass@1.71.1)
transitivePeerDependencies: transitivePeerDependencies:
- '@types/node' - '@types/node'
- less - less
@ -7691,7 +7691,7 @@ packages:
- terser - terser
dev: true dev: true
/vite@5.1.4(@types/node@20.11.20)(sass@1.71.1): /vite@5.1.4(@types/node@20.11.24)(sass@1.71.1):
resolution: {integrity: sha512-n+MPqzq+d9nMVTKyewqw6kSt+R3CkvF9QAKY8obiQn8g1fwTscKxyfaYnC632HtBXAQGc1Yjomphwn1dtwGAHg==} resolution: {integrity: sha512-n+MPqzq+d9nMVTKyewqw6kSt+R3CkvF9QAKY8obiQn8g1fwTscKxyfaYnC632HtBXAQGc1Yjomphwn1dtwGAHg==}
engines: {node: ^18.0.0 || >=20.0.0} engines: {node: ^18.0.0 || >=20.0.0}
hasBin: true hasBin: true
@ -7719,7 +7719,7 @@ packages:
terser: terser:
optional: true optional: true
dependencies: dependencies:
'@types/node': 20.11.20 '@types/node': 20.11.24
esbuild: 0.19.12 esbuild: 0.19.12
postcss: 8.4.35 postcss: 8.4.35
rollup: 4.12.0 rollup: 4.12.0
@ -7735,9 +7735,9 @@ packages:
vite: vite:
optional: true optional: true
dependencies: dependencies:
vite: 5.1.4(@types/node@20.11.20)(sass@1.71.1) vite: 5.1.4(@types/node@20.11.24)(sass@1.71.1)
/vitest@1.3.1(@types/node@20.11.20)(sass@1.71.1): /vitest@1.3.1(@types/node@20.11.24)(sass@1.71.1):
resolution: {integrity: sha512-/1QJqXs8YbCrfv/GPQ05wAZf2eakUPLPa18vkJAKE7RXOKfVHqMZZ1WlTjiwl6Gcn65M5vpNUB6EFLnEdRdEXQ==} resolution: {integrity: sha512-/1QJqXs8YbCrfv/GPQ05wAZf2eakUPLPa18vkJAKE7RXOKfVHqMZZ1WlTjiwl6Gcn65M5vpNUB6EFLnEdRdEXQ==}
engines: {node: ^18.0.0 || >=20.0.0} engines: {node: ^18.0.0 || >=20.0.0}
hasBin: true hasBin: true
@ -7762,7 +7762,7 @@ packages:
jsdom: jsdom:
optional: true optional: true
dependencies: dependencies:
'@types/node': 20.11.20 '@types/node': 20.11.24
'@vitest/expect': 1.3.1 '@vitest/expect': 1.3.1
'@vitest/runner': 1.3.1 '@vitest/runner': 1.3.1
'@vitest/snapshot': 1.3.1 '@vitest/snapshot': 1.3.1
@ -7780,8 +7780,8 @@ packages:
strip-literal: 2.0.0 strip-literal: 2.0.0
tinybench: 2.6.0 tinybench: 2.6.0
tinypool: 0.8.2 tinypool: 0.8.2
vite: 5.1.4(@types/node@20.11.20)(sass@1.71.1) vite: 5.1.4(@types/node@20.11.24)(sass@1.71.1)
vite-node: 1.3.1(@types/node@20.11.20)(sass@1.71.1) vite-node: 1.3.1(@types/node@20.11.24)(sass@1.71.1)
why-is-node-running: 2.2.2 why-is-node-running: 2.2.2
transitivePeerDependencies: transitivePeerDependencies:
- less - less

1
src/lib/flashMessages.ts Normal file
View file

@ -0,0 +1 @@
export const notSignedInMessage = { type: 'error', message: 'You are not signed in' } as const;

View file

@ -24,7 +24,6 @@ export const userSchema = z.object({
email: z.string() email: z.string()
.trim() .trim()
.max(64, { message: 'Email must be less than 64 characters' }) .max(64, { message: 'Email must be less than 64 characters' })
.email({ message: 'Please enter a valid email address' })
.optional(), .optional(),
username: z username: z
.string() .string()

View file

@ -1,6 +1,12 @@
import { redirect } from '@sveltejs/kit'; import { redirect } from 'sveltekit-flash-message/server'
import type { PageServerData } from './$types'; import type { PageServerLoad } from './$types';
import { notSignedInMessage } from '$lib/flashMessages';
export const load: PageServerData = async function ({ locals }) { export async function load(event) {
if (!locals?.user?.role?.includes('admin')) redirect(302, '/'); const { locals } = event;
if (!locals?.user?.role?.includes('admin')) {
redirect(302, '/login', notSignedInMessage, event);
}
return {}
}; };

View file

@ -1,17 +1,19 @@
import { type Actions, error, fail, redirect } from '@sveltejs/kit'; import { type Actions, error, fail } from '@sveltejs/kit';
import { and, eq } from 'drizzle-orm'; import { and, eq } from 'drizzle-orm';
import { superValidate } from 'sveltekit-superforms/server'; import { superValidate } from 'sveltekit-superforms/server';
import { zod } from 'sveltekit-superforms/adapters'; import { zod } from 'sveltekit-superforms/adapters';
import { modifyListGameSchema, type ListGame } from '$lib/config/zod-schemas.js'; import { redirect } from 'sveltekit-flash-message/server'
import { modifyListGameSchema, type ListGame } from '$lib/validations/zod-schemas';
import { search_schema } from '$lib/zodValidation.js'; import { search_schema } from '$lib/zodValidation.js';
import type { PageServerLoad } from './$types';
import db from '$lib/drizzle'; import db from '$lib/drizzle';
import { collection_items, collections, games } from '../../../../schema'; import { collection_items, collections, games } from '../../../../schema';
import { notSignedInMessage } from '$lib/flashMessages';
export const load: PageServerLoad = async ({ fetch, url, locals }) => { export async function load(event) {
const { url, locals } = event;
const user = locals.user; const user = locals.user;
if (!user) { if (!user) {
redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
// console.log('locals load', locals); // console.log('locals load', locals);

View file

@ -1,11 +1,13 @@
import { redirect } from "@sveltejs/kit"; import { redirect } from "@sveltejs/kit";
import type { PageServerLoad } from "../$types"; import type { PageServerLoad } from "../$types";
import { notSignedInMessage } from "$lib/flashMessages";
export const load: PageServerLoad = async ({ locals, fetch }) => { export async function load(event) {
const { locals } = event;
const user = locals.user; const user = locals.user;
if (!user) { if (!user) {
redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
return {}
} }

View file

@ -1,20 +1,22 @@
import { fail, redirect, type Actions } from "@sveltejs/kit"; import { fail, type Actions } from "@sveltejs/kit";
import { eq } from "drizzle-orm"; import { eq } from "drizzle-orm";
import { zod } from 'sveltekit-superforms/adapters'; import { zod } from 'sveltekit-superforms/adapters';
import { setError, superValidate } from 'sveltekit-superforms/server'; import { setError, superValidate } from 'sveltekit-superforms/server';
import { redirect } from 'sveltekit-flash-message/server'
import { Argon2id } from "oslo/password"; import { Argon2id } from "oslo/password";
import db from "$lib/drizzle"; import db from "$lib/drizzle";
import { changeUserPasswordSchema } from '$lib/config/zod-schemas.js'; import { changeUserPasswordSchema } from '$lib/validations/account';
import { lucia } from '$lib/server/auth.js'; import { lucia } from '$lib/server/auth.js';
import type { PageServerLoad } from "./$types"; import type { PageServerLoad } from "./$types";
import { users } from "../../../../../schema"; import { users } from "../../../../../schema";
import { notSignedInMessage } from "$lib/flashMessages";
export const load: PageServerLoad = async (event) => { export const load: PageServerLoad = async (event) => {
const form = await superValidate(event, zod(changeUserPasswordSchema)); const form = await superValidate(event, zod(changeUserPasswordSchema));
const user = event.locals.user; const user = event.locals.user;
if (!user) { if (!user) {
redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
form.data = { form.data = {
@ -39,7 +41,7 @@ export const actions: Actions = {
console.log('updating profile'); console.log('updating profile');
if (!event.locals.user) { if (!event.locals.user) {
redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
const user = event.locals.user; const user = event.locals.user;
@ -61,7 +63,7 @@ export const actions: Actions = {
const currentPasswordVerified = await new Argon2id().verify(dbUser.hashed_password, form.data.current_password); const currentPasswordVerified = await new Argon2id().verify(dbUser.hashed_password, form.data.current_password);
if (!currentPasswordVerified) { if (!currentPasswordVerified) {
return setError(form, 'current_password', 'Your password is incorrect.'); return setError(form, 'current_password', 'Your password is incorrect');
} }
try { try {
@ -78,13 +80,22 @@ export const actions: Actions = {
country: event.locals.session?.ip, country: event.locals.session?.ip,
}); });
const sessionCookie = lucia.createSessionCookie(session.id); const sessionCookie = lucia.createSessionCookie(session.id);
return new Response(null, { redirect({
status: 302, status: 302,
headers: { location: '/login',
Location: '/login', message: {
'Set-Cookie': sessionCookie.serialize() type: 'success',
} text: 'Password changed successfully'
},
event: sessionCookie.serialize()
}); });
// return new Response(null, {
// status: 302,
// headers: {
// Location: '/login',
// 'Set-Cookie': sessionCookie.serialize()
// }
// });
} else { } else {
return setError( return setError(
form, form,

View file

@ -1,17 +1,26 @@
<script lang="ts"> <script lang="ts">
import { zodClient } from 'sveltekit-superforms/adapters'; import { zodClient } from 'sveltekit-superforms/adapters';
import { superForm } from 'sveltekit-superforms/client'; import { superForm } from 'sveltekit-superforms/client';
import { changeUserPasswordSchema, userSchema } from '$lib/validations/zod-schemas.js'; import * as flashModule from 'sveltekit-flash-message/client';
import { changeUserPasswordSchema } from '$lib/validations/account';
import { Label } from '$components/ui/label'; import { Label } from '$components/ui/label';
import { Input } from '$components/ui/input'; import { Input } from '$components/ui/input';
import { Button } from '$components/ui/button'; import { Button } from '$components/ui/button';
import { string } from 'zod';
export let data; export let data;
const { form, errors, enhance, delayed, message } = superForm(data.form, { const { form, errors, enhance, delayed, message } = superForm(data.form, {
taintedMessage: null, taintedMessage: null,
validators: zodClient(changeUserPasswordSchema), validators: zodClient(changeUserPasswordSchema),
delayMs: 0 delayMs: 500,
multipleSubmits: 'prevent',
syncFlashMessage: true,
flashMessage: {
module: flashModule,
onError: ({ result }) => {
const errorMessage = result.error.message
message.set({ type: 'error', message: errorMessage });
}
}
}); });
</script> </script>

View file

@ -1,17 +1,18 @@
import { fail, type Actions } from '@sveltejs/kit'; import { fail, type Actions } from '@sveltejs/kit';
import { z } from 'zod';
import { eq } from 'drizzle-orm'; import { eq } from 'drizzle-orm';
import { zod } from 'sveltekit-superforms/adapters'; import { zod } from 'sveltekit-superforms/adapters';
import { message, setError, superValidate } from 'sveltekit-superforms/server'; import { message, setError, superValidate } from 'sveltekit-superforms/server';
import { redirect } from 'sveltekit-flash-message/server'; import { redirect } from 'sveltekit-flash-message/server';
import { changeEmailSchema, profileSchema } from '$lib/validations/account'; import { changeEmailSchema, profileSchema } from '$lib/validations/account';
import { notSignedInMessage } from '$lib/flashMessages';
import db from '$lib/drizzle';
import type { PageServerLoad } from './$types'; import type { PageServerLoad } from './$types';
import { users } from '../../../../schema'; import { users } from '../../../../schema';
import db from '$lib/drizzle';
export const load: PageServerLoad = async (event) => { export const load: PageServerLoad = async (event) => {
if (!event.locals.user) { if (!event.locals.user) {
const message = { type: 'error', message: 'You are not signed in' } as const; redirect(302, '/login', notSignedInMessage, event);
throw redirect(302, '/login', message, event);
} }
const { user } = event.locals; const { user } = event.locals;
@ -41,6 +42,13 @@ export const load: PageServerLoad = async (event) => {
}; };
}; };
const changeEmailIfNotEmpty = z.object({
email: z.string()
.trim()
.max(64, { message: 'Email must be less than 64 characters' })
.email({ message: 'Please enter a valid email' })
});
export const actions: Actions = { export const actions: Actions = {
profileUpdate: async (event) => { profileUpdate: async (event) => {
const form = await superValidate(event, zod(profileSchema)); const form = await superValidate(event, zod(profileSchema));
@ -51,7 +59,7 @@ export const actions: Actions = {
}); });
} }
if (!event.locals.user) { if (!event.locals.user) {
throw redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
try { try {
@ -94,14 +102,14 @@ export const actions: Actions = {
const form = await superValidate(event, zod(changeEmailSchema)); const form = await superValidate(event, zod(changeEmailSchema));
const newEmail = form.data?.email; const newEmail = form.data?.email;
if (!form.valid || !newEmail || newEmail === '') { if (!form.valid || !newEmail || (newEmail !== '' && changeEmailIfNotEmpty.safeParse(form.data).success === false)) {
return fail(400, { return fail(400, {
form form
}); });
} }
if (!event.locals.user) { if (!event.locals.user) {
throw redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
const user = event.locals.user; const user = event.locals.user;
@ -110,7 +118,7 @@ export const actions: Actions = {
}); });
if (existingUser && existingUser.id !== user.id) { if (existingUser && existingUser.id !== user.id) {
return setError(form, 'email', { type: 'error', message: 'That email is already taken' }); return setError(form, 'email', 'That email is already taken');
} }
await db await db

View file

@ -26,7 +26,12 @@
const { form: emailForm, errors: emailErrors, enhance: emailEnhance } = superForm(data.emailForm, { const { form: emailForm, errors: emailErrors, enhance: emailEnhance } = superForm(data.emailForm, {
taintedMessage: null, taintedMessage: null,
validators: zodClient(changeEmailSchema), validators: zodClient(changeEmailSchema),
delayMs: 0 delayMs: 500,
multipleSubmits: 'prevent',
syncFlashMessage: true,
flashMessage: {
module: flashModule,
}
}); });
</script> </script>

View file

@ -1,14 +1,17 @@
import { error, redirect, type Actions } from '@sveltejs/kit'; import { error, type Actions } from '@sveltejs/kit';
import { zod } from 'sveltekit-superforms/adapters'; import { zod } from 'sveltekit-superforms/adapters';
import { superValidate } from 'sveltekit-superforms/server'; import { superValidate } from 'sveltekit-superforms/server';
import { modifyListGameSchema } from '$lib/config/zod-schemas.js'; import { redirect } from 'sveltekit-flash-message/server';
import { modifyListGameSchema } from '$lib/validations/zod-schemas';
import db from '$lib/drizzle.js'; import db from '$lib/drizzle.js';
import { and, eq } from 'drizzle-orm'; import { and, eq } from 'drizzle-orm';
import { games, wishlist_items, wishlists } from '../../../../schema.js'; import { games, wishlist_items, wishlists } from '../../../../schema.js';
import { notSignedInMessage } from '$lib/flashMessages.js';
export async function load({ params, locals }) { export async function load(event) {
const { params, locals } = event;
if (!locals.user) { if (!locals.user) {
redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
console.log('Wishlist load User id', locals.user.id); console.log('Wishlist load User id', locals.user.id);
@ -54,7 +57,7 @@ export const actions: Actions = {
try { try {
if (!locals.user) { if (!locals.user) {
redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
const game = await db.query.games.findFirst({ const game = await db.query.games.findFirst({
@ -96,9 +99,10 @@ export const actions: Actions = {
} }
}, },
// Create new wishlist // Create new wishlist
create: async ({ locals }) => { create: async (event) => {
const { locals } = event;
if (!locals.user) { if (!locals.user) {
redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
return error(405, 'Method not allowed'); return error(405, 'Method not allowed');
}, },
@ -116,7 +120,7 @@ export const actions: Actions = {
try { try {
if (!locals.user) { if (!locals.user) {
redirect(302, '/login'); redirect(302, '/login', notSignedInMessage, event);
} }
const game = await db.query.games.findFirst({ const game = await db.query.games.findFirst({

View file

@ -1,9 +1,10 @@
import { redirect } from '@sveltejs/kit'; import { redirect } from 'sveltekit-flash-message/server';
import type { LayoutServerLoad } from './$types'; import { notSignedInMessage } from '$lib/flashMessages';
export const load: LayoutServerLoad = async ({ url, locals }) => { export async function load(event) {
const { url, locals } = event;
if (locals.user) { if (locals.user) {
redirect(302, '/'); redirect(302, '/', notSignedInMessage, event);
} }
return { return {

View file

@ -1,9 +1,12 @@
import { redirect, fail } from '@sveltejs/kit'; import { fail } from '@sveltejs/kit';
import { lucia } from '$lib/server/auth'; import { lucia } from '$lib/server/auth';
import type { Actions } from "./$types"; import type { Actions } from "./$types";
import { redirect } from 'sveltekit-flash-message/server';
import { notSignedInMessage } from '$lib/flashMessages';
export const actions: Actions = { export const actions: Actions = {
default: async ({ locals, cookies }) => { default: async (event) => {
const { locals, cookies } = event;
console.log('Signing out user'); console.log('Signing out user');
if (!locals.session) { if (!locals.session) {
return fail(401); return fail(401);
@ -14,6 +17,6 @@ export const actions: Actions = {
path: '.', path: '.',
...sessionCookie.attributes ...sessionCookie.attributes
}); });
return redirect(302, '/login'); return redirect(302, '/login', notSignedInMessage, event);
} }
}; };

View file

@ -2,15 +2,25 @@ import { fail, error, type Actions, redirect } from '@sveltejs/kit';
import { Argon2id } from 'oslo/password'; import { Argon2id } from 'oslo/password';
import { eq } from 'drizzle-orm'; import { eq } from 'drizzle-orm';
import { nanoid } from 'nanoid'; import { nanoid } from 'nanoid';
import { setError, superValidate } from 'sveltekit-superforms/server'; import { zod } from 'sveltekit-superforms/adapters';
import { message, setError, superValidate } from 'sveltekit-superforms/server';
import type { PageServerLoad } from './$types'; import type { PageServerLoad } from './$types';
import { lucia } from '$lib/server/auth'; import { lucia } from '$lib/server/auth';
import { signUpSchema } from '$lib/config/zod-schemas'; import { signUpSchema } from '$lib/validations/auth';
import { add_user_to_role } from '$server/roles'; import { add_user_to_role } from '$server/roles';
import type { Message } from '$lib/types.js';
import db from '$lib/drizzle'; import db from '$lib/drizzle';
import { collections, users, wishlists } from '../../../schema'; import { collections, users, wishlists } from '../../../schema';
const signUpDefaults = {
firstName: '',
lastName: '',
email: '',
username: '',
password: '',
confirm_password: '',
terms: true
};
export const load: PageServerLoad = async (event) => { export const load: PageServerLoad = async (event) => {
console.log('sign up load event', event); console.log('sign up load event', event);
// const session = await event.locals.auth.validate(); // const session = await event.locals.auth.validate();
@ -18,13 +28,15 @@ export const load: PageServerLoad = async (event) => {
// throw redirect(302, '/'); // throw redirect(302, '/');
// } // }
return { return {
form: await superValidate<typeof signUpSchema, Message>(event, signUpSchema) form: await superValidate(zod(signUpSchema), {
defaults: signUpDefaults
})
}; };
}; };
export const actions: Actions = { export const actions: Actions = {
default: async (event) => { default: async (event) => {
const form = await superValidate<typeof signUpSchema, Message>(event, signUpSchema); const form = await superValidate(event, zod(signUpSchema));
if (!form.valid) { if (!form.valid) {
form.data.password = ''; form.data.password = '';
form.data.confirm_password = ''; form.data.confirm_password = '';