wexts 3.0.1 → 4.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +49 -346
- package/bin/wexts.cjs +2 -0
- package/dist/chunk-2KAQYLVN.js +0 -0
- package/dist/chunk-2KAQYLVN.js.map +1 -1
- package/dist/{chunk-O42L6HOX.js → chunk-2LJVUMXW.js} +79 -93
- package/dist/chunk-2LJVUMXW.js.map +1 -0
- package/dist/chunk-7QKLIVRF.js +94 -0
- package/dist/chunk-7QKLIVRF.js.map +1 -0
- package/dist/{chunk-FCEZDH42.mjs → chunk-7WULUGLH.mjs} +5 -3
- package/dist/chunk-7WULUGLH.mjs.map +1 -0
- package/dist/{chunk-WF65EDRZ.js → chunk-BG56B4DE.js} +20 -2
- package/dist/chunk-BG56B4DE.js.map +1 -0
- package/dist/chunk-CLM5PNSG.mjs +496 -0
- package/dist/chunk-CLM5PNSG.mjs.map +1 -0
- package/dist/chunk-DNLGCKTT.js +31 -0
- package/dist/chunk-DNLGCKTT.js.map +1 -0
- package/dist/{chunk-VNNVLQLJ.mjs → chunk-JHOVXH3X.mjs} +2 -2
- package/dist/chunk-JHOVXH3X.mjs.map +1 -0
- package/dist/chunk-MXINIFPC.js +105 -0
- package/dist/chunk-MXINIFPC.js.map +1 -0
- package/dist/chunk-SE32ZPOZ.js +496 -0
- package/dist/chunk-SE32ZPOZ.js.map +1 -0
- package/dist/{chunk-STTOPUZ2.mjs → chunk-UAL54DVV.mjs} +21 -3
- package/dist/chunk-UAL54DVV.mjs.map +1 -0
- package/dist/{chunk-3OM7CHCA.js → chunk-WCKSKU3C.js} +1 -1
- package/dist/chunk-WCKSKU3C.js.map +1 -0
- package/dist/chunk-WU6FW77M.mjs +105 -0
- package/dist/chunk-WU6FW77M.mjs.map +1 -0
- package/dist/chunk-XE4OXN2W.js +0 -0
- package/dist/chunk-XE4OXN2W.js.map +1 -1
- package/dist/chunk-YBM3IJEA.mjs +94 -0
- package/dist/chunk-YBM3IJEA.mjs.map +1 -0
- package/dist/{chunk-KXYLEUSW.mjs → chunk-YN6WIWNQ.mjs} +69 -83
- package/dist/chunk-YN6WIWNQ.mjs.map +1 -0
- package/dist/chunk-YSLEF5C5.mjs +0 -0
- package/dist/chunk-YSLEF5C5.mjs.map +0 -0
- package/dist/chunk-ZX7QIN24.mjs +31 -0
- package/dist/chunk-ZX7QIN24.mjs.map +1 -0
- package/dist/cli/index.d.mts +10 -0
- package/dist/cli/index.d.ts +10 -0
- package/dist/cli/index.js +292 -292
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/index.mjs +294 -293
- package/dist/cli/index.mjs.map +1 -1
- package/dist/client/index.d.mts +10 -1
- package/dist/client/index.d.ts +10 -1
- package/dist/client/index.js +4 -2
- package/dist/client/index.js.map +1 -1
- package/dist/client/index.mjs +6 -4
- package/dist/client/index.mjs.map +0 -0
- package/dist/codegen/index.d.mts +2 -1
- package/dist/codegen/index.d.ts +2 -1
- package/dist/codegen/index.js +5 -3
- package/dist/codegen/index.js.map +1 -1
- package/dist/codegen/index.mjs +7 -5
- package/dist/codegen/index.mjs.map +0 -0
- package/dist/decorators-BT1FFqN0.d.mts +29 -0
- package/dist/decorators-DvS58PqC.d.ts +29 -0
- package/dist/dev-server/index.d.mts +1 -1
- package/dist/dev-server/index.d.ts +1 -1
- package/dist/dev-server/index.js +3 -3
- package/dist/dev-server/index.js.map +1 -1
- package/dist/dev-server/index.mjs +3 -3
- package/dist/dev-server/index.mjs.map +0 -0
- package/dist/{index-SjUaHgFr.d.ts → index-7QeQEf37.d.ts} +27 -10
- package/dist/{index-tFGPFVfQ.d.mts → index-7RvU-jGE.d.mts} +0 -1
- package/dist/{index-tFGPFVfQ.d.ts → index-7RvU-jGE.d.ts} +0 -1
- package/dist/{index-SjUaHgFr.d.mts → index-8nzxy0NN.d.mts} +27 -10
- package/dist/index-Co5ZsLqq.d.ts +58 -0
- package/dist/index-D94W1__r.d.mts +58 -0
- package/dist/index-DQmyVp6F.d.mts +27 -0
- package/dist/index-KL_1BrQb.d.ts +27 -0
- package/dist/index.d.mts +17 -6
- package/dist/index.d.ts +17 -6
- package/dist/index.js +57 -30
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +48 -21
- package/dist/index.mjs.map +1 -1
- package/dist/nest/index.d.mts +3 -1
- package/dist/nest/index.d.ts +3 -1
- package/dist/nest/index.js +20 -2
- package/dist/nest/index.js.map +1 -1
- package/dist/nest/index.mjs +21 -3
- package/dist/nest/index.mjs.map +0 -0
- package/dist/next/index.d.mts +7 -2
- package/dist/next/index.d.ts +7 -2
- package/dist/next/index.js +72 -5
- package/dist/next/index.js.map +1 -1
- package/dist/next/index.mjs +70 -4
- package/dist/next/index.mjs.map +1 -1
- package/dist/rpc/index.d.mts +2 -0
- package/dist/rpc/index.d.ts +2 -0
- package/dist/rpc/index.js +23 -0
- package/dist/rpc/index.js.map +1 -0
- package/dist/rpc/index.mjs +23 -0
- package/dist/{chunk-7NSRDJ5C.mjs.map → rpc/index.mjs.map} +0 -0
- package/dist/runtime/index.d.mts +55 -0
- package/dist/runtime/index.d.ts +55 -0
- package/dist/runtime/index.js +213 -0
- package/dist/runtime/index.js.map +1 -0
- package/dist/runtime/index.mjs +213 -0
- package/dist/runtime/index.mjs.map +1 -0
- package/dist/types/index.d.mts +0 -0
- package/dist/types/index.d.ts +0 -0
- package/dist/types/index.js +0 -0
- package/dist/types/index.js.map +1 -1
- package/dist/types/index.mjs +1 -1
- package/dist/types/index.mjs.map +0 -0
- package/dist/types-7d_fC-C3.d.mts +32 -0
- package/dist/types-7d_fC-C3.d.ts +32 -0
- package/dist/vercel-builder/index.d.mts +58 -0
- package/dist/vercel-builder/index.d.ts +58 -0
- package/dist/vercel-builder/index.js +330 -0
- package/dist/vercel-builder/index.js.map +1 -0
- package/dist/vercel-builder/index.mjs +330 -0
- package/dist/vercel-builder/index.mjs.map +1 -0
- package/package.json +37 -16
- package/templates/.dockerignore +43 -43
- package/templates/.env.example +0 -0
- package/templates/Dockerfile +60 -60
- package/templates/Procfile +1 -1
- package/templates/README.md +67 -58
- package/templates/api-sdk.ts +115 -115
- package/templates/docker-compose.yml +34 -34
- package/templates/nestjs-api/.env.example +0 -0
- package/templates/nestjs-api/README.md +87 -79
- package/templates/nestjs-api/nest-cli.json +6 -6
- package/templates/nestjs-api/package-lock.json +5623 -5623
- package/templates/nestjs-api/package.json +40 -40
- package/templates/nestjs-api/prisma/dev.db +0 -0
- package/templates/nestjs-api/prisma/migrations/20251123205437_init/migration.sql +0 -0
- package/templates/nestjs-api/prisma/migrations/migration_lock.toml +0 -0
- package/templates/nestjs-api/prisma/schema.prisma +29 -29
- package/templates/nestjs-api/src/app.module.ts +17 -17
- package/templates/nestjs-api/src/auth/auth.controller.ts +27 -27
- package/templates/nestjs-api/src/auth/auth.module.ts +37 -29
- package/templates/nestjs-api/src/auth/auth.service.ts +86 -86
- package/templates/nestjs-api/src/auth/dto/auth.dto.ts +22 -22
- package/templates/nestjs-api/src/auth/guards/jwt-auth.guard.ts +5 -5
- package/templates/nestjs-api/src/auth/strategies/jwt.strategy.ts +27 -19
- package/templates/nestjs-api/src/main.ts +32 -32
- package/templates/nestjs-api/src/prisma/prisma.module.ts +9 -9
- package/templates/nestjs-api/src/prisma/prisma.service.ts +14 -14
- package/templates/nestjs-api/src/todos/dto/todo.dto.ts +24 -24
- package/templates/nestjs-api/src/todos/todos.controller.ts +39 -39
- package/templates/nestjs-api/src/todos/todos.module.ts +11 -11
- package/templates/nestjs-api/src/todos/todos.service.ts +53 -53
- package/templates/nestjs-api/src/users/users.controller.ts +14 -14
- package/templates/nestjs-api/src/users/users.module.ts +12 -12
- package/templates/nestjs-api/src/users/users.service.ts +19 -19
- package/templates/nestjs-api/tsconfig.json +39 -39
- package/templates/nextjs-web/README.md +76 -68
- package/templates/nextjs-web/app/actions/auth.ts +108 -108
- package/templates/nextjs-web/app/dashboard/error.tsx +39 -39
- package/templates/nextjs-web/app/dashboard/loading.tsx +14 -14
- package/templates/nextjs-web/app/dashboard/page.tsx +5 -5
- package/templates/nextjs-web/app/globals.css +93 -93
- package/templates/nextjs-web/app/layout.tsx +29 -29
- package/templates/nextjs-web/app/login/page.tsx +5 -5
- package/templates/nextjs-web/app/page.tsx +28 -28
- package/templates/nextjs-web/app/register/page.tsx +5 -5
- package/templates/nextjs-web/components/ui/button.tsx +56 -56
- package/templates/nextjs-web/components/ui/card.tsx +79 -79
- package/templates/nextjs-web/components/ui/input.tsx +25 -25
- package/templates/nextjs-web/components/ui/label.tsx +24 -24
- package/templates/nextjs-web/features/auth/LoginForm.tsx +140 -140
- package/templates/nextjs-web/features/auth/RegisterForm.tsx +159 -159
- package/templates/nextjs-web/features/auth/api.ts +35 -35
- package/templates/nextjs-web/features/auth/index.ts +3 -3
- package/templates/nextjs-web/features/dashboard/DashboardView.tsx +204 -204
- package/templates/nextjs-web/features/dashboard/api.ts +9 -9
- package/templates/nextjs-web/features/dashboard/components.tsx +74 -74
- package/templates/nextjs-web/features/dashboard/index.ts +3 -3
- package/templates/nextjs-web/hooks/index.ts +4 -4
- package/templates/nextjs-web/lib/api-client.ts +89 -89
- package/templates/nextjs-web/lib/api.ts +115 -115
- package/templates/nextjs-web/lib/axios-global-config.ts +17 -17
- package/templates/nextjs-web/lib/utils.ts +6 -6
- package/templates/nextjs-web/lib/wexts-client.ts +4 -4
- package/templates/nextjs-web/next-env.d.ts +6 -6
- package/templates/nextjs-web/next.config.ts +20 -20
- package/templates/nextjs-web/package-lock.json +3254 -3254
- package/templates/nextjs-web/package.json +37 -37
- package/templates/nextjs-web/postcss.config.js +6 -6
- package/templates/nextjs-web/tailwind.config.ts +69 -69
- package/templates/nextjs-web/tsconfig.json +1 -1
- package/templates/nixpacks.toml +11 -11
- package/templates/root-package.json +31 -31
- package/templates/server.ts +66 -66
- package/templates/tsconfig.json +30 -30
- package/dist/chunk-2MCBBWEA.js +0 -1
- package/dist/chunk-2MCBBWEA.js.map +0 -1
- package/dist/chunk-3OM7CHCA.js.map +0 -1
- package/dist/chunk-63MTCWU2.mjs +0 -361
- package/dist/chunk-63MTCWU2.mjs.map +0 -1
- package/dist/chunk-667BQCEM.js +0 -375
- package/dist/chunk-667BQCEM.js.map +0 -1
- package/dist/chunk-67IJ6H4J.mjs +0 -44
- package/dist/chunk-67IJ6H4J.mjs.map +0 -1
- package/dist/chunk-6SVQEGEX.mjs +0 -44
- package/dist/chunk-6SVQEGEX.mjs.map +0 -1
- package/dist/chunk-7NSRDJ5C.mjs +0 -1
- package/dist/chunk-ASDXAK6G.js +0 -44
- package/dist/chunk-ASDXAK6G.js.map +0 -1
- package/dist/chunk-CKZ4VSCB.mjs +0 -18
- package/dist/chunk-CKZ4VSCB.mjs.map +0 -1
- package/dist/chunk-DW6GOKMF.js +0 -57
- package/dist/chunk-DW6GOKMF.js.map +0 -1
- package/dist/chunk-EFZPSZWO.mjs +0 -1
- package/dist/chunk-EFZPSZWO.mjs.map +0 -1
- package/dist/chunk-FCEZDH42.mjs.map +0 -1
- package/dist/chunk-FYGXL4V7.js +0 -361
- package/dist/chunk-FYGXL4V7.js.map +0 -1
- package/dist/chunk-GKVPGKAH.js +0 -66
- package/dist/chunk-GKVPGKAH.js.map +0 -1
- package/dist/chunk-GWP6PNSP.js +0 -225
- package/dist/chunk-GWP6PNSP.js.map +0 -1
- package/dist/chunk-HQKTXE7E.mjs +0 -225
- package/dist/chunk-HQKTXE7E.mjs.map +0 -1
- package/dist/chunk-HSFLZUJN.mjs +0 -57
- package/dist/chunk-HSFLZUJN.mjs.map +0 -1
- package/dist/chunk-HU63F22V.js +0 -361
- package/dist/chunk-HU63F22V.js.map +0 -1
- package/dist/chunk-J5LGTIGS.mjs +0 -10
- package/dist/chunk-J5LGTIGS.mjs.map +0 -1
- package/dist/chunk-JMBD6DOP.js +0 -225
- package/dist/chunk-JMBD6DOP.js.map +0 -1
- package/dist/chunk-K7EIJSYQ.js +0 -1
- package/dist/chunk-K7EIJSYQ.js.map +0 -1
- package/dist/chunk-KXYLEUSW.mjs.map +0 -1
- package/dist/chunk-MTHKZO55.js +0 -44
- package/dist/chunk-MTHKZO55.js.map +0 -1
- package/dist/chunk-NNQFLD7O.mjs +0 -361
- package/dist/chunk-NNQFLD7O.mjs.map +0 -1
- package/dist/chunk-NU2UB242.js +0 -82
- package/dist/chunk-NU2UB242.js.map +0 -1
- package/dist/chunk-NULGSZFE.mjs +0 -57
- package/dist/chunk-NULGSZFE.mjs.map +0 -1
- package/dist/chunk-O42L6HOX.js.map +0 -1
- package/dist/chunk-ONXNE2A6.mjs +0 -375
- package/dist/chunk-ONXNE2A6.mjs.map +0 -1
- package/dist/chunk-OTBYRUBE.mjs +0 -225
- package/dist/chunk-OTBYRUBE.mjs.map +0 -1
- package/dist/chunk-OTSAVKLY.mjs +0 -66
- package/dist/chunk-OTSAVKLY.mjs.map +0 -1
- package/dist/chunk-PZ5AY32C.js +0 -10
- package/dist/chunk-PZ5AY32C.js.map +0 -1
- package/dist/chunk-QP2TMRLG.js +0 -57
- package/dist/chunk-QP2TMRLG.js.map +0 -1
- package/dist/chunk-RS23R3ZQ.mjs +0 -82
- package/dist/chunk-RS23R3ZQ.mjs.map +0 -1
- package/dist/chunk-STTOPUZ2.mjs.map +0 -1
- package/dist/chunk-VMT3LALB.mjs +0 -51
- package/dist/chunk-VMT3LALB.mjs.map +0 -1
- package/dist/chunk-VNNVLQLJ.mjs.map +0 -1
- package/dist/chunk-W3YRVEFQ.js +0 -66
- package/dist/chunk-W3YRVEFQ.js.map +0 -1
- package/dist/chunk-WF65EDRZ.js.map +0 -1
- package/dist/chunk-WMHVXEYQ.mjs +0 -66
- package/dist/chunk-WMHVXEYQ.mjs.map +0 -1
- package/dist/chunk-XVKTIYHY.js +0 -51
- package/dist/chunk-XVKTIYHY.js.map +0 -1
- package/dist/codegen-MRZDLCYI.js +0 -13
- package/dist/codegen-MRZDLCYI.js.map +0 -1
- package/dist/codegen-UI5HTMXE.mjs +0 -13
- package/dist/codegen-UI5HTMXE.mjs.map +0 -1
- package/dist/dev-server-JKRVBWPY.mjs +0 -13
- package/dist/dev-server-JKRVBWPY.mjs.map +0 -1
- package/dist/dev-server-TLL7UQMR.js +0 -13
- package/dist/dev-server-TLL7UQMR.js.map +0 -1
- package/dist/index-BsNaOUtH.d.mts +0 -44
- package/dist/index-BsNaOUtH.d.ts +0 -44
- package/dist/index-CrbXnXsO.d.ts +0 -62
- package/dist/index-kEbGExWM.d.mts +0 -62
- package/templates/nestjs-api/.env +0 -4
- package/templates/nextjs-web/.env +0 -1
|
@@ -1,41 +1,41 @@
|
|
|
1
|
-
{
|
|
2
|
-
"name": "wexts-api",
|
|
3
|
-
"version": "1.0.0",
|
|
4
|
-
"description": "wexts NestJS API",
|
|
5
|
-
"scripts": {
|
|
6
|
-
"build": "nest build",
|
|
7
|
-
"dev": "nest start --watch",
|
|
8
|
-
"start": "nest start",
|
|
9
|
-
"start:dev": "nest start --watch",
|
|
10
|
-
"start:prod": "node dist/main",
|
|
11
|
-
"prisma:generate": "prisma generate",
|
|
12
|
-
"prisma:migrate": "prisma migrate dev",
|
|
13
|
-
"prisma:studio": "prisma studio"
|
|
14
|
-
},
|
|
15
|
-
"dependencies": {
|
|
16
|
-
"@nestjs/common": "^11.0.0",
|
|
17
|
-
"@nestjs/config": "^4.0.2",
|
|
18
|
-
"@nestjs/core": "^11.0.0",
|
|
19
|
-
"@nestjs/jwt": "^11.0.0",
|
|
20
|
-
"@nestjs/passport": "^11.0.0",
|
|
21
|
-
"@nestjs/platform-fastify": "^11.0.0",
|
|
22
|
-
"@prisma/client": "^6.0.0",
|
|
23
|
-
"bcrypt": "^5.1.1",
|
|
24
|
-
"class-transformer": "^0.5.1",
|
|
25
|
-
"class-validator": "^0.14.1",
|
|
26
|
-
"passport": "^0.7.0",
|
|
27
|
-
"passport-jwt": "^4.0.1",
|
|
28
|
-
"reflect-metadata": "^0.2.2",
|
|
29
|
-
"rxjs": "^7.8.1",
|
|
30
|
-
"wexts": "^2.0.0"
|
|
31
|
-
},
|
|
32
|
-
"devDependencies": {
|
|
33
|
-
"@nestjs/cli": "^11.0.0",
|
|
34
|
-
"@nestjs/schematics": "^11.0.0",
|
|
35
|
-
"@types/bcrypt": "^5.0.2",
|
|
36
|
-
"@types/node": "^22.0.0",
|
|
37
|
-
"@types/passport-jwt": "^4.0.1",
|
|
38
|
-
"prisma": "^6.0.0",
|
|
39
|
-
"typescript": "^5.9.3"
|
|
40
|
-
}
|
|
1
|
+
{
|
|
2
|
+
"name": "wexts-api",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "wexts NestJS API",
|
|
5
|
+
"scripts": {
|
|
6
|
+
"build": "nest build",
|
|
7
|
+
"dev": "nest start --watch",
|
|
8
|
+
"start": "nest start",
|
|
9
|
+
"start:dev": "nest start --watch",
|
|
10
|
+
"start:prod": "node dist/main",
|
|
11
|
+
"prisma:generate": "prisma generate",
|
|
12
|
+
"prisma:migrate": "prisma migrate dev",
|
|
13
|
+
"prisma:studio": "prisma studio"
|
|
14
|
+
},
|
|
15
|
+
"dependencies": {
|
|
16
|
+
"@nestjs/common": "^11.0.0",
|
|
17
|
+
"@nestjs/config": "^4.0.2",
|
|
18
|
+
"@nestjs/core": "^11.0.0",
|
|
19
|
+
"@nestjs/jwt": "^11.0.0",
|
|
20
|
+
"@nestjs/passport": "^11.0.0",
|
|
21
|
+
"@nestjs/platform-fastify": "^11.0.0",
|
|
22
|
+
"@prisma/client": "^6.0.0",
|
|
23
|
+
"bcrypt": "^5.1.1",
|
|
24
|
+
"class-transformer": "^0.5.1",
|
|
25
|
+
"class-validator": "^0.14.1",
|
|
26
|
+
"passport": "^0.7.0",
|
|
27
|
+
"passport-jwt": "^4.0.1",
|
|
28
|
+
"reflect-metadata": "^0.2.2",
|
|
29
|
+
"rxjs": "^7.8.1",
|
|
30
|
+
"wexts": "^2.0.0"
|
|
31
|
+
},
|
|
32
|
+
"devDependencies": {
|
|
33
|
+
"@nestjs/cli": "^11.0.0",
|
|
34
|
+
"@nestjs/schematics": "^11.0.0",
|
|
35
|
+
"@types/bcrypt": "^5.0.2",
|
|
36
|
+
"@types/node": "^22.0.0",
|
|
37
|
+
"@types/passport-jwt": "^4.0.1",
|
|
38
|
+
"prisma": "^6.0.0",
|
|
39
|
+
"typescript": "^5.9.3"
|
|
40
|
+
}
|
|
41
41
|
}
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
@@ -1,29 +1,29 @@
|
|
|
1
|
-
generator client {
|
|
2
|
-
provider = "prisma-client-js"
|
|
3
|
-
}
|
|
4
|
-
|
|
5
|
-
datasource db {
|
|
6
|
-
provider = "sqlite"
|
|
7
|
-
url = env("DATABASE_URL")
|
|
8
|
-
}
|
|
9
|
-
|
|
10
|
-
model User {
|
|
11
|
-
id String @id @default(uuid())
|
|
12
|
-
email String @unique
|
|
13
|
-
name String?
|
|
14
|
-
password String
|
|
15
|
-
createdAt DateTime @default(now())
|
|
16
|
-
updatedAt DateTime @updatedAt
|
|
17
|
-
todos Todo[]
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
model Todo {
|
|
21
|
-
id String @id @default(uuid())
|
|
22
|
-
title String
|
|
23
|
-
description String?
|
|
24
|
-
completed Boolean @default(false)
|
|
25
|
-
userId String
|
|
26
|
-
user User @relation(fields: [userId], references: [id], onDelete: Cascade)
|
|
27
|
-
createdAt DateTime @default(now())
|
|
28
|
-
updatedAt DateTime @updatedAt
|
|
29
|
-
}
|
|
1
|
+
generator client {
|
|
2
|
+
provider = "prisma-client-js"
|
|
3
|
+
}
|
|
4
|
+
|
|
5
|
+
datasource db {
|
|
6
|
+
provider = "sqlite"
|
|
7
|
+
url = env("DATABASE_URL")
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
model User {
|
|
11
|
+
id String @id @default(uuid())
|
|
12
|
+
email String @unique
|
|
13
|
+
name String?
|
|
14
|
+
password String
|
|
15
|
+
createdAt DateTime @default(now())
|
|
16
|
+
updatedAt DateTime @updatedAt
|
|
17
|
+
todos Todo[]
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
model Todo {
|
|
21
|
+
id String @id @default(uuid())
|
|
22
|
+
title String
|
|
23
|
+
description String?
|
|
24
|
+
completed Boolean @default(false)
|
|
25
|
+
userId String
|
|
26
|
+
user User @relation(fields: [userId], references: [id], onDelete: Cascade)
|
|
27
|
+
createdAt DateTime @default(now())
|
|
28
|
+
updatedAt DateTime @updatedAt
|
|
29
|
+
}
|
|
@@ -1,17 +1,17 @@
|
|
|
1
|
-
import { Module } from '@nestjs/common';
|
|
2
|
-
import { ConfigModule } from '@nestjs/config';
|
|
3
|
-
import { PrismaModule } from './prisma/prisma.module';
|
|
4
|
-
import { AuthModule } from './auth/auth.module';
|
|
5
|
-
import { UsersModule } from './users/users.module';
|
|
6
|
-
import { TodosModule } from './todos/todos.module';
|
|
7
|
-
|
|
8
|
-
@Module({
|
|
9
|
-
imports: [
|
|
10
|
-
ConfigModule.forRoot({ isGlobal: true }),
|
|
11
|
-
PrismaModule,
|
|
12
|
-
AuthModule,
|
|
13
|
-
UsersModule,
|
|
14
|
-
TodosModule,
|
|
15
|
-
],
|
|
16
|
-
})
|
|
17
|
-
export class AppModule { }
|
|
1
|
+
import { Module } from '@nestjs/common';
|
|
2
|
+
import { ConfigModule } from '@nestjs/config';
|
|
3
|
+
import { PrismaModule } from './prisma/prisma.module';
|
|
4
|
+
import { AuthModule } from './auth/auth.module';
|
|
5
|
+
import { UsersModule } from './users/users.module';
|
|
6
|
+
import { TodosModule } from './todos/todos.module';
|
|
7
|
+
|
|
8
|
+
@Module({
|
|
9
|
+
imports: [
|
|
10
|
+
ConfigModule.forRoot({ isGlobal: true }),
|
|
11
|
+
PrismaModule,
|
|
12
|
+
AuthModule,
|
|
13
|
+
UsersModule,
|
|
14
|
+
TodosModule,
|
|
15
|
+
],
|
|
16
|
+
})
|
|
17
|
+
export class AppModule { }
|
|
@@ -1,27 +1,27 @@
|
|
|
1
|
-
import { Controller, Post, Get, Body, UseGuards, Request, Inject } from '@nestjs/common';
|
|
2
|
-
import { AuthService } from './auth.service';
|
|
3
|
-
import { JwtAuthGuard } from './guards/jwt-auth.guard';
|
|
4
|
-
import { RegisterDto, LoginDto } from './dto/auth.dto';
|
|
5
|
-
|
|
6
|
-
@Controller('auth')
|
|
7
|
-
export class AuthController {
|
|
8
|
-
constructor(
|
|
9
|
-
@Inject(AuthService) private readonly authService: AuthService
|
|
10
|
-
) { }
|
|
11
|
-
|
|
12
|
-
@Post('register')
|
|
13
|
-
async register(@Body() dto: RegisterDto) {
|
|
14
|
-
return this.authService.register(dto);
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
@Post('login')
|
|
18
|
-
async login(@Body() dto: LoginDto) {
|
|
19
|
-
return this.authService.login(dto);
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
@Get('me')
|
|
23
|
-
@UseGuards(JwtAuthGuard)
|
|
24
|
-
async getMe(@Request() req) {
|
|
25
|
-
return this.authService.getMe(req.user.userId);
|
|
26
|
-
}
|
|
27
|
-
}
|
|
1
|
+
import { Controller, Post, Get, Body, UseGuards, Request, Inject } from '@nestjs/common';
|
|
2
|
+
import { AuthService } from './auth.service';
|
|
3
|
+
import { JwtAuthGuard } from './guards/jwt-auth.guard';
|
|
4
|
+
import { RegisterDto, LoginDto } from './dto/auth.dto';
|
|
5
|
+
|
|
6
|
+
@Controller('auth')
|
|
7
|
+
export class AuthController {
|
|
8
|
+
constructor(
|
|
9
|
+
@Inject(AuthService) private readonly authService: AuthService
|
|
10
|
+
) { }
|
|
11
|
+
|
|
12
|
+
@Post('register')
|
|
13
|
+
async register(@Body() dto: RegisterDto) {
|
|
14
|
+
return this.authService.register(dto);
|
|
15
|
+
}
|
|
16
|
+
|
|
17
|
+
@Post('login')
|
|
18
|
+
async login(@Body() dto: LoginDto) {
|
|
19
|
+
return this.authService.login(dto);
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
@Get('me')
|
|
23
|
+
@UseGuards(JwtAuthGuard)
|
|
24
|
+
async getMe(@Request() req) {
|
|
25
|
+
return this.authService.getMe(req.user.userId);
|
|
26
|
+
}
|
|
27
|
+
}
|
|
@@ -1,29 +1,37 @@
|
|
|
1
|
-
import { Module } from '@nestjs/common';
|
|
2
|
-
import { JwtModule } from '@nestjs/jwt';
|
|
3
|
-
import { PassportModule } from '@nestjs/passport';
|
|
4
|
-
import { ConfigModule, ConfigService } from '@nestjs/config';
|
|
5
|
-
import { AuthController } from './auth.controller';
|
|
6
|
-
import { AuthService } from './auth.service';
|
|
7
|
-
import { JwtStrategy } from './strategies/jwt.strategy';
|
|
8
|
-
import { PrismaModule } from '../prisma/prisma.module';
|
|
9
|
-
|
|
10
|
-
@Module({
|
|
11
|
-
imports: [
|
|
12
|
-
PrismaModule, // ✅ Important: Import PrismaModule
|
|
13
|
-
ConfigModule,
|
|
14
|
-
PassportModule,
|
|
15
|
-
JwtModule.registerAsync({
|
|
16
|
-
inject: [ConfigService],
|
|
17
|
-
useFactory: (config: ConfigService) => ({
|
|
18
|
-
secret: config
|
|
19
|
-
signOptions: {
|
|
20
|
-
expiresIn: config.get('JWT_EXPIRES_IN') || '7d',
|
|
21
|
-
},
|
|
22
|
-
}),
|
|
23
|
-
}),
|
|
24
|
-
],
|
|
25
|
-
controllers: [AuthController],
|
|
26
|
-
providers: [AuthService, JwtStrategy],
|
|
27
|
-
exports: [AuthService],
|
|
28
|
-
})
|
|
29
|
-
export class AuthModule { }
|
|
1
|
+
import { Module } from '@nestjs/common';
|
|
2
|
+
import { JwtModule } from '@nestjs/jwt';
|
|
3
|
+
import { PassportModule } from '@nestjs/passport';
|
|
4
|
+
import { ConfigModule, ConfigService } from '@nestjs/config';
|
|
5
|
+
import { AuthController } from './auth.controller';
|
|
6
|
+
import { AuthService } from './auth.service';
|
|
7
|
+
import { JwtStrategy } from './strategies/jwt.strategy';
|
|
8
|
+
import { PrismaModule } from '../prisma/prisma.module';
|
|
9
|
+
|
|
10
|
+
@Module({
|
|
11
|
+
imports: [
|
|
12
|
+
PrismaModule, // ✅ Important: Import PrismaModule
|
|
13
|
+
ConfigModule,
|
|
14
|
+
PassportModule,
|
|
15
|
+
JwtModule.registerAsync({
|
|
16
|
+
inject: [ConfigService],
|
|
17
|
+
useFactory: (config: ConfigService) => ({
|
|
18
|
+
secret: getJwtSecret(config),
|
|
19
|
+
signOptions: {
|
|
20
|
+
expiresIn: config.get('JWT_EXPIRES_IN') || '7d',
|
|
21
|
+
},
|
|
22
|
+
}),
|
|
23
|
+
}),
|
|
24
|
+
],
|
|
25
|
+
controllers: [AuthController],
|
|
26
|
+
providers: [AuthService, JwtStrategy],
|
|
27
|
+
exports: [AuthService],
|
|
28
|
+
})
|
|
29
|
+
export class AuthModule { }
|
|
30
|
+
|
|
31
|
+
function getJwtSecret(config: ConfigService): string {
|
|
32
|
+
const secret = config.get<string>('JWT_SECRET');
|
|
33
|
+
if (!secret || secret.length < 32) {
|
|
34
|
+
throw new Error('JWT_SECRET must be set to at least 32 characters.');
|
|
35
|
+
}
|
|
36
|
+
return secret;
|
|
37
|
+
}
|
|
@@ -1,86 +1,86 @@
|
|
|
1
|
-
import { Injectable, UnauthorizedException, Inject } from '@nestjs/common';
|
|
2
|
-
import { JwtService } from '@nestjs/jwt';
|
|
3
|
-
import { PrismaService } from '../prisma/prisma.service';
|
|
4
|
-
import * as bcrypt from 'bcryptjs';
|
|
5
|
-
import { RegisterDto, LoginDto } from './dto/auth.dto';
|
|
6
|
-
|
|
7
|
-
@Injectable()
|
|
8
|
-
export class AuthService {
|
|
9
|
-
constructor(
|
|
10
|
-
@Inject(PrismaService) private readonly prisma: PrismaService,
|
|
11
|
-
@Inject(JwtService) private readonly jwtService: JwtService,
|
|
12
|
-
) { }
|
|
13
|
-
|
|
14
|
-
async register(dto: RegisterDto) {
|
|
15
|
-
const exists = await this.prisma.user.findUnique({
|
|
16
|
-
where: { email: dto.email },
|
|
17
|
-
});
|
|
18
|
-
|
|
19
|
-
if (exists) {
|
|
20
|
-
throw new UnauthorizedException('Email already registered');
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
const hashedPassword = await bcrypt.hash(dto.password, 10);
|
|
24
|
-
|
|
25
|
-
const user = await this.prisma.user.create({
|
|
26
|
-
data: {
|
|
27
|
-
email: dto.email,
|
|
28
|
-
name: dto.name,
|
|
29
|
-
password: hashedPassword,
|
|
30
|
-
},
|
|
31
|
-
select: {
|
|
32
|
-
id: true,
|
|
33
|
-
email: true,
|
|
34
|
-
name: true,
|
|
35
|
-
createdAt: true,
|
|
36
|
-
},
|
|
37
|
-
});
|
|
38
|
-
|
|
39
|
-
const access_token = this.generateToken(user.id, user.email);
|
|
40
|
-
|
|
41
|
-
return { user, access_token };
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
async login(dto: LoginDto) {
|
|
45
|
-
const user = await this.prisma.user.findUnique({
|
|
46
|
-
where: { email: dto.email },
|
|
47
|
-
});
|
|
48
|
-
|
|
49
|
-
if (!user) {
|
|
50
|
-
throw new UnauthorizedException('Invalid credentials');
|
|
51
|
-
}
|
|
52
|
-
|
|
53
|
-
const valid = await bcrypt.compare(dto.password, user.password);
|
|
54
|
-
|
|
55
|
-
if (!valid) {
|
|
56
|
-
throw new UnauthorizedException('Invalid credentials');
|
|
57
|
-
}
|
|
58
|
-
|
|
59
|
-
const access_token = this.generateToken(user.id, user.email);
|
|
60
|
-
|
|
61
|
-
return {
|
|
62
|
-
user: {
|
|
63
|
-
id: user.id,
|
|
64
|
-
email: user.email,
|
|
65
|
-
name: user.name,
|
|
66
|
-
},
|
|
67
|
-
access_token,
|
|
68
|
-
};
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
async getMe(userId: string) {
|
|
72
|
-
return this.prisma.user.findUnique({
|
|
73
|
-
where: { id: userId },
|
|
74
|
-
select: {
|
|
75
|
-
id: true,
|
|
76
|
-
email: true,
|
|
77
|
-
name: true,
|
|
78
|
-
createdAt: true,
|
|
79
|
-
},
|
|
80
|
-
});
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
private generateToken(userId: string, email: string): string {
|
|
84
|
-
return this.jwtService.sign({ sub: userId, email });
|
|
85
|
-
}
|
|
86
|
-
}
|
|
1
|
+
import { Injectable, UnauthorizedException, Inject } from '@nestjs/common';
|
|
2
|
+
import { JwtService } from '@nestjs/jwt';
|
|
3
|
+
import { PrismaService } from '../prisma/prisma.service';
|
|
4
|
+
import * as bcrypt from 'bcryptjs';
|
|
5
|
+
import { RegisterDto, LoginDto } from './dto/auth.dto';
|
|
6
|
+
|
|
7
|
+
@Injectable()
|
|
8
|
+
export class AuthService {
|
|
9
|
+
constructor(
|
|
10
|
+
@Inject(PrismaService) private readonly prisma: PrismaService,
|
|
11
|
+
@Inject(JwtService) private readonly jwtService: JwtService,
|
|
12
|
+
) { }
|
|
13
|
+
|
|
14
|
+
async register(dto: RegisterDto) {
|
|
15
|
+
const exists = await this.prisma.user.findUnique({
|
|
16
|
+
where: { email: dto.email },
|
|
17
|
+
});
|
|
18
|
+
|
|
19
|
+
if (exists) {
|
|
20
|
+
throw new UnauthorizedException('Email already registered');
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
const hashedPassword = await bcrypt.hash(dto.password, 10);
|
|
24
|
+
|
|
25
|
+
const user = await this.prisma.user.create({
|
|
26
|
+
data: {
|
|
27
|
+
email: dto.email,
|
|
28
|
+
name: dto.name,
|
|
29
|
+
password: hashedPassword,
|
|
30
|
+
},
|
|
31
|
+
select: {
|
|
32
|
+
id: true,
|
|
33
|
+
email: true,
|
|
34
|
+
name: true,
|
|
35
|
+
createdAt: true,
|
|
36
|
+
},
|
|
37
|
+
});
|
|
38
|
+
|
|
39
|
+
const access_token = this.generateToken(user.id, user.email);
|
|
40
|
+
|
|
41
|
+
return { user, access_token };
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
async login(dto: LoginDto) {
|
|
45
|
+
const user = await this.prisma.user.findUnique({
|
|
46
|
+
where: { email: dto.email },
|
|
47
|
+
});
|
|
48
|
+
|
|
49
|
+
if (!user) {
|
|
50
|
+
throw new UnauthorizedException('Invalid credentials');
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
const valid = await bcrypt.compare(dto.password, user.password);
|
|
54
|
+
|
|
55
|
+
if (!valid) {
|
|
56
|
+
throw new UnauthorizedException('Invalid credentials');
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
const access_token = this.generateToken(user.id, user.email);
|
|
60
|
+
|
|
61
|
+
return {
|
|
62
|
+
user: {
|
|
63
|
+
id: user.id,
|
|
64
|
+
email: user.email,
|
|
65
|
+
name: user.name,
|
|
66
|
+
},
|
|
67
|
+
access_token,
|
|
68
|
+
};
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
async getMe(userId: string) {
|
|
72
|
+
return this.prisma.user.findUnique({
|
|
73
|
+
where: { id: userId },
|
|
74
|
+
select: {
|
|
75
|
+
id: true,
|
|
76
|
+
email: true,
|
|
77
|
+
name: true,
|
|
78
|
+
createdAt: true,
|
|
79
|
+
},
|
|
80
|
+
});
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
private generateToken(userId: string, email: string): string {
|
|
84
|
+
return this.jwtService.sign({ sub: userId, email });
|
|
85
|
+
}
|
|
86
|
+
}
|
|
@@ -1,22 +1,22 @@
|
|
|
1
|
-
import { IsEmail, IsString, MinLength, IsOptional } from 'class-validator';
|
|
2
|
-
|
|
3
|
-
export class RegisterDto {
|
|
4
|
-
@IsEmail()
|
|
5
|
-
email: string;
|
|
6
|
-
|
|
7
|
-
@IsString()
|
|
8
|
-
@MinLength(6)
|
|
9
|
-
password: string;
|
|
10
|
-
|
|
11
|
-
@IsString()
|
|
12
|
-
@IsOptional()
|
|
13
|
-
name?: string;
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
export class LoginDto {
|
|
17
|
-
@IsEmail()
|
|
18
|
-
email: string;
|
|
19
|
-
|
|
20
|
-
@IsString()
|
|
21
|
-
password: string;
|
|
22
|
-
}
|
|
1
|
+
import { IsEmail, IsString, MinLength, IsOptional } from 'class-validator';
|
|
2
|
+
|
|
3
|
+
export class RegisterDto {
|
|
4
|
+
@IsEmail()
|
|
5
|
+
email: string;
|
|
6
|
+
|
|
7
|
+
@IsString()
|
|
8
|
+
@MinLength(6)
|
|
9
|
+
password: string;
|
|
10
|
+
|
|
11
|
+
@IsString()
|
|
12
|
+
@IsOptional()
|
|
13
|
+
name?: string;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
export class LoginDto {
|
|
17
|
+
@IsEmail()
|
|
18
|
+
email: string;
|
|
19
|
+
|
|
20
|
+
@IsString()
|
|
21
|
+
password: string;
|
|
22
|
+
}
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { Injectable } from '@nestjs/common';
|
|
2
|
-
import { AuthGuard } from '@nestjs/passport';
|
|
3
|
-
|
|
4
|
-
@Injectable()
|
|
5
|
-
export class JwtAuthGuard extends AuthGuard('jwt') { }
|
|
1
|
+
import { Injectable } from '@nestjs/common';
|
|
2
|
+
import { AuthGuard } from '@nestjs/passport';
|
|
3
|
+
|
|
4
|
+
@Injectable()
|
|
5
|
+
export class JwtAuthGuard extends AuthGuard('jwt') { }
|
|
@@ -1,19 +1,27 @@
|
|
|
1
|
-
import { ExtractJwt, Strategy } from 'passport-jwt';
|
|
2
|
-
import { PassportStrategy } from '@nestjs/passport';
|
|
3
|
-
import { Injectable } from '@nestjs/common';
|
|
4
|
-
import { ConfigService } from '@nestjs/config';
|
|
5
|
-
|
|
6
|
-
@Injectable()
|
|
7
|
-
export class JwtStrategy extends PassportStrategy(Strategy) {
|
|
8
|
-
constructor(configService: ConfigService) {
|
|
9
|
-
super({
|
|
10
|
-
jwtFromRequest: ExtractJwt.fromAuthHeaderAsBearerToken(),
|
|
11
|
-
ignoreExpiration: false,
|
|
12
|
-
secretOrKey: configService
|
|
13
|
-
});
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
async validate(payload: any) {
|
|
17
|
-
return { userId: payload.sub, email: payload.email };
|
|
18
|
-
}
|
|
19
|
-
}
|
|
1
|
+
import { ExtractJwt, Strategy } from 'passport-jwt';
|
|
2
|
+
import { PassportStrategy } from '@nestjs/passport';
|
|
3
|
+
import { Injectable } from '@nestjs/common';
|
|
4
|
+
import { ConfigService } from '@nestjs/config';
|
|
5
|
+
|
|
6
|
+
@Injectable()
|
|
7
|
+
export class JwtStrategy extends PassportStrategy(Strategy) {
|
|
8
|
+
constructor(configService: ConfigService) {
|
|
9
|
+
super({
|
|
10
|
+
jwtFromRequest: ExtractJwt.fromAuthHeaderAsBearerToken(),
|
|
11
|
+
ignoreExpiration: false,
|
|
12
|
+
secretOrKey: getJwtSecret(configService),
|
|
13
|
+
});
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
async validate(payload: any) {
|
|
17
|
+
return { userId: payload.sub, email: payload.email };
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
function getJwtSecret(configService: ConfigService): string {
|
|
22
|
+
const secret = configService.get<string>('JWT_SECRET');
|
|
23
|
+
if (!secret || secret.length < 32) {
|
|
24
|
+
throw new Error('JWT_SECRET must be set to at least 32 characters.');
|
|
25
|
+
}
|
|
26
|
+
return secret;
|
|
27
|
+
}
|
|
@@ -1,32 +1,32 @@
|
|
|
1
|
-
import { NestFactory } from '@nestjs/core';
|
|
2
|
-
import { FastifyAdapter, NestFastifyApplication } from '@nestjs/platform-fastify';
|
|
3
|
-
import { ValidationPipe } from '@nestjs/common';
|
|
4
|
-
import { AppModule } from './app.module';
|
|
5
|
-
|
|
6
|
-
async function bootstrap() {
|
|
7
|
-
const app = await NestFactory.create<NestFastifyApplication>(
|
|
8
|
-
AppModule,
|
|
9
|
-
new FastifyAdapter({ logger: true })
|
|
10
|
-
);
|
|
11
|
-
|
|
12
|
-
// Enable CORS
|
|
13
|
-
app.enableCors({
|
|
14
|
-
origin: process.env.FRONTEND_URL || 'http://localhost:3000',
|
|
15
|
-
credentials: true,
|
|
16
|
-
});
|
|
17
|
-
|
|
18
|
-
// Global validation pipe
|
|
19
|
-
app.useGlobalPipes(
|
|
20
|
-
new ValidationPipe({
|
|
21
|
-
whitelist: true,
|
|
22
|
-
transform: true,
|
|
23
|
-
})
|
|
24
|
-
);
|
|
25
|
-
|
|
26
|
-
const port = process.env.PORT || 5050;
|
|
27
|
-
await app.listen(port, '0.0.0.0');
|
|
28
|
-
|
|
29
|
-
console.log(`🚀 wexts API running on http://localhost:${port}`);
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
bootstrap();
|
|
1
|
+
import { NestFactory } from '@nestjs/core';
|
|
2
|
+
import { FastifyAdapter, NestFastifyApplication } from '@nestjs/platform-fastify';
|
|
3
|
+
import { ValidationPipe } from '@nestjs/common';
|
|
4
|
+
import { AppModule } from './app.module';
|
|
5
|
+
|
|
6
|
+
async function bootstrap() {
|
|
7
|
+
const app = await NestFactory.create<NestFastifyApplication>(
|
|
8
|
+
AppModule,
|
|
9
|
+
new FastifyAdapter({ logger: true })
|
|
10
|
+
);
|
|
11
|
+
|
|
12
|
+
// Enable CORS
|
|
13
|
+
app.enableCors({
|
|
14
|
+
origin: process.env.FRONTEND_URL || 'http://localhost:3000',
|
|
15
|
+
credentials: true,
|
|
16
|
+
});
|
|
17
|
+
|
|
18
|
+
// Global validation pipe
|
|
19
|
+
app.useGlobalPipes(
|
|
20
|
+
new ValidationPipe({
|
|
21
|
+
whitelist: true,
|
|
22
|
+
transform: true,
|
|
23
|
+
})
|
|
24
|
+
);
|
|
25
|
+
|
|
26
|
+
const port = process.env.PORT || 5050;
|
|
27
|
+
await app.listen(port, '0.0.0.0');
|
|
28
|
+
|
|
29
|
+
console.log(`🚀 wexts API running on http://localhost:${port}`);
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
bootstrap();
|