create-tigra 1.1.0 → 2.0.1

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.
Files changed (243) hide show
  1. package/LICENSE +21 -21
  2. package/README.md +80 -87
  3. package/bin/create-tigra.js +259 -308
  4. package/package.json +49 -41
  5. package/template/_claude/QUICK_REFERENCE.md +193 -0
  6. package/template/_claude/README.md +53 -0
  7. package/template/_claude/commands/create-client.md +881 -0
  8. package/template/_claude/commands/create-server.md +383 -0
  9. package/template/_claude/rules/client/01-project-structure.md +133 -0
  10. package/template/_claude/rules/client/02-components-and-types.md +146 -0
  11. package/template/_claude/rules/client/03-data-and-state.md +156 -0
  12. package/template/_claude/rules/client/04-design-system.md +185 -0
  13. package/template/_claude/rules/client/05-security.md +55 -0
  14. package/template/_claude/rules/client/06-ux-checklist.md +81 -0
  15. package/template/_claude/rules/client/core.md +42 -0
  16. package/template/_claude/rules/global/core.md +77 -0
  17. package/template/_claude/rules/server/core.md +50 -0
  18. package/template/_claude/rules/server/database.md +124 -0
  19. package/template/_claude/rules/server/project-conventions.md +150 -0
  20. package/template/_claude/rules/server/response-handling.md +144 -0
  21. package/template/client/.env.example +5 -0
  22. package/template/client/README.md +36 -0
  23. package/template/client/components.json +23 -0
  24. package/template/client/eslint.config.mjs +18 -0
  25. package/template/client/next.config.ts +34 -0
  26. package/template/client/package.json +44 -0
  27. package/template/client/postcss.config.mjs +7 -0
  28. package/template/client/src/app/(auth)/layout.tsx +18 -0
  29. package/template/client/src/app/(auth)/login/page.tsx +13 -0
  30. package/template/client/src/app/(auth)/register/page.tsx +13 -0
  31. package/template/client/src/app/(main)/dashboard/page.tsx +22 -0
  32. package/template/client/src/app/(main)/layout.tsx +11 -0
  33. package/template/client/src/app/error.tsx +27 -0
  34. package/template/client/src/app/favicon.ico +0 -0
  35. package/template/client/src/app/globals.css +145 -0
  36. package/template/client/src/app/layout.tsx +36 -0
  37. package/template/client/src/app/loading.tsx +11 -0
  38. package/template/client/src/app/not-found.tsx +23 -0
  39. package/template/client/src/app/page.tsx +45 -0
  40. package/template/client/src/app/providers.tsx +43 -0
  41. package/template/client/src/components/common/ConfirmDialog.tsx +56 -0
  42. package/template/client/src/components/common/EmptyState.tsx +31 -0
  43. package/template/client/src/components/common/LoadingSpinner.tsx +30 -0
  44. package/template/client/src/components/common/Pagination.tsx +55 -0
  45. package/template/client/src/components/layout/Footer.tsx +17 -0
  46. package/template/client/src/components/layout/Header.tsx +173 -0
  47. package/template/client/src/components/layout/MainLayout.tsx +18 -0
  48. package/template/client/src/components/ui/alert-dialog.tsx +196 -0
  49. package/template/client/src/components/ui/badge.tsx +48 -0
  50. package/template/client/src/components/ui/button.tsx +64 -0
  51. package/template/client/src/components/ui/card.tsx +92 -0
  52. package/template/client/src/components/ui/input.tsx +21 -0
  53. package/template/client/src/components/ui/label.tsx +24 -0
  54. package/template/client/src/components/ui/select.tsx +190 -0
  55. package/template/client/src/components/ui/skeleton.tsx +13 -0
  56. package/template/client/src/components/ui/table.tsx +116 -0
  57. package/template/client/src/features/auth/components/AuthInitializer.tsx +55 -0
  58. package/template/client/src/features/auth/components/LoginForm.tsx +107 -0
  59. package/template/client/src/features/auth/components/RegisterForm.tsx +178 -0
  60. package/template/client/src/features/auth/hooks/useAuth.ts +84 -0
  61. package/template/client/src/features/auth/services/auth.service.ts +52 -0
  62. package/template/client/src/features/auth/store/authSlice.ts +38 -0
  63. package/template/client/src/features/auth/types/auth.types.ts +32 -0
  64. package/template/client/src/hooks/useDebounce.ts +14 -0
  65. package/template/client/src/hooks/useLocalStorage.ts +55 -0
  66. package/template/client/src/hooks/useMediaQuery.ts +27 -0
  67. package/template/client/src/lib/api/api.types.ts +34 -0
  68. package/template/client/src/lib/api/axios.config.ts +98 -0
  69. package/template/client/src/lib/constants/api-endpoints.ts +18 -0
  70. package/template/client/src/lib/constants/app.constants.ts +12 -0
  71. package/template/client/src/lib/constants/routes.ts +9 -0
  72. package/template/client/src/lib/utils/error.ts +32 -0
  73. package/template/client/src/lib/utils/format.ts +37 -0
  74. package/template/client/src/lib/utils/security.ts +34 -0
  75. package/template/client/src/lib/utils.ts +6 -0
  76. package/template/client/src/middleware.ts +57 -0
  77. package/template/client/src/store/hooks.ts +7 -0
  78. package/template/client/src/store/index.ts +12 -0
  79. package/template/client/src/types/index.ts +3 -0
  80. package/template/client/tsconfig.json +34 -0
  81. package/template/gitignore +34 -0
  82. package/template/server/.dockerignore +66 -0
  83. package/template/server/.env.example +96 -69
  84. package/template/server/.env.production.example +90 -0
  85. package/template/server/Dockerfile +94 -0
  86. package/template/server/docker-compose.yml +82 -111
  87. package/template/server/docs/logging.md +62 -0
  88. package/template/server/eslint.config.mjs +17 -0
  89. package/template/server/package.json +68 -81
  90. package/template/server/phpmyadmin-config.php +26 -0
  91. package/template/server/postman_collection.json +666 -0
  92. package/template/server/prisma/schema.prisma +77 -93
  93. package/template/server/prisma/seed.ts +46 -142
  94. package/template/server/scripts/flush-redis.ts +41 -0
  95. package/template/server/src/app.ts +243 -71
  96. package/template/server/src/config/env.ts +67 -94
  97. package/template/server/src/libs/auth.ts +88 -0
  98. package/template/server/src/libs/cleanup.ts +35 -0
  99. package/template/server/src/libs/cookies.ts +46 -0
  100. package/template/server/src/libs/logger.ts +33 -60
  101. package/template/server/src/libs/monitoring.ts +205 -0
  102. package/template/server/src/libs/password.ts +38 -0
  103. package/template/server/src/libs/prisma.ts +68 -0
  104. package/template/server/src/libs/redis.ts +60 -79
  105. package/template/server/src/libs/requestLogger.ts +66 -0
  106. package/template/server/src/libs/storage/file-storage.service.ts +211 -0
  107. package/template/server/src/libs/storage/file-validator.ts +97 -0
  108. package/template/server/src/libs/storage/filename-sanitizer.ts +71 -0
  109. package/template/server/src/libs/storage/image-optimizer.service.ts +144 -0
  110. package/template/server/src/modules/auth/__tests__/auth.service.test.ts +365 -0
  111. package/template/server/src/modules/auth/auth.controller.ts +90 -141
  112. package/template/server/src/modules/auth/auth.repo.ts +120 -218
  113. package/template/server/src/modules/auth/auth.routes.ts +96 -83
  114. package/template/server/src/modules/auth/auth.schemas.ts +35 -137
  115. package/template/server/src/modules/auth/auth.service.ts +286 -329
  116. package/template/server/src/modules/auth/session.repo.ts +110 -0
  117. package/template/server/src/modules/users/users.controller.ts +120 -0
  118. package/template/server/src/modules/users/users.repo.ts +77 -0
  119. package/template/server/src/modules/users/users.routes.ts +89 -0
  120. package/template/server/src/modules/users/users.schemas.ts +21 -0
  121. package/template/server/src/modules/users/users.service.ts +169 -0
  122. package/template/server/src/server.ts +58 -139
  123. package/template/server/src/shared/errors/AppError.ts +21 -0
  124. package/template/server/src/shared/errors/errors.ts +43 -0
  125. package/template/server/src/shared/responses/paginatedResponse.ts +38 -0
  126. package/template/server/src/shared/responses/successResponse.ts +17 -0
  127. package/template/server/src/shared/schemas/pagination.schema.ts +12 -0
  128. package/template/server/src/shared/types/index.ts +26 -0
  129. package/template/server/src/test/setup.ts +74 -38
  130. package/template/server/tsconfig.json +27 -89
  131. package/template/server/uploads/avatars/.gitkeep +1 -0
  132. package/template/server/vitest.config.ts +43 -98
  133. package/template/.agent/rules/client/01-project-structure.md +0 -326
  134. package/template/.agent/rules/client/02-component-patterns.md +0 -249
  135. package/template/.agent/rules/client/03-typescript-rules.md +0 -226
  136. package/template/.agent/rules/client/04-state-management.md +0 -474
  137. package/template/.agent/rules/client/05-api-integration.md +0 -129
  138. package/template/.agent/rules/client/06-forms-validation.md +0 -129
  139. package/template/.agent/rules/client/07-common-patterns.md +0 -150
  140. package/template/.agent/rules/client/08-color-system.md +0 -93
  141. package/template/.agent/rules/client/09-security-rules.md +0 -97
  142. package/template/.agent/rules/client/10-testing-strategy.md +0 -370
  143. package/template/.agent/rules/global/ai-edit-safety.md +0 -38
  144. package/template/.agent/rules/server/01-db-and-migrations.md +0 -242
  145. package/template/.agent/rules/server/02-general-rules.md +0 -111
  146. package/template/.agent/rules/server/03-migrations.md +0 -20
  147. package/template/.agent/rules/server/04-pagination.md +0 -130
  148. package/template/.agent/rules/server/05-project-conventions.md +0 -71
  149. package/template/.agent/rules/server/06-response-handling.md +0 -173
  150. package/template/.agent/rules/server/07-testing-strategy.md +0 -506
  151. package/template/.agent/rules/server/08-observability.md +0 -180
  152. package/template/.agent/rules/server/10-background-jobs-v2.md +0 -185
  153. package/template/.agent/rules/server/11-rate-limiting-v2.md +0 -210
  154. package/template/.agent/rules/server/12-performance-optimization.md +0 -567
  155. package/template/.claude/rules/client-01-project-structure.md +0 -327
  156. package/template/.claude/rules/client-02-component-patterns.md +0 -250
  157. package/template/.claude/rules/client-03-typescript-rules.md +0 -227
  158. package/template/.claude/rules/client-04-state-management.md +0 -475
  159. package/template/.claude/rules/client-05-api-integration.md +0 -130
  160. package/template/.claude/rules/client-06-forms-validation.md +0 -130
  161. package/template/.claude/rules/client-07-common-patterns.md +0 -151
  162. package/template/.claude/rules/client-08-color-system.md +0 -94
  163. package/template/.claude/rules/client-09-security-rules.md +0 -98
  164. package/template/.claude/rules/client-10-testing-strategy.md +0 -371
  165. package/template/.claude/rules/global-ai-edit-safety.md +0 -39
  166. package/template/.claude/rules/server-01-db-and-migrations.md +0 -243
  167. package/template/.claude/rules/server-02-general-rules.md +0 -112
  168. package/template/.claude/rules/server-03-migrations.md +0 -21
  169. package/template/.claude/rules/server-04-pagination.md +0 -131
  170. package/template/.claude/rules/server-05-project-conventions.md +0 -72
  171. package/template/.claude/rules/server-06-response-handling.md +0 -174
  172. package/template/.claude/rules/server-07-testing-strategy.md +0 -507
  173. package/template/.claude/rules/server-08-observability.md +0 -181
  174. package/template/.claude/rules/server-10-background-jobs-v2.md +0 -186
  175. package/template/.claude/rules/server-11-rate-limiting-v2.md +0 -211
  176. package/template/.claude/rules/server-12-performance-optimization.md +0 -568
  177. package/template/.cursor/rules/client-01-project-structure.mdc +0 -327
  178. package/template/.cursor/rules/client-02-component-patterns.mdc +0 -250
  179. package/template/.cursor/rules/client-03-typescript-rules.mdc +0 -227
  180. package/template/.cursor/rules/client-04-state-management.mdc +0 -475
  181. package/template/.cursor/rules/client-05-api-integration.mdc +0 -130
  182. package/template/.cursor/rules/client-06-forms-validation.mdc +0 -130
  183. package/template/.cursor/rules/client-07-common-patterns.mdc +0 -151
  184. package/template/.cursor/rules/client-08-color-system.mdc +0 -94
  185. package/template/.cursor/rules/client-09-security-rules.mdc +0 -98
  186. package/template/.cursor/rules/client-10-testing-strategy.mdc +0 -371
  187. package/template/.cursor/rules/global-ai-edit-safety.mdc +0 -39
  188. package/template/.cursor/rules/server-01-db-and-migrations.mdc +0 -243
  189. package/template/.cursor/rules/server-02-general-rules.mdc +0 -112
  190. package/template/.cursor/rules/server-03-migrations.mdc +0 -21
  191. package/template/.cursor/rules/server-04-pagination.mdc +0 -131
  192. package/template/.cursor/rules/server-05-project-conventions.mdc +0 -72
  193. package/template/.cursor/rules/server-06-response-handling.mdc +0 -174
  194. package/template/.cursor/rules/server-07-testing-strategy.mdc +0 -507
  195. package/template/.cursor/rules/server-08-observability.mdc +0 -181
  196. package/template/.cursor/rules/server-09-api-documentation-v2.mdc +0 -169
  197. package/template/.cursor/rules/server-10-background-jobs-v2.mdc +0 -186
  198. package/template/.cursor/rules/server-11-rate-limiting-v2.mdc +0 -211
  199. package/template/.cursor/rules/server-12-performance-optimization.mdc +0 -568
  200. package/template/CLAUDE.md +0 -207
  201. package/template/server/.tsc-aliasrc.json +0 -13
  202. package/template/server/IMPORT_FIX_CHECKLIST.md +0 -98
  203. package/template/server/IMPORT_FIX_COMPLETE.md +0 -89
  204. package/template/server/README.md +0 -183
  205. package/template/server/REMAINING_IMPORT_FIXES.md +0 -150
  206. package/template/server/SECURITY.md +0 -190
  207. package/template/server/Tigra-API.postman_collection.json +0 -733
  208. package/template/server/biome.json +0 -42
  209. package/template/server/scripts/fix-all-imports.ps1 +0 -52
  210. package/template/server/scripts/fix-imports-reference.ps1 +0 -16
  211. package/template/server/scripts/fix-imports.mjs +0 -55
  212. package/template/server/scripts/setup-env.js +0 -50
  213. package/template/server/scripts/wait-for-db.js +0 -60
  214. package/template/server/src/hooks/request-timing.hook.ts +0 -26
  215. package/template/server/src/libs/auth/authenticate.middleware.ts +0 -22
  216. package/template/server/src/libs/auth/rbac.middleware.test.ts +0 -134
  217. package/template/server/src/libs/auth/rbac.middleware.ts +0 -147
  218. package/template/server/src/libs/db.ts +0 -76
  219. package/template/server/src/libs/error-handler.ts +0 -89
  220. package/template/server/src/libs/queue.ts +0 -79
  221. package/template/server/src/modules/admin/admin.controller.ts +0 -122
  222. package/template/server/src/modules/admin/admin.routes.ts +0 -62
  223. package/template/server/src/modules/admin/admin.schemas.ts +0 -35
  224. package/template/server/src/modules/admin/admin.service.ts +0 -167
  225. package/template/server/src/modules/auth/auth.integration.test.ts +0 -150
  226. package/template/server/src/modules/auth/auth.service.test.ts +0 -119
  227. package/template/server/src/modules/auth/auth.types.ts +0 -97
  228. package/template/server/src/modules/resources/resources.controller.ts +0 -218
  229. package/template/server/src/modules/resources/resources.repo.ts +0 -253
  230. package/template/server/src/modules/resources/resources.routes.ts +0 -116
  231. package/template/server/src/modules/resources/resources.schemas.ts +0 -146
  232. package/template/server/src/modules/resources/resources.service.ts +0 -218
  233. package/template/server/src/modules/resources/resources.types.ts +0 -73
  234. package/template/server/src/plugins/rate-limit.plugin.ts +0 -21
  235. package/template/server/src/plugins/security.plugin.ts +0 -21
  236. package/template/server/src/routes/health.routes.ts +0 -31
  237. package/template/server/src/types/fastify.d.ts +0 -36
  238. package/template/server/src/utils/errors.ts +0 -108
  239. package/template/server/src/utils/pagination.ts +0 -120
  240. package/template/server/src/utils/response.ts +0 -110
  241. package/template/server/src/workers/file.worker.ts +0 -106
  242. package/template/server/tsconfig.build.json +0 -30
  243. package/template/server/tsconfig.test.json +0 -22
