create-next-pro-cli 0.1.26 → 0.1.27
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 +205 -292
- package/create-next-pro-completion.sh +8 -38
- package/create-next-pro-completion.zsh +13 -0
- package/dist/bin.bun.js +1127 -628
- package/dist/bin.node.js +1170 -617
- package/dist/bin.node.js.map +1 -1
- package/package.json +49 -27
- package/templates/Projects/default/.env.example +17 -0
- package/templates/Projects/default/.github/workflows/quality.yml +24 -0
- package/templates/Projects/default/.gitignore.template +47 -0
- package/templates/Projects/default/.prettierignore +3 -0
- package/templates/Projects/default/README.md +52 -108
- package/templates/Projects/default/bun.lock +1152 -0
- package/templates/Projects/default/eslint.config.mjs +27 -11
- package/templates/Projects/default/messages/en/_global_ui.json +23 -10
- package/templates/Projects/default/messages/en.ts +17 -2
- package/templates/Projects/default/messages/fr/_global_ui.json +23 -10
- package/templates/Projects/default/messages/fr.ts +17 -2
- package/templates/Projects/default/next.config.ts +43 -3
- package/templates/Projects/default/package.json +42 -24
- package/templates/Projects/default/playwright.config.ts +26 -0
- package/templates/Projects/default/pnpm-workspace.yaml +5 -0
- package/templates/Projects/default/public/{cnp-logo.svg → logo.svg} +1 -1
- package/templates/Projects/default/src/app/[locale]/(public)/layout.tsx +8 -1
- package/templates/Projects/default/src/app/[locale]/(public)/login/page.tsx +8 -0
- package/templates/Projects/default/src/app/[locale]/(public)/register/page.tsx +8 -0
- package/templates/Projects/default/src/app/[locale]/(user)/dashboard/error.tsx +25 -0
- package/templates/Projects/default/src/app/[locale]/(user)/dashboard/loading.tsx +5 -0
- package/templates/Projects/default/src/app/[locale]/(user)/{Dashboard → dashboard}/page.tsx +1 -1
- package/templates/Projects/default/src/app/[locale]/(user)/layout.tsx +24 -2
- package/templates/Projects/default/src/app/[locale]/(user)/settings/loading.tsx +5 -0
- package/templates/Projects/default/src/app/[locale]/(user)/{Settings → settings}/page.tsx +1 -2
- package/templates/Projects/default/src/app/[locale]/(user)/userInfo/loading.tsx +5 -0
- package/templates/Projects/default/src/app/[locale]/(user)/{UserInfo → userInfo}/page.tsx +1 -2
- package/templates/Projects/default/src/app/[locale]/layout.tsx +34 -10
- package/templates/Projects/default/src/app/[locale]/loading.tsx +0 -9
- package/templates/Projects/default/src/app/[locale]/not-found.tsx +6 -15
- package/templates/Projects/default/src/app/[locale]/page.tsx +10 -1
- package/templates/Projects/default/src/app/api/auth/[...nextauth]/route.ts +8 -60
- package/templates/Projects/default/src/app/not-found.tsx +1 -1
- package/templates/Projects/default/src/app/sitemap.ts +2 -2
- package/templates/Projects/default/src/app/styles/globals.css +166 -113
- package/templates/Projects/default/src/auth.ts +20 -0
- package/templates/Projects/default/src/config.ts +3 -3
- package/templates/Projects/default/src/env.ts +65 -0
- package/templates/Projects/default/src/lib/i18n/messages.ts +8 -0
- package/templates/Projects/default/src/lib/i18n/request.ts +2 -16
- package/templates/Projects/default/src/lib/security/csp.ts +16 -0
- package/templates/Projects/default/src/lib/utils.ts +2 -1
- package/templates/Projects/default/src/proxy.ts +13 -0
- package/templates/Projects/default/src/ui/_global/BackButton.tsx +4 -2
- package/templates/Projects/default/src/ui/_global/Button.tsx +3 -8
- package/templates/Projects/default/src/ui/_global/GlobalHeader.tsx +10 -28
- package/templates/Projects/default/src/ui/_global/GlobalMain.tsx +1 -1
- package/templates/Projects/default/src/ui/_global/LocaleSwitcher.tsx +9 -10
- package/templates/Projects/default/src/ui/_global/PublicNav.tsx +51 -17
- package/templates/Projects/default/src/ui/_global/ThemeToggle.tsx +45 -39
- package/templates/Projects/default/src/ui/_global/UserNav.tsx +6 -6
- package/templates/Projects/default/src/ui/_home/page-ui.tsx +5 -7
- package/templates/Projects/default/src/ui/{Dashboard → dashboard}/LogoutButton.tsx +9 -7
- package/templates/Projects/default/src/ui/{Dashboard → dashboard}/StatsCard.tsx +4 -4
- package/templates/Projects/default/src/ui/{Dashboard → dashboard}/page-ui.tsx +7 -8
- package/templates/Projects/default/src/ui/login/page-ui.tsx +36 -0
- package/templates/Projects/default/src/ui/register/page-ui.tsx +38 -0
- package/templates/Projects/default/src/ui/settings/page-ui.tsx +15 -0
- package/templates/Projects/default/src/ui/userInfo/page-ui.tsx +15 -0
- package/templates/Projects/default/tailwind.config.ts +81 -1
- package/templates/Projects/default/tests/consumer/validate-template.ts +66 -0
- package/templates/Projects/default/tests/e2e/template-remediation.playwright.ts +106 -0
- package/templates/Projects/default/tests/rendering/verify-rendering.ts +56 -0
- package/templates/Projects/default/tests/unit/csp.test.ts +19 -0
- package/templates/Projects/default/tests/unit/env.test.ts +76 -0
- package/templates/Projects/default/tsconfig.json +6 -6
- package/templates/Projects/default/example.env +0 -8
- package/templates/Projects/default/messages/getMergedMessages.ts +0 -31
- package/templates/Projects/default/middleware.ts +0 -11
- package/templates/Projects/default/src/app/[locale]/(public)/Login/page.tsx +0 -6
- package/templates/Projects/default/src/app/[locale]/(public)/Register/page.tsx +0 -6
- package/templates/Projects/default/src/app/[locale]/(user)/Dashboard/error.tsx +0 -38
- package/templates/Projects/default/src/app/[locale]/(user)/Dashboard/loading.tsx +0 -10
- package/templates/Projects/default/src/app/[locale]/(user)/Settings/loading.tsx +0 -17
- package/templates/Projects/default/src/app/[locale]/(user)/UserInfo/loading.tsx +0 -17
- package/templates/Projects/default/src/app/api/auth/post-login/route.ts +0 -26
- package/templates/Projects/default/src/app/api/hello/route.ts +0 -5
- package/templates/Projects/default/src/app/layout.tsx +0 -11
- package/templates/Projects/default/src/app/page.tsx +0 -6
- package/templates/Projects/default/src/auth.config.ts +0 -0
- package/templates/Projects/default/src/lib/auth/disconnect.ts +0 -11
- package/templates/Projects/default/src/lib/auth/isConnected.ts +0 -18
- package/templates/Projects/default/src/lib/sample/example.ts +0 -3
- package/templates/Projects/default/src/lib/sample/index.ts +0 -3
- package/templates/Projects/default/src/ui/Login/page-ui.tsx +0 -22
- package/templates/Projects/default/src/ui/Register/page-ui.tsx +0 -26
- package/templates/Projects/default/src/ui/Settings/page-ui.tsx +0 -17
- package/templates/Projects/default/src/ui/UserInfo/page-ui.tsx +0 -17
- /package/templates/Projects/default/messages/en/{Dashboard.json → dashboard.json} +0 -0
- /package/templates/Projects/default/messages/en/{Login.json → login.json} +0 -0
- /package/templates/Projects/default/messages/en/{Register.json → register.json} +0 -0
- /package/templates/Projects/default/messages/en/{Settings.json → settings.json} +0 -0
- /package/templates/Projects/default/messages/en/{UserInfo.json → userInfo.json} +0 -0
- /package/templates/Projects/default/messages/fr/{Dashboard.json → dashboard.json} +0 -0
- /package/templates/Projects/default/messages/fr/{Login.json → login.json} +0 -0
- /package/templates/Projects/default/messages/fr/{Register.json → register.json} +0 -0
- /package/templates/Projects/default/messages/fr/{Settings.json → settings.json} +0 -0
- /package/templates/Projects/default/messages/fr/{UserInfo.json → userInfo.json} +0 -0
- /package/templates/Projects/default/public/{cnp-logo.png → logo.png} +0 -0
- /package/templates/Projects/default/src/ui/{Dashboard → dashboard}/WelcomeCard.tsx +0 -0
|
@@ -1,16 +1,32 @@
|
|
|
1
|
-
import
|
|
2
|
-
import
|
|
3
|
-
import { FlatCompat } from "@eslint/eslintrc";
|
|
4
|
-
|
|
5
|
-
const __filename = fileURLToPath(import.meta.url);
|
|
6
|
-
const __dirname = dirname(__filename);
|
|
7
|
-
|
|
8
|
-
const compat = new FlatCompat({
|
|
9
|
-
baseDirectory: __dirname,
|
|
10
|
-
});
|
|
1
|
+
import nextCoreWebVitals from "eslint-config-next/core-web-vitals";
|
|
2
|
+
import nextTypescript from "eslint-config-next/typescript";
|
|
11
3
|
|
|
12
4
|
const eslintConfig = [
|
|
13
|
-
...
|
|
5
|
+
...nextCoreWebVitals,
|
|
6
|
+
...nextTypescript,
|
|
7
|
+
{
|
|
8
|
+
rules: {
|
|
9
|
+
"react/jsx-key": "error",
|
|
10
|
+
"react/jsx-no-duplicate-props": "error",
|
|
11
|
+
"react/jsx-no-target-blank": "error",
|
|
12
|
+
"react/no-children-prop": "error",
|
|
13
|
+
"react/no-danger-with-children": "error",
|
|
14
|
+
"react/no-unknown-property": "error",
|
|
15
|
+
"react/no-unescaped-entities": "error",
|
|
16
|
+
},
|
|
17
|
+
},
|
|
18
|
+
{
|
|
19
|
+
ignores: [
|
|
20
|
+
"node_modules/**",
|
|
21
|
+
".next/**",
|
|
22
|
+
"out/**",
|
|
23
|
+
"build/**",
|
|
24
|
+
"artifacts/**",
|
|
25
|
+
"playwright-report/**",
|
|
26
|
+
"test-results/**",
|
|
27
|
+
"next-env.d.ts",
|
|
28
|
+
],
|
|
29
|
+
},
|
|
14
30
|
];
|
|
15
31
|
|
|
16
32
|
export default eslintConfig;
|
|
@@ -1,5 +1,21 @@
|
|
|
1
1
|
{
|
|
2
|
+
"user_nav": {
|
|
3
|
+
"links": {
|
|
4
|
+
"home": "Home",
|
|
5
|
+
"dashboard": "Dashboard",
|
|
6
|
+
"settings": "Settings",
|
|
7
|
+
"user_info": "User Information"
|
|
8
|
+
}
|
|
9
|
+
},
|
|
10
|
+
"Loading": {
|
|
11
|
+
"title": "Loading",
|
|
12
|
+
"description": "Please wait while we prepare your experience..."
|
|
13
|
+
},
|
|
14
|
+
"back": "Back",
|
|
15
|
+
"select_language": "Select language",
|
|
16
|
+
"toggle_theme": "Toggle theme",
|
|
2
17
|
"public_nav": {
|
|
18
|
+
"menu": "Public navigation menu",
|
|
3
19
|
"links": {
|
|
4
20
|
"home": "Home",
|
|
5
21
|
"login": "Login",
|
|
@@ -19,16 +35,13 @@
|
|
|
19
35
|
"search": "Search"
|
|
20
36
|
}
|
|
21
37
|
},
|
|
22
|
-
"
|
|
23
|
-
"
|
|
24
|
-
|
|
25
|
-
"dashboard": "Dashboard",
|
|
26
|
-
"settings": "Settings",
|
|
27
|
-
"user_info": "User Information"
|
|
28
|
-
}
|
|
38
|
+
"error": {
|
|
39
|
+
"title": "Something went wrong!",
|
|
40
|
+
"retry": "Try again"
|
|
29
41
|
},
|
|
30
|
-
"
|
|
31
|
-
"title": "
|
|
32
|
-
"description": "
|
|
42
|
+
"not_found": {
|
|
43
|
+
"title": "Not Found",
|
|
44
|
+
"description": "Could not find the requested resource",
|
|
45
|
+
"home": "Return Home"
|
|
33
46
|
}
|
|
34
47
|
}
|
|
@@ -1,4 +1,19 @@
|
|
|
1
|
-
import
|
|
1
|
+
import globalUi from "./en/_global_ui.json";
|
|
2
|
+
import home from "./en/_home.json";
|
|
3
|
+
import dashboard from "./en/dashboard.json";
|
|
4
|
+
import login from "./en/login.json";
|
|
5
|
+
import register from "./en/register.json";
|
|
6
|
+
import settings from "./en/settings.json";
|
|
7
|
+
import userInfo from "./en/userInfo.json";
|
|
8
|
+
|
|
9
|
+
const messages = {
|
|
10
|
+
_global_ui: globalUi,
|
|
11
|
+
_home: home,
|
|
12
|
+
dashboard,
|
|
13
|
+
login,
|
|
14
|
+
register,
|
|
15
|
+
settings,
|
|
16
|
+
userInfo,
|
|
17
|
+
};
|
|
2
18
|
|
|
3
|
-
const messages = await getMergedMessages(import.meta.url);
|
|
4
19
|
export default messages;
|
|
@@ -1,5 +1,21 @@
|
|
|
1
1
|
{
|
|
2
|
+
"user_nav": {
|
|
3
|
+
"links": {
|
|
4
|
+
"home": "Accueil",
|
|
5
|
+
"dashboard": "Tableau de bord",
|
|
6
|
+
"settings": "Paramètres",
|
|
7
|
+
"user_info": "Informations sur l'utilisateur"
|
|
8
|
+
}
|
|
9
|
+
},
|
|
10
|
+
"Loading": {
|
|
11
|
+
"title": "Chargement en cours",
|
|
12
|
+
"description": "Veuillez patienter pendant que nous préparons votre expérience..."
|
|
13
|
+
},
|
|
14
|
+
"back": "Retour",
|
|
15
|
+
"select_language": "Choisir la langue",
|
|
16
|
+
"toggle_theme": "Changer de thème",
|
|
2
17
|
"public_nav": {
|
|
18
|
+
"menu": "Menu de navigation publique",
|
|
3
19
|
"links": {
|
|
4
20
|
"home": "Accueil",
|
|
5
21
|
"login": "Connexion",
|
|
@@ -19,16 +35,13 @@
|
|
|
19
35
|
"search": "Recherche"
|
|
20
36
|
}
|
|
21
37
|
},
|
|
22
|
-
"
|
|
23
|
-
"
|
|
24
|
-
|
|
25
|
-
"dashboard": "Tableau de bord",
|
|
26
|
-
"settings": "Paramètres",
|
|
27
|
-
"user_info": "Informations sur l'utilisateur"
|
|
28
|
-
}
|
|
38
|
+
"error": {
|
|
39
|
+
"title": "Une erreur est survenue !",
|
|
40
|
+
"retry": "Réessayer"
|
|
29
41
|
},
|
|
30
|
-
"
|
|
31
|
-
"title": "
|
|
32
|
-
"description": "
|
|
42
|
+
"not_found": {
|
|
43
|
+
"title": "Page introuvable",
|
|
44
|
+
"description": "La ressource demandée est introuvable",
|
|
45
|
+
"home": "Retour à l'accueil"
|
|
33
46
|
}
|
|
34
47
|
}
|
|
@@ -1,4 +1,19 @@
|
|
|
1
|
-
import
|
|
1
|
+
import globalUi from "./fr/_global_ui.json";
|
|
2
|
+
import home from "./fr/_home.json";
|
|
3
|
+
import dashboard from "./fr/dashboard.json";
|
|
4
|
+
import login from "./fr/login.json";
|
|
5
|
+
import register from "./fr/register.json";
|
|
6
|
+
import settings from "./fr/settings.json";
|
|
7
|
+
import userInfo from "./fr/userInfo.json";
|
|
8
|
+
|
|
9
|
+
const messages = {
|
|
10
|
+
_global_ui: globalUi,
|
|
11
|
+
_home: home,
|
|
12
|
+
dashboard,
|
|
13
|
+
login,
|
|
14
|
+
register,
|
|
15
|
+
settings,
|
|
16
|
+
userInfo,
|
|
17
|
+
};
|
|
2
18
|
|
|
3
|
-
const messages = await getMergedMessages(import.meta.url);
|
|
4
19
|
export default messages;
|
|
@@ -1,10 +1,50 @@
|
|
|
1
1
|
import { NextConfig } from "next";
|
|
2
2
|
import createNextIntlPlugin from "next-intl/plugin";
|
|
3
|
+
import { createContentSecurityPolicy } from "./src/lib/security/csp";
|
|
4
|
+
|
|
5
|
+
const contentSecurityPolicy = createContentSecurityPolicy(
|
|
6
|
+
process.env.NODE_ENV !== "production",
|
|
7
|
+
);
|
|
3
8
|
|
|
4
9
|
const nextConfig: NextConfig = {
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
10
|
+
poweredByHeader: false,
|
|
11
|
+
async headers() {
|
|
12
|
+
const headers = [
|
|
13
|
+
{
|
|
14
|
+
key: "X-Frame-Options",
|
|
15
|
+
value: "DENY",
|
|
16
|
+
},
|
|
17
|
+
{
|
|
18
|
+
key: "X-Content-Type-Options",
|
|
19
|
+
value: "nosniff",
|
|
20
|
+
},
|
|
21
|
+
{
|
|
22
|
+
key: "Referrer-Policy",
|
|
23
|
+
value: "strict-origin-when-cross-origin",
|
|
24
|
+
},
|
|
25
|
+
{
|
|
26
|
+
key: "Permissions-Policy",
|
|
27
|
+
value: "camera=(), microphone=(), geolocation=()",
|
|
28
|
+
},
|
|
29
|
+
{
|
|
30
|
+
key: "Content-Security-Policy",
|
|
31
|
+
value: contentSecurityPolicy,
|
|
32
|
+
},
|
|
33
|
+
];
|
|
34
|
+
if (process.env.NODE_ENV === "production") {
|
|
35
|
+
headers.push({
|
|
36
|
+
key: "Strict-Transport-Security",
|
|
37
|
+
value: "max-age=31536000; includeSubDomains",
|
|
38
|
+
});
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
return [
|
|
42
|
+
{
|
|
43
|
+
source: "/(.*)",
|
|
44
|
+
headers,
|
|
45
|
+
},
|
|
46
|
+
];
|
|
47
|
+
},
|
|
8
48
|
};
|
|
9
49
|
|
|
10
50
|
const withNextIntl = createNextIntlPlugin("./src/lib/i18n/request.ts");
|
|
@@ -2,37 +2,55 @@
|
|
|
2
2
|
"name": "my-next-pro",
|
|
3
3
|
"version": "0.1.0",
|
|
4
4
|
"private": true,
|
|
5
|
+
"type": "module",
|
|
6
|
+
"packageManager": "bun@1.3.14",
|
|
7
|
+
"engines": {
|
|
8
|
+
"node": ">=24.0.0",
|
|
9
|
+
"bun": ">=1.3.14"
|
|
10
|
+
},
|
|
5
11
|
"scripts": {
|
|
6
12
|
"dev": "next dev --turbopack",
|
|
7
13
|
"build": "next build",
|
|
8
14
|
"start": "next start",
|
|
9
|
-
"lint": "
|
|
15
|
+
"lint": "eslint .",
|
|
16
|
+
"typecheck": "tsc --noEmit",
|
|
17
|
+
"format": "prettier --write .",
|
|
18
|
+
"format:check": "prettier --check .",
|
|
19
|
+
"test": "vitest run",
|
|
20
|
+
"test:e2e": "playwright test",
|
|
21
|
+
"verify:rendering": "node --experimental-strip-types tests/rendering/verify-rendering.ts",
|
|
22
|
+
"check": "prettier --check . && eslint . && tsc --noEmit && vitest run && next build && node --experimental-strip-types tests/rendering/verify-rendering.ts",
|
|
23
|
+
"test:consumer": "node --experimental-strip-types tests/consumer/validate-template.ts",
|
|
24
|
+
"audit": "bun audit"
|
|
10
25
|
},
|
|
11
26
|
"dependencies": {
|
|
12
|
-
"@radix-ui/react-slot": "
|
|
13
|
-
"class-variance-authority": "
|
|
14
|
-
"clsx": "
|
|
15
|
-
"
|
|
16
|
-
"
|
|
17
|
-
"
|
|
18
|
-
"next": "
|
|
19
|
-
"
|
|
20
|
-
"
|
|
21
|
-
"
|
|
22
|
-
"
|
|
23
|
-
"
|
|
24
|
-
"tailwindcss-animate": "^1.0.7"
|
|
27
|
+
"@radix-ui/react-slot": "1.3.0",
|
|
28
|
+
"class-variance-authority": "0.7.1",
|
|
29
|
+
"clsx": "2.1.1",
|
|
30
|
+
"lucide-react": "1.24.0",
|
|
31
|
+
"next": "16.2.10",
|
|
32
|
+
"next-auth": "5.0.0-beta.31",
|
|
33
|
+
"next-intl": "4.13.2",
|
|
34
|
+
"react": "19.2.7",
|
|
35
|
+
"react-dom": "19.2.7",
|
|
36
|
+
"simple-icons": "16.26.0",
|
|
37
|
+
"tailwind-merge": "3.6.0",
|
|
38
|
+
"tailwindcss-animate": "1.0.7"
|
|
25
39
|
},
|
|
26
40
|
"devDependencies": {
|
|
27
|
-
"@
|
|
28
|
-
"@tailwindcss/postcss": "
|
|
29
|
-
"@types/
|
|
30
|
-
"@types/
|
|
31
|
-
"@types/react": "
|
|
32
|
-
"
|
|
33
|
-
"eslint": "
|
|
34
|
-
"
|
|
35
|
-
"tailwindcss": "
|
|
36
|
-
"typescript": "
|
|
41
|
+
"@playwright/test": "1.61.1",
|
|
42
|
+
"@tailwindcss/postcss": "4.3.3",
|
|
43
|
+
"@types/node": "24.13.3",
|
|
44
|
+
"@types/react": "19.2.17",
|
|
45
|
+
"@types/react-dom": "19.2.3",
|
|
46
|
+
"eslint": "9.39.4",
|
|
47
|
+
"eslint-config-next": "16.2.10",
|
|
48
|
+
"prettier": "3.9.5",
|
|
49
|
+
"tailwindcss": "4.3.3",
|
|
50
|
+
"typescript": "6.0.3",
|
|
51
|
+
"vitest": "4.1.10"
|
|
52
|
+
},
|
|
53
|
+
"overrides": {
|
|
54
|
+
"postcss": "8.5.15"
|
|
37
55
|
}
|
|
38
56
|
}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
import { defineConfig, devices } from "@playwright/test";
|
|
2
|
+
|
|
3
|
+
export default defineConfig({
|
|
4
|
+
testDir: "./tests/e2e",
|
|
5
|
+
testMatch: "**/*.playwright.ts",
|
|
6
|
+
fullyParallel: true,
|
|
7
|
+
retries: process.env.CI ? 2 : 0,
|
|
8
|
+
reporter: process.env.CI ? "github" : "list",
|
|
9
|
+
use: {
|
|
10
|
+
baseURL: "http://127.0.0.1:3100",
|
|
11
|
+
trace: "retain-on-failure",
|
|
12
|
+
},
|
|
13
|
+
projects: [
|
|
14
|
+
{ name: "desktop", use: { ...devices["Desktop Chrome"] } },
|
|
15
|
+
{ name: "mobile", use: { ...devices["Pixel 5"] } },
|
|
16
|
+
],
|
|
17
|
+
webServer: {
|
|
18
|
+
command: "next build && next start --hostname 127.0.0.1 --port 3100",
|
|
19
|
+
url: "http://127.0.0.1:3100/en",
|
|
20
|
+
reuseExistingServer: !process.env.CI,
|
|
21
|
+
env: {
|
|
22
|
+
AUTH_DISABLED: "true",
|
|
23
|
+
NEXT_PUBLIC_APP_URL: "http://127.0.0.1:3100",
|
|
24
|
+
},
|
|
25
|
+
},
|
|
26
|
+
});
|
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
version="1.1"
|
|
9
9
|
id="svg1484"
|
|
10
10
|
inkscape:version="1.2.2 (b0a8486541, 2022-12-01)"
|
|
11
|
-
sodipodi:docname="
|
|
11
|
+
sodipodi:docname="logo.svg"
|
|
12
12
|
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
|
13
13
|
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
|
14
14
|
xmlns="http://www.w3.org/2000/svg"
|
|
@@ -1,9 +1,16 @@
|
|
|
1
1
|
import React from "react";
|
|
2
|
+
import GlobalHeader from "@/ui/_global/GlobalHeader";
|
|
3
|
+
import GlobalMain from "@/ui/_global/GlobalMain";
|
|
2
4
|
|
|
3
5
|
export default function PublicLayout({
|
|
4
6
|
children,
|
|
5
7
|
}: {
|
|
6
8
|
children: React.ReactNode;
|
|
7
9
|
}) {
|
|
8
|
-
return
|
|
10
|
+
return (
|
|
11
|
+
<>
|
|
12
|
+
<GlobalHeader hasSessionInitial={false} />
|
|
13
|
+
<GlobalMain>{children}</GlobalMain>
|
|
14
|
+
</>
|
|
15
|
+
);
|
|
9
16
|
}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
// app/[locale]/error.tsx
|
|
2
|
+
"use client";
|
|
3
|
+
|
|
4
|
+
import { useEffect } from "react";
|
|
5
|
+
import { useTranslations } from "next-intl";
|
|
6
|
+
|
|
7
|
+
export default function Error({
|
|
8
|
+
error,
|
|
9
|
+
reset,
|
|
10
|
+
}: {
|
|
11
|
+
error: Error & { digest?: string };
|
|
12
|
+
reset: () => void;
|
|
13
|
+
}) {
|
|
14
|
+
const t = useTranslations("_global_ui.error");
|
|
15
|
+
useEffect(() => {
|
|
16
|
+
console.error(error);
|
|
17
|
+
}, [error]);
|
|
18
|
+
|
|
19
|
+
return (
|
|
20
|
+
<div>
|
|
21
|
+
<h2>{t("title")}</h2>
|
|
22
|
+
<button onClick={() => reset()}>{t("retry")}</button>
|
|
23
|
+
</div>
|
|
24
|
+
);
|
|
25
|
+
}
|
|
@@ -1,9 +1,31 @@
|
|
|
1
1
|
// app/[locale]/(user)/layout.tsx
|
|
2
|
+
import { auth, isAuthConfigured } from "@/auth";
|
|
3
|
+
import { redirect } from "@/lib/i18n/navigation";
|
|
4
|
+
import GlobalHeader from "@/ui/_global/GlobalHeader";
|
|
5
|
+
import GlobalMain from "@/ui/_global/GlobalMain";
|
|
2
6
|
|
|
3
|
-
export default function UserLayout({
|
|
7
|
+
export default async function UserLayout({
|
|
4
8
|
children,
|
|
9
|
+
params,
|
|
5
10
|
}: {
|
|
6
11
|
children: React.ReactNode;
|
|
12
|
+
params: Promise<{ locale: string }>;
|
|
7
13
|
}) {
|
|
8
|
-
|
|
14
|
+
const { locale } = await params;
|
|
15
|
+
if (!isAuthConfigured()) {
|
|
16
|
+
redirect({ href: "/login", locale });
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
const session = await auth();
|
|
20
|
+
|
|
21
|
+
if (!session?.user) {
|
|
22
|
+
redirect({ href: "/login", locale });
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
return (
|
|
26
|
+
<>
|
|
27
|
+
<GlobalHeader hasSessionInitial />
|
|
28
|
+
<GlobalMain>{children}</GlobalMain>
|
|
29
|
+
</>
|
|
30
|
+
);
|
|
9
31
|
}
|
|
@@ -1,11 +1,26 @@
|
|
|
1
1
|
// app/[locale]/layout.tsx
|
|
2
2
|
import { NextIntlClientProvider } from "next-intl";
|
|
3
3
|
import { setRequestLocale } from "next-intl/server";
|
|
4
|
+
import { hasLocale } from "next-intl";
|
|
5
|
+
import type { Metadata } from "next";
|
|
6
|
+
import { notFound } from "next/navigation";
|
|
7
|
+
import Script from "next/script";
|
|
4
8
|
import React from "react";
|
|
5
|
-
import "@/app/styles/globals.css";
|
|
6
|
-
import
|
|
7
|
-
import
|
|
8
|
-
|
|
9
|
+
import "@/app/styles/globals.css";
|
|
10
|
+
import { routing } from "@/lib/i18n/routing";
|
|
11
|
+
import { getMessages } from "@/lib/i18n/messages";
|
|
12
|
+
|
|
13
|
+
export const metadata: Metadata = {
|
|
14
|
+
title: {
|
|
15
|
+
default: "Create Next Pro",
|
|
16
|
+
template: "%s | Create Next Pro",
|
|
17
|
+
},
|
|
18
|
+
description: "A Bun-first Next.js template for create-next-pro-cli.",
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
export function generateStaticParams() {
|
|
22
|
+
return routing.locales.map((locale) => ({ locale }));
|
|
23
|
+
}
|
|
9
24
|
|
|
10
25
|
export default async function LocaleLayout({
|
|
11
26
|
children,
|
|
@@ -15,16 +30,25 @@ export default async function LocaleLayout({
|
|
|
15
30
|
params: Promise<{ locale: string }>;
|
|
16
31
|
}) {
|
|
17
32
|
const { locale } = await params;
|
|
18
|
-
|
|
19
|
-
|
|
33
|
+
if (!hasLocale(routing.locales, locale)) {
|
|
34
|
+
notFound();
|
|
35
|
+
}
|
|
20
36
|
|
|
37
|
+
setRequestLocale(locale);
|
|
38
|
+
const messages = getMessages(locale);
|
|
21
39
|
return (
|
|
22
|
-
<html lang={locale}>
|
|
40
|
+
<html lang={locale} className="light" suppressHydrationWarning>
|
|
23
41
|
<body>
|
|
24
|
-
<NextIntlClientProvider>
|
|
25
|
-
|
|
26
|
-
<GlobalMain>{children}</GlobalMain>
|
|
42
|
+
<NextIntlClientProvider locale={locale} messages={messages}>
|
|
43
|
+
{children}
|
|
27
44
|
</NextIntlClientProvider>
|
|
45
|
+
<Script
|
|
46
|
+
id="theme-initializer"
|
|
47
|
+
strategy="beforeInteractive"
|
|
48
|
+
dangerouslySetInnerHTML={{
|
|
49
|
+
__html: `try{var t=localStorage.getItem("theme");var d=t?t==="dark":window.matchMedia("(prefers-color-scheme: dark)").matches;document.documentElement.classList.toggle("dark",d);document.documentElement.classList.toggle("light",!d);}catch{document.documentElement.classList.add("light");}`,
|
|
50
|
+
}}
|
|
51
|
+
/>
|
|
28
52
|
</body>
|
|
29
53
|
</html>
|
|
30
54
|
);
|
|
@@ -1,14 +1,5 @@
|
|
|
1
|
-
// app/[locale]/dashboard/loading.tsx
|
|
2
|
-
|
|
3
1
|
import LoadingUI from "@/ui/_global/Loading";
|
|
4
2
|
|
|
5
3
|
export default function Loading() {
|
|
6
4
|
return <LoadingUI />;
|
|
7
5
|
}
|
|
8
|
-
// This component is used to show a loading state while the dashboard is being prepared
|
|
9
|
-
// You can customize it with a spinner, skeletons, or any loading UI you prefer
|
|
10
|
-
// It will be displayed when the dashboard is loading, for example during data fetching or component rendering
|
|
11
|
-
// This is useful for providing feedback to users that something is happening in the background
|
|
12
|
-
// You can also use this to implement a more complex loading state with animations or placeholders
|
|
13
|
-
// Make sure to keep it lightweight to avoid blocking the main thread
|
|
14
|
-
// This component is part of the Next.js app directory structure and will be automatically used by Next.js
|
|
@@ -1,22 +1,13 @@
|
|
|
1
|
-
|
|
1
|
+
import { getTranslations } from "next-intl/server";
|
|
2
2
|
import { Link } from "@/lib/i18n/navigation";
|
|
3
3
|
|
|
4
|
-
export default function NotFound() {
|
|
4
|
+
export default async function NotFound() {
|
|
5
|
+
const t = await getTranslations("_global_ui.not_found");
|
|
5
6
|
return (
|
|
6
7
|
<div>
|
|
7
|
-
<h2>
|
|
8
|
-
<p>
|
|
9
|
-
<Link href="/">
|
|
8
|
+
<h2>{t("title")}</h2>
|
|
9
|
+
<p>{t("description")}</p>
|
|
10
|
+
<Link href="/">{t("home")}</Link>
|
|
10
11
|
</div>
|
|
11
12
|
);
|
|
12
13
|
}
|
|
13
|
-
// This page is used to handle 404 errors in the application
|
|
14
|
-
// You can customize this page to display a user-friendly error message
|
|
15
|
-
// or redirect to a different page if needed
|
|
16
|
-
// This is part of the Next.js app directory structure and will be automatically used by Next.js
|
|
17
|
-
// when a requested page is not found
|
|
18
|
-
// Make sure to handle 404 errors gracefully to improve user experience
|
|
19
|
-
// You can also log errors or send them to an error tracking service
|
|
20
|
-
// This component can be styled with CSS or Tailwind CSS to match your application's design
|
|
21
|
-
// You can also add additional links or actions for the user to take, such as searching or navigating to other parts of the site
|
|
22
|
-
// This component is lightweight and does not block the main thread
|
|
@@ -1,6 +1,15 @@
|
|
|
1
1
|
import React from "react";
|
|
2
2
|
import HomePage from "@/app/[locale]/(public)/_home/page";
|
|
3
|
+
import GlobalHeader from "@/ui/_global/GlobalHeader";
|
|
4
|
+
import GlobalMain from "@/ui/_global/GlobalMain";
|
|
3
5
|
|
|
4
6
|
export default async function FallbackPage() {
|
|
5
|
-
return
|
|
7
|
+
return (
|
|
8
|
+
<>
|
|
9
|
+
<GlobalHeader hasSessionInitial={false} />
|
|
10
|
+
<GlobalMain>
|
|
11
|
+
<HomePage />
|
|
12
|
+
</GlobalMain>
|
|
13
|
+
</>
|
|
14
|
+
);
|
|
6
15
|
}
|