create-ej-app 3.2.0 → 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/cli.js +5 -1
- package/cli.ts +40 -33
- package/package.json +4 -4
- package/template/base/.env.example +10 -9
- package/template/base/.eslintrc.cjs +17 -15
- package/template/base/components.json +1 -1
- package/template/base/drizzle.config.ts +11 -0
- package/template/base/next.config.mjs +1 -12
- package/template/base/package.json +63 -56
- package/template/base/postcss.config.mjs +8 -0
- package/template/base/prettier.config.mjs +11 -0
- package/template/base/public/vercel.svg +1 -0
- package/template/base/src/app/(app)/dashboard/layout.tsx +14 -0
- package/template/base/src/app/(app)/dashboard/page.tsx +0 -7
- package/template/base/src/app/(app)/layout.tsx +55 -20
- package/template/base/src/app/(app)/roles/[id]/actions.ts +59 -0
- package/template/base/src/app/(app)/roles/[id]/page.tsx +46 -0
- package/template/base/src/app/(app)/roles/[id]/render.tsx +264 -0
- package/template/base/src/app/(app)/roles/[id]/validation.ts +22 -0
- package/template/base/src/app/(app)/roles/actions.ts +33 -0
- package/template/base/src/app/(app)/roles/page.tsx +52 -0
- package/template/base/src/app/(app)/roles/render.tsx +80 -0
- package/template/base/src/app/(app)/settings/actions.ts +11 -12
- package/template/base/src/app/(app)/settings/layout.tsx +14 -0
- package/template/base/src/app/(app)/settings/page.tsx +1 -10
- package/template/base/src/app/(app)/settings/render.tsx +11 -17
- package/template/base/src/app/(app)/settings/validation.ts +5 -0
- package/template/base/src/app/(app)/tasks/[id]/actions.ts +69 -124
- package/template/base/src/app/(app)/tasks/[id]/page.tsx +37 -3
- package/template/base/src/app/(app)/tasks/[id]/render.tsx +162 -93
- package/template/base/src/app/(app)/tasks/[id]/validation.ts +18 -0
- package/template/base/src/app/(app)/tasks/actions.ts +34 -64
- package/template/base/src/app/(app)/tasks/page.tsx +15 -9
- package/template/base/src/app/(app)/tasks/render.tsx +28 -6
- package/template/base/src/app/(app)/tasks/statusEnum.ts +3 -0
- package/template/base/src/app/(app)/users/[id]/actions.ts +47 -62
- package/template/base/src/app/(app)/users/[id]/page.tsx +15 -8
- package/template/base/src/app/(app)/users/[id]/render.tsx +119 -34
- package/template/base/src/app/(app)/users/[id]/validation.ts +18 -0
- package/template/base/src/app/(app)/users/actions.ts +28 -49
- package/template/base/src/app/(app)/users/page.tsx +22 -9
- package/template/base/src/app/(app)/users/render.tsx +47 -3
- package/template/base/src/app/(auth)/layout.tsx +7 -0
- package/template/base/src/app/(auth)/login/page.tsx +2 -2
- package/template/base/src/app/(auth)/login/render.tsx +146 -0
- package/template/base/src/app/(marketing)/layout.tsx +1 -1
- package/template/base/src/app/(marketing)/page.tsx +8 -7
- package/template/base/src/app/favicon.ico +0 -0
- package/template/base/src/app/layout.tsx +14 -17
- package/template/base/src/components/app-nav-command.tsx +18 -0
- package/template/base/src/components/data-table/data-table-column-header.tsx +2 -2
- package/template/base/src/components/icons.tsx +21 -5
- package/template/base/src/components/ui/alert-dialog.tsx +1 -1
- package/template/base/src/components/ui/command.tsx +1 -1
- package/template/base/src/components/ui/dialog.tsx +1 -1
- package/template/base/src/components/ui/sonner.tsx +31 -0
- package/template/base/src/components/user-avatar.tsx +4 -2
- package/template/base/src/data-access/resource.ts +85 -0
- package/template/base/src/data-access/role-permission.ts +45 -0
- package/template/base/src/data-access/role.ts +105 -0
- package/template/base/src/data-access/task.ts +141 -0
- package/template/base/src/data-access/user.ts +141 -0
- package/template/base/src/db/index.ts +14 -0
- package/template/base/src/db/schema.ts +287 -0
- package/template/base/src/env.mjs +10 -30
- package/template/base/src/hooks/use-lock-body.tsx +2 -1
- package/template/base/src/lib/auth.ts +32 -23
- package/template/base/src/lib/currentUser.ts +8 -0
- package/template/base/src/lib/s3Client.ts +156 -0
- package/template/base/src/lib/safe-action.ts +19 -0
- package/template/base/src/lib/sortOrderEnum.ts +2 -0
- package/template/base/src/use-case/role-permission.ts +19 -0
- package/template/base/src/use-case/role.ts +110 -0
- package/template/base/src/use-case/task.ts +166 -0
- package/template/base/src/use-case/user.ts +121 -0
- package/template/base/tailwind.config.ts +5 -4
- package/template/base/tsconfig.json +3 -2
- package/template/prisma/.env.example +16 -0
- package/template/prisma/.eslintrc.cjs +24 -0
- package/template/prisma/components.json +17 -0
- package/template/prisma/next.config.mjs +15 -0
- package/template/prisma/package.json +80 -0
- package/template/prisma/public/next.svg +1 -0
- package/template/prisma/src/app/(app)/dashboard/page.tsx +19 -0
- package/template/prisma/src/app/(app)/layout.tsx +90 -0
- package/template/prisma/src/app/(app)/settings/actions.ts +18 -0
- package/template/prisma/src/app/(app)/settings/loading.tsx +28 -0
- package/template/prisma/src/app/(app)/settings/page.tsx +28 -0
- package/template/prisma/src/app/(app)/settings/render.tsx +113 -0
- package/template/prisma/src/app/(app)/tasks/[id]/actions.ts +147 -0
- package/template/prisma/src/app/(app)/tasks/[id]/page.tsx +25 -0
- package/template/prisma/src/app/(app)/tasks/[id]/render.tsx +413 -0
- package/template/prisma/src/app/(app)/tasks/actions.ts +69 -0
- package/template/prisma/src/app/(app)/tasks/page.tsx +53 -0
- package/template/prisma/src/app/(app)/tasks/render.tsx +107 -0
- package/template/prisma/src/app/(app)/users/[id]/actions.ts +83 -0
- package/template/prisma/src/app/(app)/users/[id]/page.tsx +32 -0
- package/template/prisma/src/app/(app)/users/[id]/render.tsx +240 -0
- package/template/prisma/src/app/(app)/users/actions.ts +55 -0
- package/template/prisma/src/app/(app)/users/page.tsx +49 -0
- package/template/prisma/src/app/(app)/users/render.tsx +80 -0
- package/template/prisma/src/app/(auth)/layout.tsx +20 -0
- package/template/prisma/src/app/(auth)/login/page.tsx +49 -0
- package/template/prisma/src/app/(marketing)/layout.tsx +42 -0
- package/template/prisma/src/app/(marketing)/page.tsx +96 -0
- package/template/prisma/src/app/api/auth/[...nextauth]/route.ts +7 -0
- package/template/prisma/src/app/favicon.ico +0 -0
- package/template/prisma/src/app/layout.tsx +34 -0
- package/template/prisma/src/components/app-nav-command.tsx +160 -0
- package/template/prisma/src/components/dark-mode-toggle.tsx +43 -0
- package/template/prisma/src/components/data-table/data-table-column-header.tsx +91 -0
- package/template/prisma/src/components/data-table/data-table-faceted-filter.tsx +149 -0
- package/template/prisma/src/components/data-table/data-table-loading.tsx +77 -0
- package/template/prisma/src/components/data-table/data-table-pagination.tsx +94 -0
- package/template/prisma/src/components/data-table/data-table-toolbar.tsx +78 -0
- package/template/prisma/src/components/data-table/data-table-types.ts +17 -0
- package/template/prisma/src/components/data-table/data-table-view-options.tsx +59 -0
- package/template/prisma/src/components/data-table/data-table.tsx +301 -0
- package/template/prisma/src/components/data-table/simple-data-table.tsx +109 -0
- package/template/prisma/src/components/empty-placeholder.tsx +78 -0
- package/template/prisma/src/components/heading.tsx +17 -0
- package/template/prisma/src/components/icons.tsx +85 -0
- package/template/prisma/src/components/main-nav.tsx +64 -0
- package/template/prisma/src/components/shell.tsx +13 -0
- package/template/prisma/src/components/side-nav.tsx +51 -0
- package/template/prisma/src/components/site-footer.tsx +31 -0
- package/template/prisma/src/components/system-info.tsx +36 -0
- package/template/prisma/src/components/ui/alert-dialog.tsx +141 -0
- package/template/prisma/src/components/ui/avatar.tsx +50 -0
- package/template/prisma/src/components/ui/badge.tsx +36 -0
- package/template/prisma/src/components/ui/button.tsx +56 -0
- package/template/prisma/src/components/ui/card.tsx +79 -0
- package/template/prisma/src/components/ui/checkbox.tsx +30 -0
- package/template/prisma/src/components/ui/command.tsx +155 -0
- package/template/prisma/src/components/ui/dialog.tsx +122 -0
- package/template/prisma/src/components/ui/dropdown-menu.tsx +200 -0
- package/template/prisma/src/components/ui/form.tsx +176 -0
- package/template/prisma/src/components/ui/input.tsx +25 -0
- package/template/prisma/src/components/ui/label.tsx +26 -0
- package/template/prisma/src/components/ui/popover.tsx +31 -0
- package/template/prisma/src/components/ui/select.tsx +160 -0
- package/template/prisma/src/components/ui/separator.tsx +31 -0
- package/template/prisma/src/components/ui/skeleton.tsx +15 -0
- package/template/prisma/src/components/ui/table.tsx +117 -0
- package/template/prisma/src/components/user-account-nav.tsx +60 -0
- package/template/prisma/src/components/user-avatar.tsx +25 -0
- package/template/prisma/src/env.mjs +78 -0
- package/template/prisma/src/hooks/use-debounce.ts +17 -0
- package/template/prisma/src/hooks/use-lock-body.tsx +12 -0
- package/template/prisma/src/lib/auth.ts +80 -0
- package/template/prisma/src/lib/cn.ts +4 -0
- package/template/prisma/src/lib/delay.ts +2 -0
- package/template/prisma/src/lib/formatDate.ts +11 -0
- package/template/prisma/src/lib/generateLabel.ts +5 -0
- package/template/prisma/src/lib/siteConfig.ts +4 -0
- package/template/prisma/src/styles/globals.css +76 -0
- package/template/prisma/tailwind.config.ts +80 -0
- package/template/prisma/tsconfig.json +46 -0
- /package/template/{advanced/src/styles → base/src/app}/globals.css +0 -0
- /package/template/{advanced/src/hooks/use-debounce.ts → base/src/hooks/use-debounce.tsx} +0 -0
- /package/template/{base → prisma}/postcss.config.cjs +0 -0
- /package/template/{base → prisma}/prettier.config.ts +0 -0
- /package/template/{base → prisma}/prisma/schema.prisma +0 -0
- /package/template/{base → prisma}/src/app/(auth)/login/user-auth-form.tsx +0 -0
- /package/template/{base → prisma}/src/app/api/upload/route.ts +0 -0
- /package/template/{advanced → prisma}/src/components/mobile-nav.tsx +0 -0
- /package/template/{base → prisma}/src/components/theme-provider.tsx +0 -0
- /package/template/{base → prisma}/src/components/ui/textarea.tsx +0 -0
- /package/template/{base → prisma}/src/components/ui/toast.tsx +0 -0
- /package/template/{base → prisma}/src/components/ui/toaster.tsx +0 -0
- /package/template/{base → prisma}/src/components/ui/use-toast.ts +0 -0
- /package/template/{base → prisma}/src/lib/db.ts +0 -0
- /package/template/{base → prisma}/src/lib/storageClient.ts +0 -0
- /package/template/{base → prisma}/src/styles/editor.css +0 -0
- /package/template/{base → prisma}/src/types/UnwrapPromise.ts +0 -0
- /package/template/{advanced → prisma-advanced}/.env.example +0 -0
- /package/template/{advanced → prisma-advanced}/.eslintrc.cjs +0 -0
- /package/template/{advanced → prisma-advanced}/components.json +0 -0
- /package/template/{advanced → prisma-advanced}/next.config.mjs +0 -0
- /package/template/{advanced → prisma-advanced}/package.json +0 -0
- /package/template/{advanced → prisma-advanced}/postcss.config.cjs +0 -0
- /package/template/{advanced → prisma-advanced}/prettier.config.ts +0 -0
- /package/template/{advanced → prisma-advanced}/prisma/schema.prisma +0 -0
- /package/template/{advanced → prisma-advanced}/public/next.svg +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/dashboard/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/layout.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/roles/[id]/actions.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/roles/[id]/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/roles/[id]/render.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/roles/actions.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/roles/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/roles/render.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/settings/actions.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/settings/loading.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/settings/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/settings/render.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/tasks/[id]/actions.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/tasks/[id]/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/tasks/[id]/render.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/tasks/actions.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/tasks/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/tasks/render.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/users/[id]/actions.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/users/[id]/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/users/[id]/render.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/users/actions.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/users/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(app)/users/render.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(auth)/layout.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(auth)/login/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(auth)/login/user-auth-form.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(marketing)/layout.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/(marketing)/page.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/api/auth/[...nextauth]/route.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/api/upload/route.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/favicon.ico +0 -0
- /package/template/{advanced → prisma-advanced}/src/app/layout.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/app-nav-command.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/dark-mode-toggle.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-column-header.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-faceted-filter.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-loading.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-pagination.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-toolbar.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-types.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-view-options.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/data-table/data-table.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/data-table/simple-data-table.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/empty-placeholder.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/heading.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/icons.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/main-nav.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/shell.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/side-nav.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/site-footer.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/system-info.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/theme-provider.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/alert-dialog.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/avatar.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/badge.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/button.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/card.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/checkbox.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/command.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/dialog.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/dropdown-menu.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/form.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/input.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/label.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/popover.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/select.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/separator.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/skeleton.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/table.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/textarea.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/toast.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/toaster.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/ui/use-toast.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/user-account-nav.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/components/user-avatar.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/env.mjs +0 -0
- /package/template/{base → prisma-advanced}/src/hooks/use-debounce.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/hooks/use-lock-body.tsx +0 -0
- /package/template/{advanced → prisma-advanced}/src/lib/auth.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/lib/cn.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/lib/db.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/lib/delay.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/lib/formatDate.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/lib/generateLabel.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/lib/siteConfig.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/lib/storageClient.ts +0 -0
- /package/template/{advanced → prisma-advanced}/src/styles/editor.css +0 -0
- /package/template/{base → prisma-advanced}/src/styles/globals.css +0 -0
- /package/template/{advanced → prisma-advanced}/src/types/UnwrapPromise.ts +0 -0
- /package/template/{advanced → prisma-advanced}/tailwind.config.ts +0 -0
- /package/template/{advanced → prisma-advanced}/tsconfig.json +0 -0
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
import { createEnv } from '@t3-oss/env-nextjs'
|
|
2
|
+
import { z } from 'zod'
|
|
3
|
+
|
|
4
|
+
export const env = createEnv({
|
|
5
|
+
/**
|
|
6
|
+
* Specify your server-side environment variables schema here. This way you can ensure the app
|
|
7
|
+
* isn't built with invalid env vars.
|
|
8
|
+
*/
|
|
9
|
+
server: {
|
|
10
|
+
NODE_ENV: z.enum(['development', 'test', 'production']),
|
|
11
|
+
DATABASE_URL: z.string().url(),
|
|
12
|
+
NEXTAUTH_SECRET:
|
|
13
|
+
process.env.NODE_ENV === 'production'
|
|
14
|
+
? z.string().min(1)
|
|
15
|
+
: z.string().min(1).optional(),
|
|
16
|
+
NEXTAUTH_URL: z.preprocess(
|
|
17
|
+
// This makes Vercel deployments not fail if you don't set NEXTAUTH_URL
|
|
18
|
+
// Since NextAuth.js automatically uses the VERCEL_URL if present.
|
|
19
|
+
str => process.env.VERCEL_URL ?? str,
|
|
20
|
+
// VERCEL_URL doesn't include `https` so it cant be validated as a URL
|
|
21
|
+
process.env.VERCEL ? z.string().min(1) : z.string().url()
|
|
22
|
+
),
|
|
23
|
+
EMAIL_SERVER_HOST: z.string().min(1),
|
|
24
|
+
EMAIL_SERVER_PORT: z.number(),
|
|
25
|
+
EMAIL_SERVER_USER: z.string().min(1),
|
|
26
|
+
EMAIL_SERVER_PASSWORD: z.string().min(1),
|
|
27
|
+
EMAIL_FROM: z.string().email(),
|
|
28
|
+
GOOGLE_ID: z.string().min(1),
|
|
29
|
+
GOOGLE_SECRET: z.string().min(1),
|
|
30
|
+
GITHUB_ID: z.string().min(1),
|
|
31
|
+
GITHUB_SECRET: z.string().min(1),
|
|
32
|
+
FIREBASE_PROJECT_ID: z.string().min(1),
|
|
33
|
+
FIREBASE_PRIVATE_KEY: z.string().min(1),
|
|
34
|
+
FIREBASE_CLIENT_EMAIL: z.string().min(1),
|
|
35
|
+
FIREBASE_STORAGE_BUCKET: z.string().min(1)
|
|
36
|
+
},
|
|
37
|
+
|
|
38
|
+
/**
|
|
39
|
+
* Specify your client-side environment variables schema here. This way you can ensure the app
|
|
40
|
+
* isn't built with invalid env vars. To expose them to the client, prefix them with
|
|
41
|
+
* `NEXT_PUBLIC_`.
|
|
42
|
+
*/
|
|
43
|
+
client: {
|
|
44
|
+
// NEXT_PUBLIC_CLIENTVAR: z.string().min(1),
|
|
45
|
+
},
|
|
46
|
+
|
|
47
|
+
/**
|
|
48
|
+
* You can't destruct `process.env` as a regular object in the Next.js edge runtimes (e.g.
|
|
49
|
+
* middlewares) or client-side so we need to destruct manually.
|
|
50
|
+
*/
|
|
51
|
+
runtimeEnv: {
|
|
52
|
+
NODE_ENV: process.env.NODE_ENV,
|
|
53
|
+
DATABASE_URL: process.env.DATABASE_URL,
|
|
54
|
+
NEXTAUTH_SECRET: process.env.NEXTAUTH_SECRET,
|
|
55
|
+
NEXTAUTH_URL: process.env.NEXTAUTH_URL,
|
|
56
|
+
EMAIL_SERVER_HOST: process.env.EMAIL_SERVER_HOST,
|
|
57
|
+
EMAIL_SERVER_PORT: parseInt(process.env.EMAIL_SERVER_PORT || ''),
|
|
58
|
+
EMAIL_SERVER_USER: process.env.EMAIL_SERVER_USER,
|
|
59
|
+
EMAIL_SERVER_PASSWORD: process.env.EMAIL_SERVER_PASSWORD,
|
|
60
|
+
EMAIL_FROM: process.env.EMAIL_FROM,
|
|
61
|
+
GOOGLE_ID: process.env.GOOGLE_ID,
|
|
62
|
+
GOOGLE_SECRET: process.env.GOOGLE_SECRET,
|
|
63
|
+
GITHUB_ID: process.env.GITHUB_ID,
|
|
64
|
+
GITHUB_SECRET: process.env.GITHUB_SECRET,
|
|
65
|
+
FIREBASE_PROJECT_ID: process.env.FIREBASE_PROJECT_ID,
|
|
66
|
+
FIREBASE_PRIVATE_KEY: process.env.FIREBASE_PRIVATE_KEY,
|
|
67
|
+
FIREBASE_CLIENT_EMAIL: process.env.FIREBASE_CLIENT_EMAIL,
|
|
68
|
+
FIREBASE_STORAGE_BUCKET: process.env.FIREBASE_STORAGE_BUCKET
|
|
69
|
+
},
|
|
70
|
+
/**
|
|
71
|
+
* Run `build` or `dev` with `SKIP_ENV_VALIDATION` to skip env validation.
|
|
72
|
+
* This is especially useful for Docker builds.
|
|
73
|
+
*/
|
|
74
|
+
skipValidation: !!process.env.SKIP_ENV_VALIDATION,
|
|
75
|
+
|
|
76
|
+
// This makes empty strings be treated as undefined
|
|
77
|
+
emptyStringAsUndefined: true
|
|
78
|
+
})
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
'use client'
|
|
2
|
+
|
|
3
|
+
import { useEffect, useState } from 'react'
|
|
4
|
+
|
|
5
|
+
export function useDebounce<T>(value: T, delay?: number): T {
|
|
6
|
+
const [debouncedValue, setDebouncedValue] = useState<T>(value)
|
|
7
|
+
|
|
8
|
+
useEffect(() => {
|
|
9
|
+
const timer = setTimeout(() => setDebouncedValue(value), delay || 500)
|
|
10
|
+
|
|
11
|
+
return () => {
|
|
12
|
+
clearTimeout(timer)
|
|
13
|
+
}
|
|
14
|
+
}, [value, delay])
|
|
15
|
+
|
|
16
|
+
return debouncedValue
|
|
17
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { useLayoutEffect } from 'react'
|
|
2
|
+
|
|
3
|
+
// @see https://usehooks.com/useLockBodyScroll.
|
|
4
|
+
export function useLockBody() {
|
|
5
|
+
useLayoutEffect((): (() => void) => {
|
|
6
|
+
const originalStyle: string = window.getComputedStyle(
|
|
7
|
+
document.body
|
|
8
|
+
).overflow
|
|
9
|
+
document.body.style.overflow = 'hidden'
|
|
10
|
+
return () => (document.body.style.overflow = originalStyle)
|
|
11
|
+
}, [])
|
|
12
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import { PrismaAdapter } from '@next-auth/prisma-adapter'
|
|
2
|
+
import { User as PrismaUser } from '@prisma/client'
|
|
3
|
+
import {
|
|
4
|
+
getServerSession,
|
|
5
|
+
type DefaultSession,
|
|
6
|
+
type NextAuthOptions
|
|
7
|
+
} from 'next-auth'
|
|
8
|
+
import EmailProvider from 'next-auth/providers/email'
|
|
9
|
+
import GitHubProvider from 'next-auth/providers/github'
|
|
10
|
+
import GoogleProvider from 'next-auth/providers/google'
|
|
11
|
+
|
|
12
|
+
import { env } from '@/env.mjs'
|
|
13
|
+
import { prisma } from '@/lib/db'
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* Module augmentation for `next-auth` types. Allows us to add custom properties to the `session`
|
|
17
|
+
* object and keep type safety.
|
|
18
|
+
*
|
|
19
|
+
* @see https://next-auth.js.org/getting-started/typescript#module-augmentation
|
|
20
|
+
*/
|
|
21
|
+
declare module 'next-auth' {
|
|
22
|
+
interface Session extends DefaultSession {
|
|
23
|
+
user: {
|
|
24
|
+
id: string
|
|
25
|
+
} & DefaultSession['user']
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
interface User extends PrismaUser {}
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
/**
|
|
32
|
+
* Options for NextAuth.js used to configure adapters, providers, callbacks, etc.
|
|
33
|
+
*
|
|
34
|
+
* @see https://next-auth.js.org/configuration/options
|
|
35
|
+
*/
|
|
36
|
+
export const authOptions: NextAuthOptions = {
|
|
37
|
+
pages: {
|
|
38
|
+
signIn: '/login'
|
|
39
|
+
},
|
|
40
|
+
callbacks: {
|
|
41
|
+
session({ session, user }) {
|
|
42
|
+
return {
|
|
43
|
+
...session,
|
|
44
|
+
user: {
|
|
45
|
+
...session.user,
|
|
46
|
+
id: user.id
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
},
|
|
51
|
+
adapter: PrismaAdapter(prisma),
|
|
52
|
+
providers: [
|
|
53
|
+
EmailProvider({
|
|
54
|
+
server: {
|
|
55
|
+
host: env.EMAIL_SERVER_HOST,
|
|
56
|
+
port: env.EMAIL_SERVER_PORT,
|
|
57
|
+
auth: {
|
|
58
|
+
user: env.EMAIL_SERVER_USER,
|
|
59
|
+
pass: env.EMAIL_SERVER_PASSWORD
|
|
60
|
+
}
|
|
61
|
+
},
|
|
62
|
+
from: env.EMAIL_FROM
|
|
63
|
+
}),
|
|
64
|
+
GoogleProvider({
|
|
65
|
+
clientId: env.GOOGLE_ID,
|
|
66
|
+
clientSecret: env.GOOGLE_SECRET
|
|
67
|
+
}),
|
|
68
|
+
GitHubProvider({
|
|
69
|
+
clientId: env.GITHUB_ID,
|
|
70
|
+
clientSecret: env.GITHUB_SECRET
|
|
71
|
+
})
|
|
72
|
+
]
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
/**
|
|
76
|
+
* Wrapper for `getServerSession` so that you don't need to import the `authOptions` in every file.
|
|
77
|
+
*
|
|
78
|
+
* @see https://next-auth.js.org/configuration/nextjs
|
|
79
|
+
*/
|
|
80
|
+
export const getAuthSession = () => getServerSession(authOptions)
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import dayjs from 'dayjs'
|
|
2
|
+
import relativeTime from 'dayjs/plugin/relativeTime'
|
|
3
|
+
|
|
4
|
+
dayjs.extend(relativeTime)
|
|
5
|
+
|
|
6
|
+
export const formatDate = (date: Date) => dayjs(date).format('DD/MM/YYYY')
|
|
7
|
+
|
|
8
|
+
export const formatDateTime = (date: Date) =>
|
|
9
|
+
dayjs(date).format('DD/MM/YYYY hh:mm:ss A')
|
|
10
|
+
|
|
11
|
+
export const timesAgo = (date: Date) => dayjs(date).fromNow()
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
@tailwind base;
|
|
2
|
+
@tailwind components;
|
|
3
|
+
@tailwind utilities;
|
|
4
|
+
|
|
5
|
+
@layer base {
|
|
6
|
+
:root {
|
|
7
|
+
--background: 0 0% 100%;
|
|
8
|
+
--foreground: 0 0% 3.9%;
|
|
9
|
+
|
|
10
|
+
--card: 0 0% 100%;
|
|
11
|
+
--card-foreground: 0 0% 3.9%;
|
|
12
|
+
|
|
13
|
+
--popover: 0 0% 100%;
|
|
14
|
+
--popover-foreground: 0 0% 3.9%;
|
|
15
|
+
|
|
16
|
+
--primary: 0 0% 9%;
|
|
17
|
+
--primary-foreground: 0 0% 98%;
|
|
18
|
+
|
|
19
|
+
--secondary: 0 0% 96.1%;
|
|
20
|
+
--secondary-foreground: 0 0% 9%;
|
|
21
|
+
|
|
22
|
+
--muted: 0 0% 96.1%;
|
|
23
|
+
--muted-foreground: 0 0% 45.1%;
|
|
24
|
+
|
|
25
|
+
--accent: 0 0% 96.1%;
|
|
26
|
+
--accent-foreground: 0 0% 9%;
|
|
27
|
+
|
|
28
|
+
--destructive: 0 84.2% 60.2%;
|
|
29
|
+
--destructive-foreground: 0 0% 98%;
|
|
30
|
+
|
|
31
|
+
--border: 0 0% 89.8%;
|
|
32
|
+
--input: 0 0% 89.8%;
|
|
33
|
+
--ring: 0 0% 3.9%;
|
|
34
|
+
|
|
35
|
+
--radius: 0.5rem;
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
.dark {
|
|
39
|
+
--background: 0 0% 3.9%;
|
|
40
|
+
--foreground: 0 0% 98%;
|
|
41
|
+
|
|
42
|
+
--card: 0 0% 3.9%;
|
|
43
|
+
--card-foreground: 0 0% 98%;
|
|
44
|
+
|
|
45
|
+
--popover: 0 0% 3.9%;
|
|
46
|
+
--popover-foreground: 0 0% 98%;
|
|
47
|
+
|
|
48
|
+
--primary: 0 0% 98%;
|
|
49
|
+
--primary-foreground: 0 0% 9%;
|
|
50
|
+
|
|
51
|
+
--secondary: 0 0% 14.9%;
|
|
52
|
+
--secondary-foreground: 0 0% 98%;
|
|
53
|
+
|
|
54
|
+
--muted: 0 0% 14.9%;
|
|
55
|
+
--muted-foreground: 0 0% 63.9%;
|
|
56
|
+
|
|
57
|
+
--accent: 0 0% 14.9%;
|
|
58
|
+
--accent-foreground: 0 0% 98%;
|
|
59
|
+
|
|
60
|
+
--destructive: 0 62.8% 30.6%;
|
|
61
|
+
--destructive-foreground: 0 0% 98%;
|
|
62
|
+
|
|
63
|
+
--border: 0 0% 14.9%;
|
|
64
|
+
--input: 0 0% 14.9%;
|
|
65
|
+
--ring: 0 0% 83.1%;
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
@layer base {
|
|
70
|
+
* {
|
|
71
|
+
@apply border-border;
|
|
72
|
+
}
|
|
73
|
+
body {
|
|
74
|
+
@apply bg-background text-foreground;
|
|
75
|
+
}
|
|
76
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import type { Config } from 'tailwindcss'
|
|
2
|
+
|
|
3
|
+
const config = {
|
|
4
|
+
darkMode: ['class'],
|
|
5
|
+
content: ['./src/**/*.{js,ts,jsx,tsx,mdx}'],
|
|
6
|
+
prefix: '',
|
|
7
|
+
theme: {
|
|
8
|
+
container: {
|
|
9
|
+
center: true,
|
|
10
|
+
padding: '2rem',
|
|
11
|
+
screens: {
|
|
12
|
+
'2xl': '1400px'
|
|
13
|
+
}
|
|
14
|
+
},
|
|
15
|
+
extend: {
|
|
16
|
+
backgroundImage: {
|
|
17
|
+
'gradient-radial': 'radial-gradient(var(--tw-gradient-stops))',
|
|
18
|
+
'gradient-conic':
|
|
19
|
+
'conic-gradient(from 180deg at 50% 50%, var(--tw-gradient-stops))'
|
|
20
|
+
},
|
|
21
|
+
colors: {
|
|
22
|
+
border: 'hsl(var(--border))',
|
|
23
|
+
input: 'hsl(var(--input))',
|
|
24
|
+
ring: 'hsl(var(--ring))',
|
|
25
|
+
background: 'hsl(var(--background))',
|
|
26
|
+
foreground: 'hsl(var(--foreground))',
|
|
27
|
+
primary: {
|
|
28
|
+
DEFAULT: 'hsl(var(--primary))',
|
|
29
|
+
foreground: 'hsl(var(--primary-foreground))'
|
|
30
|
+
},
|
|
31
|
+
secondary: {
|
|
32
|
+
DEFAULT: 'hsl(var(--secondary))',
|
|
33
|
+
foreground: 'hsl(var(--secondary-foreground))'
|
|
34
|
+
},
|
|
35
|
+
destructive: {
|
|
36
|
+
DEFAULT: 'hsl(var(--destructive))',
|
|
37
|
+
foreground: 'hsl(var(--destructive-foreground))'
|
|
38
|
+
},
|
|
39
|
+
muted: {
|
|
40
|
+
DEFAULT: 'hsl(var(--muted))',
|
|
41
|
+
foreground: 'hsl(var(--muted-foreground))'
|
|
42
|
+
},
|
|
43
|
+
accent: {
|
|
44
|
+
DEFAULT: 'hsl(var(--accent))',
|
|
45
|
+
foreground: 'hsl(var(--accent-foreground))'
|
|
46
|
+
},
|
|
47
|
+
popover: {
|
|
48
|
+
DEFAULT: 'hsl(var(--popover))',
|
|
49
|
+
foreground: 'hsl(var(--popover-foreground))'
|
|
50
|
+
},
|
|
51
|
+
card: {
|
|
52
|
+
DEFAULT: 'hsl(var(--card))',
|
|
53
|
+
foreground: 'hsl(var(--card-foreground))'
|
|
54
|
+
}
|
|
55
|
+
},
|
|
56
|
+
borderRadius: {
|
|
57
|
+
lg: 'var(--radius)',
|
|
58
|
+
md: 'calc(var(--radius) - 2px)',
|
|
59
|
+
sm: 'calc(var(--radius) - 4px)'
|
|
60
|
+
},
|
|
61
|
+
keyframes: {
|
|
62
|
+
'accordion-down': {
|
|
63
|
+
from: { height: '0' },
|
|
64
|
+
to: { height: 'var(--radix-accordion-content-height)' }
|
|
65
|
+
},
|
|
66
|
+
'accordion-up': {
|
|
67
|
+
from: { height: 'var(--radix-accordion-content-height)' },
|
|
68
|
+
to: { height: '0' }
|
|
69
|
+
}
|
|
70
|
+
},
|
|
71
|
+
animation: {
|
|
72
|
+
'accordion-down': 'accordion-down 0.2s ease-out',
|
|
73
|
+
'accordion-up': 'accordion-up 0.2s ease-out'
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
},
|
|
77
|
+
plugins: [require('tailwindcss-animate'), require('@tailwindcss/typography')]
|
|
78
|
+
} satisfies Config
|
|
79
|
+
|
|
80
|
+
export default config
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
{
|
|
2
|
+
"compilerOptions": {
|
|
3
|
+
"target": "ES2017",
|
|
4
|
+
"lib": ["DOM", "DOM.Iterable", "ESNext"],
|
|
5
|
+
"allowJs": true,
|
|
6
|
+
"checkJs": true,
|
|
7
|
+
"skipLibCheck": true,
|
|
8
|
+
"strict": true,
|
|
9
|
+
"noImplicitAny": true,
|
|
10
|
+
"strictNullChecks": true,
|
|
11
|
+
"strictFunctionTypes": true,
|
|
12
|
+
"noImplicitThis": true,
|
|
13
|
+
"noUncheckedIndexedAccess": true,
|
|
14
|
+
"noUnusedLocals": true,
|
|
15
|
+
"noUnusedParameters": true,
|
|
16
|
+
"noImplicitReturns": true,
|
|
17
|
+
"noFallthroughCasesInSwitch": true,
|
|
18
|
+
"forceConsistentCasingInFileNames": true,
|
|
19
|
+
"noEmit": true,
|
|
20
|
+
"esModuleInterop": true,
|
|
21
|
+
"module": "ESNext",
|
|
22
|
+
"moduleResolution": "Bundler",
|
|
23
|
+
"resolveJsonModule": true,
|
|
24
|
+
"isolatedModules": true,
|
|
25
|
+
"jsx": "preserve",
|
|
26
|
+
"incremental": true,
|
|
27
|
+
"plugins": [
|
|
28
|
+
{
|
|
29
|
+
"name": "next"
|
|
30
|
+
}
|
|
31
|
+
],
|
|
32
|
+
"paths": {
|
|
33
|
+
"@/*": ["./src/*"]
|
|
34
|
+
}
|
|
35
|
+
},
|
|
36
|
+
"include": [
|
|
37
|
+
".eslintrc.cjs",
|
|
38
|
+
"next-env.d.ts",
|
|
39
|
+
"**/*.ts",
|
|
40
|
+
"**/*.tsx",
|
|
41
|
+
"**/*.cjs",
|
|
42
|
+
"**/*.mjs",
|
|
43
|
+
".next/types/**/*.ts"
|
|
44
|
+
],
|
|
45
|
+
"exclude": ["node_modules"]
|
|
46
|
+
}
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
/package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-loading.tsx
RENAMED
|
File without changes
|
/package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-pagination.tsx
RENAMED
|
File without changes
|
/package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-toolbar.tsx
RENAMED
|
File without changes
|
/package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-types.ts
RENAMED
|
File without changes
|
/package/template/{advanced → prisma-advanced}/src/components/data-table/data-table-view-options.tsx
RENAMED
|
File without changes
|
|
File without changes
|
/package/template/{advanced → prisma-advanced}/src/components/data-table/simple-data-table.tsx
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|