@@ -0,0 +1,156 @@
1
+ > **SCOPE**: These rules apply specifically to the **client** directory (Next.js App Router).
2
+
3
+ # Data, State & API Integration
4
+
5
+ ## State Decision Matrix
6
+
7
+ | State Type | Tool | When |
8
+ |---|---|---|
9
+ | Server data (initial page load) | Server Components | SEO-critical, page-level data |
10
+ | Server data (client-triggered) | React Query | User actions, real-time updates, mutations |
11
+ | Global client state | Redux | Auth user + init/logout state — **nothing else** |
12
+ | Local UI state | `useState` / `useReducer` | Modals, hover, form inputs |
13
+ | URL-shareable state | `useSearchParams` | Filters, pagination, search query |
14
+
15
+ ### Anti-patterns
16
+
17
+ - **No server state in Redux.** Use Server Components or React Query.
18
+ - **No UI state in Redux** (modals, loading). Use local state.
19
+ - **Prefer Server Component fetch** over client-side `useQuery` when the data is available at page level.
20
+
21
+ ---
22
+
23
+ ## React Query Config
24
+
25
+ Defaults in `app/providers.tsx`:
26
+
27
+ ```typescript
28
+ staleTime: 5 * 60 * 1000 // 5 min
29
+ gcTime: 10 * 60 * 1000 // 10 min
30
+ refetchOnWindowFocus: false
31
+ retry: 1
32
+ ```
33
+
34
+ ### Query Key Factory Pattern
35
+
36
+ ```typescript
37
+ export const itemKeys = {
38
+ all: ['items'] as const,
39
+ lists: () => [...itemKeys.all, 'list'] as const,
40
+ list: (filters: ItemFilters) => [...itemKeys.lists(), filters] as const,
41
+ details: () => [...itemKeys.all, 'detail'] as const,
42
+ detail: (id: string) => [...itemKeys.details(), id] as const,
43
+ };
44
+ ```
45
+
46
+ ### Mutations
47
+
48
+ On success: invalidate related queries, show toast, navigate if needed.
49
+ On error: `toast.error(getErrorMessage(error))`.
50
+
51
+ ---
52
+
53
+ ## Redux
54
+
55
+ **Scope**: Auth only. Single slice: `authSlice` with actions: `setUser`, `setInitialized`, `setLoggingOut`, `logout`.
56
+
57
+ Typed hooks in `store/hooks.ts`: `useAppDispatch`, `useAppSelector`.
58
+
59
+ State shape:
60
+ ```typescript
61
+ { user: IUser | null; isAuthenticated: boolean; isInitializing: boolean; isLoggingOut: boolean }
62
+ ```
63
+
64
+ **Not persisted to localStorage** — auth state is hydrated on page load by `AuthInitializer` calling `getMe()`. Tokens are stored in httpOnly cookies (not accessible from JS).
65
+
66
+ ---
67
+
68
+ ## Axios Config
69
+
70
+ `lib/api/axios.config.ts` — singleton `apiClient`:
71
+
72
+ - **Base URL**: `process.env.NEXT_PUBLIC_API_BASE_URL` (fallback `http://localhost:8000/api/v1`)
73
+ - **Timeout**: 30s
74
+ - **`withCredentials: true`**: Sends httpOnly cookies automatically with every request.
75
+ - **No request interceptor** — cookies handle auth, no `Authorization` header needed.
76
+ - **Response interceptor**: On 401, attempts token refresh via `/auth/refresh` (cookie sent automatically). Queues concurrent 401s to avoid multiple refresh attempts. If refresh fails, dispatches `logout()` and redirects to `/login`.
77
+
78
+ ---
79
+
80
+ ## Service Pattern
81
+
82
+ Services are **classes**, singleton-exported, using `apiClient` and `API_ENDPOINTS`.
83
+
84
+ ```typescript
85
+ class ItemService {
86
+ async getItems(params?: ItemFilters & PaginationParams): Promise<PaginatedData<Item>>
87
+ async getItem(id: string): Promise<Item>
88
+ async createItem(data: CreateItemRequest): Promise<Item>
89
+ async updateItem(id: string, data: UpdateItemRequest): Promise<Item>
90
+ async deleteItem(id: string): Promise<void>
91
+ }
92
+ export const itemService = new ItemService();
93
+ ```
94
+
95
+ Auth service methods: `register`, `login`, `logout`, `refreshToken`, `getMe`, `verifyEmail`, `requestPasswordReset`, `resetPassword`.
96
+
97
+ ---
98
+
99
+ ## Error Handling
100
+
101
+ ```typescript
102
+ // lib/utils/error.ts
103
+ export const getErrorMessage = (error: unknown): string => {
104
+ // Checks: axios error → ApiError shape → network error → generic Error → fallback string
105
+ };
106
+ ```
107
+
108
+ **Toast library**: `sonner`. Use `toast.success()`, `toast.error(getErrorMessage(error))`.
109
+
110
+ ---
111
+
112
+ ## Next.js Caching Defaults
113
+
114
+ | Data type | Strategy | Example |
115
+ |---|---|---|
116
+ | General content | `next: { revalidate: 60 }` | Items list |
117
+ | User-specific | `cache: 'no-store'` | User profile |
118
+ | Static lookups | `cache: 'force-cache'` | Categories, settings |
119
+
120
+ Use `revalidatePath()` / `revalidateTag()` in Server Actions after mutations.
121
+
122
+ ---
123
+
124
+ ## Forms
125
+
126
+ **Approach**: Hybrid — React Hook Form + Zod for client-side validation, Server Action for submission.
127
+
128
+ ### Password Schema Requirements
129
+
130
+ ```typescript
131
+ z.string()
132
+ .min(8, 'Min 8 characters')
133
+ .regex(/[A-Z]/, 'Must contain uppercase')
134
+ .regex(/[a-z]/, 'Must contain lowercase')
135
+ .regex(/[0-9]/, 'Must contain number')
136
+ ```
137
+
138
+ ### File Upload Validation
139
+
140
+ - Allowed types: `image/jpeg`, `image/png`, `image/webp`
141
+ - Max size: 5MB
142
+ - Validate extension AND MIME type
143
+
144
+ ### Form Rules
145
+
146
+ - Show field-level errors below the field (red text + red border).
147
+ - Disable submit button during submission.
148
+ - Never clear the form on error — preserve user input.
149
+ - Use `useFormStatus` for pending states in Server Action forms.
150
+
151
+ ---
152
+
153
+ ## Utility Defaults
154
+
155
+ - **Default currency**: `USD` for `formatCurrency`.
156
+ - **Date format**: `Intl.DateTimeFormat('en-US', { year: 'numeric', month: 'long', day: 'numeric' })`.
@@ -0,0 +1,185 @@
1
+ > **SCOPE**: These rules apply specifically to the **client** directory (Next.js App Router).
2
+
3
+ # Design System
4
+
5
+ ## Philosophy: "Neuro-Minimalism"
6
+
7
+ Clean, airy, "expensive" look inspired by Linear, Vercel, Stripe, Arc. Every visual decision reduces cognitive load.
8
+
9
+ ---
10
+
11
+ ## CSS Architecture (Source of Truth)
12
+
13
+ This project uses **Tailwind CSS v4** with **OKLCH color space** and the `@theme inline` directive (not the legacy `tailwind.config.ts`).
14
+
15
+ ```css
16
+ /* app/globals.css */
17
+ @import "tailwindcss";
18
+ @import "tw-animate-css";
19
+ @import "shadcn/tailwind.css";
20
+
21
+ @custom-variant dark (&:is(.dark *));
22
+
23
+ @theme inline {
24
+ --color-background: var(--background);
25
+ --color-foreground: var(--foreground);
26
+ --font-sans: var(--font-geist-sans);
27
+ --font-mono: var(--font-geist-mono);
28
+ /* ... maps all semantic tokens to Tailwind */
29
+ }
30
+
31
+ :root {
32
+ --radius: 0.625rem;
33
+ --background: oklch(1 0 0);
34
+ --foreground: oklch(0.145 0 0);
35
+ --primary: oklch(0.45 0.2 260);
36
+ --primary-foreground: oklch(0.985 0 0);
37
+ --secondary: oklch(0.97 0 0);
38
+ --secondary-foreground: oklch(0.205 0 0);
39
+ --muted: oklch(0.97 0 0);
40
+ --muted-foreground: oklch(0.556 0 0);
41
+ --accent: oklch(0.97 0 0);
42
+ --accent-foreground: oklch(0.205 0 0);
43
+ --destructive: oklch(0.577 0.245 27.325);
44
+ --border: oklch(0.922 0 0);
45
+ --input: oklch(0.922 0 0);
46
+ --ring: oklch(0.45 0.2 260);
47
+ --success: oklch(0.52 0.17 155);
48
+ --success-foreground: oklch(1 0 0);
49
+ --warning: oklch(0.75 0.18 75);
50
+ --warning-foreground: oklch(0.2 0 0);
51
+ --info: oklch(0.55 0.15 240);
52
+ --info-foreground: oklch(1 0 0);
53
+ --chart-1 through --chart-5 /* Data visualization colors */
54
+ --sidebar, --sidebar-foreground, etc. /* Sidebar-specific tokens */
55
+ }
56
+
57
+ .dark {
58
+ --background: oklch(0.145 0 0);
59
+ --foreground: oklch(0.985 0 0);
60
+ /* ... dark mode overrides for all tokens */
61
+ }
62
+ ```
63
+
64
+ **Key differences from Tailwind v3:**
65
+ - No `tailwind.config.ts` — all config is CSS-based via `@theme inline`
66
+ - Colors use **OKLCH** (perceptually uniform) not HSL
67
+ - `@custom-variant dark` replaces `darkMode: 'class'`
68
+ - No `@layer base { :root { } }` — variables defined directly on `:root`
69
+
70
+ ## Color Usage
71
+
72
+ | Token | Purpose | Example use |
73
+ |---|---|---|
74
+ | `primary` | Main CTAs, links, active states | "Get started" button |
75
+ | `secondary` | Secondary actions | Cancel, back |
76
+ | `destructive` | Delete, errors | Delete button, error alert |
77
+ | `success` | Success states | "Action completed" |
78
+ | `warning` | Warnings | "Pending approval" |
79
+ | `info` | Information | "New feature" badge |
80
+ | `muted` | Disabled, placeholders | Disabled input |
81
+ | `accent` | Highlights | "Featured" badge |
82
+ | `card` | Card backgrounds | Content card |
83
+ | `border` | Borders, dividers | Card border |
84
+
85
+ ### Color Rules
86
+
87
+ 1. **Never hardcode**: No `bg-blue-500`, no `bg-[#3b82f6]`, no `style={{ color }}`. Always semantic tokens.
88
+ 2. **Semantic names by purpose**: `bg-destructive` not `bg-red`.
89
+ 3. **Always pair bg + foreground**: `bg-primary text-primary-foreground` for contrast.
90
+ 4. **Single source of truth**: Change colors only in `globals.css` variables.
91
+ 5. **90% monochrome**: 90% of UI uses `background`, `foreground`, `muted`, `border`. Color is the exception.
92
+ 6. **Opacity for hierarchy**: Use `bg-primary/10`, `bg-primary/5` for tinted backgrounds.
93
+
94
+ ---
95
+
96
+ ## Surfaces & Depth
97
+
98
+ - **Border radius**: `rounded-xl` (12px) or `rounded-2xl` (16px) for cards, modals, containers.
99
+ - **Shadows** (layered by elevation):
100
+ - Resting cards: `shadow-sm`
101
+ - Hovered/elevated: `shadow-md` to `shadow-lg`
102
+ - Modals/popovers: `shadow-xl`
103
+ - **Glassmorphism**: Only on sticky headers, floating toolbars, modal backdrops. Never on content cards.
104
+ `backdrop-filter: blur(12px) saturate(1.5); background: oklch(from var(--background) l c h / 0.8);`
105
+ - **No pure black/white**: Use `--background` and `--foreground` tokens (already off-pure).
106
+
107
+ ---
108
+
109
+ ## Typography
110
+
111
+ - **Font**: Inter v4 (variable) or Geist Sans via `next/font`.
112
+ - **Headings**: `text-wrap: balance`, `leading-tight`. H1: `text-3xl`–`text-4xl`, H2: `text-2xl`.
113
+ - **Body**: `text-base`, `leading-relaxed`. Max reading width: `max-w-prose` (~65ch).
114
+ - **Data/numbers**: Always `tabular-nums` for alignment.
115
+ - **Captions/meta**: `text-sm text-muted-foreground`.
116
+
117
+ ---
118
+
119
+ ## Spacing
120
+
121
+ - **Whitespace IS the divider.** Prefer spacing over visible borders/lines.
122
+ - **Section gap = 2x internal gap**: `space-y-16` between sections, `space-y-6` within.
123
+ - **Stick to scale**: `4, 6, 8, 12, 16, 20, 24` from Tailwind. Avoid arbitrary values.
124
+ - **Container**: `container mx-auto px-4 md:px-6 lg:px-8`.
125
+
126
+ ---
127
+
128
+ ## Motion & Interactions
129
+
130
+ Every interactive element MUST have visible `:hover`, `:active`, and `:focus-visible` states.
131
+
132
+ ### Standard Patterns
133
+ ```
134
+ Button: transition-all duration-200 ease-out hover:brightness-110 active:scale-[0.98]
135
+ Card: transition-all duration-300 ease-out hover:shadow-lg hover:-translate-y-0.5
136
+ Link: transition-colors duration-150 hover:text-primary
137
+ ```
138
+
139
+ ### Rules
140
+ - **Transform + opacity only** — never animate layout properties (`width`, `height`, `top`).
141
+ - **Respect `prefers-reduced-motion`**: Use `motion-safe:` / `motion-reduce:` variants.
142
+ - **Motion budget**: Max 2-3 animated elements in viewport at once.
143
+ - **Zero CLS**: Animations must never cause layout shift.
144
+
145
+ ---
146
+
147
+ ## Images
148
+
149
+ - **Format priority**: AVIF > WebP > JPEG (Next.js `<Image>` handles this).
150
+ - **LCP image**: Always add `priority` prop.
151
+ - **Blur placeholder**: Use `placeholder="blur"` with `blurDataURL`.
152
+ - **Always set** explicit `width`/`height` or use `aspect-ratio` to prevent CLS.
153
+
154
+ ---
155
+
156
+ ## Modern CSS Features (Use Where Appropriate)
157
+
158
+ | Feature | Use for |
159
+ |---|---|
160
+ | `@container` | Component-level responsive behavior |
161
+ | CSS Subgrid | Child alignment with parent grid |
162
+ | `dvh` | Full-height layouts (avoids mobile browser bar) |
163
+ | `<dialog>` | Modals (with glassmorphism backdrop) |
164
+ | Popover API | Dropdowns, tooltips |
165
+ | `:has()` | Parent-based styling without JS |
166
+ | `content-visibility: auto` | Long lists/pages performance |
167
+ | `@starting-style` | Entry animations |
168
+
169
+ ---
170
+
171
+ ## Component Visual Patterns
172
+
173
+ - **Cards**: `rounded-xl border border-border/50 bg-card shadow-sm transition-all duration-300 hover:shadow-md hover:-translate-y-0.5`
174
+ - **Empty states**: Centered, muted icon, 2-line text max, one clear CTA.
175
+ - **Loading**: Skeleton loaders matching content shape. Show immediately, no delay.
176
+ - **Modals**: Max `max-w-lg`. Dismissible with Escape + backdrop click. Glassmorphism backdrop.
177
+
178
+ ---
179
+
180
+ ## Dark Mode
181
+
182
+ - Use `next-themes` with `attribute="class"`, `defaultTheme="system"`.
183
+ - Reduce shadow visibility in dark mode (use subtle light borders instead).
184
+ - Consider `brightness-90` on images in dark mode.
185
+ - Add `suppressHydrationWarning` to `<html>` tag.
@@ -0,0 +1,55 @@
1
+ > **SCOPE**: These rules apply specifically to the **client** directory (Next.js App Router).
2
+
3
+ # Security
4
+
5
+ ## Token Storage
6
+
7
+ - **httpOnly cookies** (`access_token` + `refresh_token`) set by the server via `Set-Cookie` headers.
8
+ - Tokens are **never accessible from JavaScript** — no localStorage, no Redux token state.
9
+ - Axios sends cookies automatically via `withCredentials: true`.
10
+ - `AuthInitializer` hydrates user state on page load by calling `getMe()` (cookie sent automatically).
11
+ - On logout: call logout API endpoint (server clears cookies), dispatch `logout()` action, redirect to `/login`.
12
+
13
+ ## Environment Variables
14
+
15
+ - **Never prefix secrets with `NEXT_PUBLIC_`** — only public values (API URL, app name) get the prefix.
16
+ - Server-only secrets (DB URL, JWT secret) have no prefix and are only accessible in Server Components / Server Actions.
17
+ - Validate env with Zod at startup.
18
+
19
+ ## File Upload Validation
20
+
21
+ - Allowed types: `image/jpeg`, `image/png`, `image/webp`
22
+ - Max size: 5MB
23
+ - Validate both MIME type AND file extension.
24
+
25
+ ## Security Headers (`next.config.ts`)
26
+
27
+ ```
28
+ X-Frame-Options: DENY
29
+ X-Content-Type-Options: nosniff
30
+ Referrer-Policy: origin-when-cross-origin
31
+ X-XSS-Protection: 1; mode=block
32
+ ```
33
+
34
+ ## Content Security Policy
35
+
36
+ ```
37
+ default-src 'self';
38
+ script-src 'self' 'unsafe-eval' 'unsafe-inline';
39
+ style-src 'self' 'unsafe-inline';
40
+ img-src 'self' blob: data: https:;
41
+ font-src 'self';
42
+ object-src 'none';
43
+ base-uri 'self';
44
+ form-action 'self';
45
+ frame-ancestors 'none';
46
+ connect-src 'self' ${NEXT_PUBLIC_API_BASE_URL};
47
+ ```
48
+
49
+ ## Rules
50
+
51
+ 1. **Never inject raw HTML** without sanitizing it first (use DOMPurify with allowed tags/attrs).
52
+ 2. **Never log sensitive data** (tokens, passwords, full user objects). Dev-only: log IDs at most.
53
+ 3. **Validate all inputs** with Zod — client-side (UX) AND server-side (security).
54
+ 4. **External links**: Always `target="_blank" rel="noopener noreferrer"`.
55
+ 5. **Sanitize URLs**: Only allow `http:`, `https:`, `mailto:` protocols before rendering as links.
@@ -0,0 +1,81 @@
1
+ > **SCOPE**: These rules apply specifically to the **client** directory (Next.js App Router).
2
+
3
+ # Neuro-UX Checklist
4
+
5
+ ## Cognitive Load — Miller's Law
6
+
7
+ - **Max 5-7 interactive elements** per viewport section. Use progressive disclosure (tabs, accordions, "Show more") for more.
8
+
9
+ ## Gestalt Principles
10
+
11
+ - **Proximity**: Related items close together. Gap between groups = 2x gap within groups.
12
+ - **Grid alignment**: All elements on a strict grid. No floating/misaligned elements.
13
+ - **Similarity**: Same action = same visual style across all pages.
14
+ - **Common region**: Group related controls in a visual container (`bg-muted/50` or subtle border).
15
+
16
+ ## Instant Feedback
17
+
18
+ | User action | Required feedback | Timing |
19
+ |---|---|---|
20
+ | Click button | Press state (`active:scale-[0.98]`) | Instant |
21
+ | Submit form | Loading state on button + disable | Instant |
22
+ | Successful action | Toast notification | <500ms |
23
+ | Failed action | Inline error OR toast | <500ms |
24
+ | Navigate | Skeleton or page transition | Instant |
25
+ | Hover interactive | Color/shadow/scale change | <100ms |
26
+
27
+ - **Optimistic UI**: Update UI immediately before server confirms. Revert on error.
28
+ - **Skeletons over spinners. Always.** Spinners only inside buttons during submission.
29
+
30
+ ## Nielsen's 10 Heuristics
31
+
32
+ 1. **System status**: Show loading, toast on completion, inline validation as user types.
33
+ 2. **Real-world match**: Human language ("Sign in" not "Authenticate"). Locale-formatted dates/currencies.
34
+ 3. **User control**: Every modal dismissible with Escape + backdrop. Undo for destructive actions. Back always works.
35
+ 4. **Consistency**: Same action = same button style, position, label everywhere.
36
+ 5. **Error prevention**: Real-time validation. Disable submit until valid. Type-appropriate inputs. Confirm destructive actions.
37
+ 6. **Recognition > recall**: Visible labels (not placeholder-only). Show recent searches. Visible nav on desktop.
38
+ 7. **Flexibility**: Keyboard shortcuts (Cmd+K). Preserve filters in URL. Bulk actions where appropriate.
39
+ 8. **Minimalist design**: Every element earns its place. Prefer whitespace over separators.
40
+ 9. **Error recovery**: Say what went wrong + how to fix it. Highlight the field. Never clear form on error.
41
+ 10. **Help**: Contextual tooltips on complex features. Dismissible onboarding hints.
42
+
43
+ ## Performance Targets
44
+
45
+ | Metric | Target |
46
+ |---|---|
47
+ | Lighthouse Performance | 98+ |
48
+ | Lighthouse Accessibility | 98+ |
49
+ | LCP | <2.5s |
50
+ | CLS | 0 |
51
+ | INP | <200ms |
52
+
53
+ ## Accessibility
54
+
55
+ - All interactive elements reachable via Tab in logical order.
56
+ - Focus rings: `:focus-visible` only (not `:focus`). Style: `ring-2 ring-primary/50`.
57
+ - Icon-only buttons: must have `aria-label`.
58
+ - One `h1` per page. No skipped heading levels.
59
+ - Dynamic content updates: `aria-live="polite"`.
60
+ - All animations in `motion-safe:` variant.
61
+ - WCAG AA contrast: 4.5:1 for text, 3:1 for large text/UI.
62
+
63
+ ## Microcopy
64
+
65
+ - **Buttons**: Action verbs — "Save changes", "Create item", "Delete account". Never "Submit" or "OK".
66
+ - **Toasts**: Under 10 words. Success: confirm. Error: what happened + what to do.
67
+ - **Empty states**: Explain what this area is for + CTA to fill it. ("No items yet. Create your first one.")
68
+ - **Form errors**: Specific to the field. Below the field. Red text + red border.
69
+
70
+ ## Page Audit Checklist
71
+
72
+ 1. Interactive elements per section ≤ 7?
73
+ 2. All elements on grid?
74
+ 3. Every button/link has hover + active + focus-visible?
75
+ 4. Skeletons for all async content?
76
+ 5. Inline field-level errors on forms?
77
+ 6. Every modal dismissible with Escape?
78
+ 7. Tab through all elements in logical order?
79
+ 8. Text passes WCAG AA contrast?
80
+ 9. All animation in `motion-safe:`?
81
+ 10. LCP image has `priority`?
@@ -0,0 +1,42 @@
1
+ > **SCOPE**: These rules apply specifically to the **client** directory (Next.js App Router).
2
+
3
+ # Client Rules — Core Index
4
+
5
+ **Read only the file relevant to your current task.**
6
+
7
+ | You are doing... | Read this |
8
+ |---|---|
9
+ | Creating files, folders, feature modules | `01-project-structure.md` |
10
+ | Building components, writing types/interfaces | `02-components-and-types.md` |
11
+ | Fetching data, managing state, calling APIs, forms | `03-data-and-state.md` |
12
+ | Choosing colors, styling, typography, spacing, motion | `04-design-system.md` |
13
+ | Auth tokens, env vars, security headers | `05-security.md` |
14
+ | UX psychology, cognitive load, a11y, performance | `06-ux-checklist.md` |
15
+
16
+ ---
17
+
18
+ ## Architecture
19
+
20
+ ```
21
+ Page (Server Component — fetches data)
22
+ → Feature Components (Server or Client)
23
+ → UI (shadcn/ui + Tailwind)
24
+
25
+ State: Server data (SSR) → Server Components
26
+ Server data (client) → React Query
27
+ Global client state → Redux (auth only)
28
+ Local state → useState / useReducer
29
+ URL state → useSearchParams
30
+ ```
31
+
32
+ ---
33
+
34
+ ## Non-negotiable rules
35
+
36
+ 1. **Server Components by default.** Only add `'use client'` when you need hooks, state, or event handlers.
37
+ 2. **Component limits**: Max 250 lines, max 5 props, max 3 JSX nesting levels.
38
+ 3. **No hardcoded colors**: Use Tailwind semantic tokens (`bg-primary`, `text-foreground`). Never hex/rgb.
39
+ 4. **No inline styles**: Tailwind only. Use `cn()` for conditional classes.
40
+ 5. **Import order**: React/Next → third-party → UI → local → hooks → services → types → utils.
41
+ 6. **Forms**: Validate with Zod. Always validate client-side AND server-side.
42
+ 7. **Security**: Never inject raw HTML without sanitization. Never prefix secrets with `NEXT_PUBLIC_`.
@@ -0,0 +1,77 @@
1
+ > **SCOPE**: These rules apply to the **entire workspace** (server + client). Always active.
2
+
3
+ # Global Rules
4
+
5
+ These rules are always in effect regardless of which directory you are working in.
6
+
7
+ ---
8
+
9
+ ## New Project Setup
10
+
11
+ When the user asks to create, scaffold, or start a new server or client project, **always run `/create-server` or `/create-client` first** before writing any code. These commands contain the full scaffolding templates, dependency lists, and boilerplate that match our architecture. Do not attempt to scaffold a project from memory.
12
+
13
+ ---
14
+
15
+ ## Safe Editing
16
+
17
+ 1. **Small, focused changes**: Only modify what's necessary. Don't restructure code unless asked.
18
+ 2. **Preserve signatures**: Don't change existing function signatures, exports, or imports unless explicitly requested.
19
+ 3. **Extend, don't rewrite**: Add to existing modules. Don't gut and rebuild.
20
+ 4. **Protect critical flows**: Never break existing auth, core business flows, or payment logic.
21
+ 5. **No half-done work**: If something is incomplete, add a `// TODO:` with explanation.
22
+ 6. **No noisy logs**: No debug logs in production code. Mark temporary ones with `// TODO: remove debug log`.
23
+ 7. **Call out breaking changes**: If a breaking change is unavoidable, state it clearly in your explanation.
24
+ 8. **Assume production**: Treat this as a real production project. Avoid destructive or experimental changes.
25
+
26
+ ---
27
+
28
+ ## TypeScript
29
+
30
+ - **Strict mode ON** in both client and server. No exceptions.
31
+ - **No `any`** — use `unknown` if the type is truly unknown.
32
+ - **Explicit return types** on all functions.
33
+ - **Always `import type`** for type-only imports.
34
+ - **Validate all inputs with Zod** — client-side for UX, server-side for security.
35
+
36
+ ---
37
+
38
+ ## Git & Branching
39
+
40
+ - **Branch naming**: `feature/<name>`, `fix/<name>`, `chore/<name>`, `hotfix/<name>`.
41
+ - **Commit messages**: Use conventional commits — `feat:`, `fix:`, `chore:`, `refactor:`, `docs:`, `test:`.
42
+ - Keep the subject line under 72 characters.
43
+ - Use imperative mood: "Add search filter" not "Added search filter".
44
+ - **Never commit**: `.env` files, secrets, `node_modules`, build artifacts, OS files (`.DS_Store`, `Thumbs.db`).
45
+ - **One logical change per commit**. Don't mix unrelated changes.
46
+
47
+ ---
48
+
49
+ ## Environment & Configuration
50
+
51
+ - **`.env` files are never committed.** Use `.env.example` as the template with placeholder values.
52
+ - **Adding a new env var**: Add it to `.env.example` with a comment, and document where it's used.
53
+ - **Secrets** (DB URLs, JWT secrets, API keys) must never be prefixed with `NEXT_PUBLIC_` and must never appear in client-side code.
54
+ - **Public values only** (API base URL, app name) get the `NEXT_PUBLIC_` prefix.
55
+
56
+ ---
57
+
58
+ ## Testing
59
+
60
+ - **New features and bug fixes should include tests** unless the change is trivial (copy, config, styling).
61
+ - **Test naming**: `describe('<ModuleName>')` → `it('should <expected behavior>')`.
62
+ - **Tests must be deterministic**: No reliance on real time, network, or random values. Mock external dependencies.
63
+ - **Don't test implementation details** — test behavior and outputs.
64
+
65
+ ---
66
+
67
+ ## Code Review Checklist
68
+
69
+ Before considering work done, verify:
70
+
71
+ - [ ] No `any` types.
72
+ - [ ] No hardcoded values (URLs, colors, magic numbers) — use constants and tokens.
73
+ - [ ] No `console.log` left in code.
74
+ - [ ] No commented-out code without a `// TODO:` explaining why.
75
+ - [ ] Inputs validated with Zod.
76
+ - [ ] Error cases handled (not just the happy path).
77
+ - [ ] Existing tests still pass.
@@ -0,0 +1,50 @@
1
+ > **SCOPE**: These rules apply specifically to the **server** directory (Fastify backend).
2
+
3
+ # Server Rules — Core Index
4
+
5
+ **Do NOT read every rule file upfront.** Use this index to find the right rules for your current task.
6
+
7
+ ---
8
+
9
+ ## When to read which file
10
+
11
+ | You are doing... | Read this |
12
+ |------------------|-----------|
13
+ | Setting up a module, organizing code, understanding the stack | `project-conventions.md` |
14
+ | Creating or modifying a route / controller | `project-conventions.md` + `response-handling.md` |
15
+ | Returning data (success, error, or paginated) | `response-handling.md` |
16
+ | Handling or throwing errors | `response-handling.md` |
17
+ | Writing service or business logic | `project-conventions.md` (Layer Responsibilities) |
18
+ | Changing DB schema, migrations, indexes | `database.md` |
19
+ | Adding or changing API endpoints | `project-conventions.md` (Postman Collection) |
20
+ | Unsure where to start | This file |
21
+
22
+ ---
23
+
24
+ ## Architecture at a glance
25
+
26
+ ```
27
+ Request
28
+ -> Route (Fastify plugin, defines HTTP method + path)
29
+ -> Controller (validates input with Zod, calls service, returns response)
30
+ -> Service (business logic, throws typed errors)
31
+ -> Repository (Prisma queries, returns raw data)
32
+ -> Database
33
+ ```
34
+
35
+ **Three strict boundaries:**
36
+ 1. **Controllers** — parse input, call services, format responses. No business logic. No direct DB access.
37
+ 2. **Services** — all business logic. No Fastify concepts (request, reply). Throw typed `AppError` instances.
38
+ 3. **Repositories** — Prisma queries only. No business logic. No error formatting.
39
+
40
+ ---
41
+
42
+ ## Non-negotiable rules (always apply)
43
+
44
+ 1. **Response format**: All controllers use `successResponse()` / `paginatedResponse()`. No custom shapes.
45
+ 2. **Error handling**: Only throw `AppError` subclasses. Never raw `Error` or strings. Global error handler formats all errors.
46
+ 3. **Validation**: All input validated with Zod schemas before reaching services.
47
+ 4. **Database changes**: Always via Prisma migrations. Never raw DDL.
48
+ 5. **Logging**: Use `logger` from `src/libs/logger`. Never `console.log`.
49
+ 6. **Routes**: All prefixed with `/api/v1`. Registered as Fastify plugins.
50
+ 7. **Postman**: Every new or modified endpoint must be reflected in `postman/collection.json`. Create the collection if it doesn't exist.