create-lumen 1.1.4 → 1.2.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.
Files changed (217) hide show
  1. package/README.md +41 -34
  2. package/package.json +5 -1
  3. package/src/configure.js +6 -2
  4. package/src/css.js +71 -24
  5. package/src/dependencies.js +15 -6
  6. package/src/injector.js +116 -24
  7. package/src/main.js +3 -1
  8. package/src/readme.js +64 -22
  9. package/templates/architectures/component-based/src/App.jsx +6 -3
  10. package/templates/architectures/component-based/src/App.tsx +6 -3
  11. package/templates/architectures/component-based/src/components/common/Button.jsx +5 -2
  12. package/templates/architectures/component-based/src/components/common/Button.tsx +5 -2
  13. package/templates/architectures/component-based/src/hooks/useApp.js +10 -0
  14. package/templates/architectures/component-based/src/hooks/useApp.ts +10 -0
  15. package/templates/architectures/component-based/src/layouts/MainLayout.jsx +12 -4
  16. package/templates/architectures/component-based/src/layouts/MainLayout.tsx +12 -4
  17. package/templates/architectures/component-based/src/pages/Home/Home.jsx +6 -1
  18. package/templates/architectures/component-based/src/pages/Home/Home.tsx +6 -1
  19. package/templates/architectures/component-based/src/providers/AppProvider.jsx +20 -0
  20. package/templates/architectures/component-based/src/providers/AppProvider.tsx +24 -0
  21. package/templates/architectures/component-based/src/providers/appcontext.js +3 -0
  22. package/templates/architectures/component-based/src/{context/app-context.ts → providers/appcontext.ts} +1 -3
  23. package/templates/architectures/{feature-based → component-based}/src/types/index.js +7 -0
  24. package/templates/architectures/{feature-based → component-based}/src/types/index.ts +5 -0
  25. package/templates/architectures/feature-based/main.jsx +1 -1
  26. package/templates/architectures/feature-based/main.tsx +1 -1
  27. package/templates/architectures/feature-based/scripts/create-feature.mjs +2 -2
  28. package/templates/architectures/feature-based/src/app/App.jsx +15 -4
  29. package/templates/architectures/feature-based/src/app/App.tsx +15 -4
  30. package/templates/architectures/feature-based/src/app/contexts/themecontext.js +3 -0
  31. package/templates/architectures/feature-based/src/app/contexts/themecontext.ts +8 -0
  32. package/templates/architectures/feature-based/src/app/hooks/useTheme.js +10 -0
  33. package/templates/architectures/feature-based/src/app/hooks/useTheme.ts +10 -0
  34. package/templates/architectures/feature-based/src/app/providers/ThemeProvider.jsx +18 -1
  35. package/templates/architectures/feature-based/src/app/providers/ThemeProvider.tsx +19 -2
  36. package/templates/architectures/feature-based/src/features/home/pages/HomePage.jsx +18 -4
  37. package/templates/architectures/feature-based/src/features/home/pages/HomePage.tsx +18 -4
  38. package/templates/architectures/feature-based/src/shared/components/ui/Button.jsx +31 -0
  39. package/templates/architectures/feature-based/src/shared/components/ui/Button.tsx +36 -0
  40. package/templates/architectures/feature-based/src/shared/layouts/.gitkeep +0 -0
  41. package/templates/architectures/feature-based/src/shared/stores/.gitkeep +0 -0
  42. package/templates/architectures/feature-based/src/shared/styles/.gitkeep +0 -0
  43. package/templates/architectures/feature-based/src/shared/types/index.js +20 -0
  44. package/templates/architectures/feature-based/src/shared/types/index.ts +16 -0
  45. package/templates/conditional/axios/component-based/src/config/axios.config.js +7 -0
  46. package/templates/conditional/axios/component-based/src/config/axios.config.ts +7 -0
  47. package/templates/conditional/axios/component-based/src/services/axios.client.js +24 -0
  48. package/templates/conditional/axios/component-based/src/services/axios.client.ts +24 -0
  49. package/templates/conditional/axios/component-based/src/services/user.service.js +33 -0
  50. package/templates/conditional/axios/component-based/src/services/user.service.ts +29 -0
  51. package/templates/conditional/axios/feature-based/src/features/home/services/user.service.js +33 -0
  52. package/templates/conditional/axios/feature-based/src/features/home/services/user.service.ts +29 -0
  53. package/templates/conditional/axios/feature-based/src/shared/lib/axios/api.client.js +24 -0
  54. package/templates/conditional/axios/feature-based/src/shared/lib/axios/api.client.ts +24 -0
  55. package/templates/conditional/axios/feature-based/src/shared/lib/axios/api.config.js +7 -0
  56. package/templates/conditional/axios/feature-based/src/shared/lib/axios/api.config.ts +7 -0
  57. package/templates/conditional/axios/feature-based/src/shared/lib/axios/index.js +1 -0
  58. package/templates/conditional/axios/feature-based/src/shared/lib/axios/index.ts +1 -0
  59. package/templates/conditional/fetch/component-based/src/config/api.config.js +7 -0
  60. package/templates/conditional/fetch/component-based/src/config/api.config.ts +7 -0
  61. package/templates/conditional/fetch/component-based/src/services/api.client.js +51 -0
  62. package/templates/conditional/fetch/component-based/src/services/api.client.ts +55 -0
  63. package/templates/conditional/fetch/component-based/src/services/user.service.js +33 -0
  64. package/templates/conditional/fetch/component-based/src/services/user.service.ts +29 -0
  65. package/templates/conditional/fetch/feature-based/src/features/home/services/user.service.js +33 -0
  66. package/templates/conditional/fetch/feature-based/src/features/home/services/user.service.ts +29 -0
  67. package/templates/conditional/fetch/feature-based/src/shared/api/api.client.js +51 -0
  68. package/templates/conditional/fetch/feature-based/src/shared/api/api.client.ts +55 -0
  69. package/templates/conditional/fetch/feature-based/src/shared/api/api.config.js +7 -0
  70. package/templates/conditional/fetch/feature-based/src/shared/api/api.config.ts +7 -0
  71. package/templates/conditional/fetch/feature-based/src/shared/api/index.js +1 -0
  72. package/templates/conditional/fetch/feature-based/src/shared/api/index.ts +1 -0
  73. package/templates/conditional/icons/huge/component-based/bootstrap/src/pages/Home/Home.jsx +20 -0
  74. package/templates/conditional/icons/huge/component-based/bootstrap/src/pages/Home/Home.tsx +20 -0
  75. package/templates/conditional/icons/huge/component-based/src/pages/Home/Home.jsx +24 -8
  76. package/templates/conditional/icons/huge/component-based/src/pages/Home/Home.tsx +24 -8
  77. package/templates/conditional/icons/huge/component-based/tailwind/src/pages/Home/Home.jsx +20 -0
  78. package/templates/conditional/icons/huge/component-based/tailwind/src/pages/Home/Home.tsx +20 -0
  79. package/templates/conditional/icons/huge/feature-based/bootstrap/src/features/home/pages/HomePage.jsx +20 -0
  80. package/templates/conditional/icons/huge/feature-based/bootstrap/src/features/home/pages/HomePage.tsx +20 -0
  81. package/templates/conditional/icons/huge/feature-based/src/features/home/pages/HomePage.jsx +25 -9
  82. package/templates/conditional/icons/huge/feature-based/src/features/home/pages/HomePage.tsx +25 -9
  83. package/templates/conditional/icons/huge/feature-based/tailwind/src/features/home/pages/HomePage.jsx +20 -0
  84. package/templates/conditional/icons/huge/feature-based/tailwind/src/features/home/pages/HomePage.tsx +20 -0
  85. package/templates/conditional/icons/lucide/component-based/bootstrap/src/pages/Home/Home.jsx +19 -0
  86. package/templates/conditional/icons/lucide/component-based/bootstrap/src/pages/Home/Home.tsx +19 -0
  87. package/templates/conditional/icons/lucide/component-based/src/pages/Home/Home.jsx +24 -8
  88. package/templates/conditional/icons/lucide/component-based/src/pages/Home/Home.tsx +24 -8
  89. package/templates/conditional/icons/lucide/component-based/tailwind/src/pages/Home/Home.jsx +19 -0
  90. package/templates/conditional/icons/lucide/component-based/tailwind/src/pages/Home/Home.tsx +19 -0
  91. package/templates/conditional/icons/lucide/feature-based/bootstrap/src/features/home/pages/HomePage.jsx +19 -0
  92. package/templates/conditional/icons/lucide/feature-based/bootstrap/src/features/home/pages/HomePage.tsx +19 -0
  93. package/templates/conditional/icons/lucide/feature-based/src/features/home/pages/HomePage.jsx +25 -9
  94. package/templates/conditional/icons/lucide/feature-based/src/features/home/pages/HomePage.tsx +25 -9
  95. package/templates/conditional/icons/lucide/feature-based/tailwind/src/features/home/pages/HomePage.jsx +19 -0
  96. package/templates/conditional/icons/lucide/feature-based/tailwind/src/features/home/pages/HomePage.tsx +19 -0
  97. package/templates/conditional/router/component-based/bootstrap/src/layouts/MainLayout.jsx +17 -0
  98. package/templates/conditional/router/component-based/bootstrap/src/layouts/MainLayout.tsx +17 -0
  99. package/templates/conditional/router/component-based/src/App.jsx +4 -4
  100. package/templates/conditional/router/component-based/src/App.tsx +4 -4
  101. package/templates/conditional/router/component-based/src/layouts/MainLayout.jsx +39 -0
  102. package/templates/conditional/router/component-based/src/layouts/MainLayout.tsx +39 -0
  103. package/templates/conditional/router/component-based/src/router/guards/AuthGuard.jsx +8 -0
  104. package/templates/conditional/router/component-based/src/router/guards/AuthGuard.tsx +14 -0
  105. package/templates/conditional/router/component-based/src/router/guards/GuestGuard.jsx +8 -0
  106. package/templates/conditional/router/component-based/src/router/guards/GuestGuard.tsx +14 -0
  107. package/templates/conditional/router/component-based/src/router/index.jsx +44 -0
  108. package/templates/conditional/router/component-based/src/router/index.tsx +44 -0
  109. package/templates/conditional/router/component-based/tailwind/src/layouts/MainLayout.jsx +17 -0
  110. package/templates/conditional/router/component-based/tailwind/src/layouts/MainLayout.tsx +17 -0
  111. package/templates/conditional/router/feature-based/bootstrap/src/shared/layouts/RootLayout.jsx +9 -0
  112. package/templates/conditional/router/feature-based/bootstrap/src/shared/layouts/RootLayout.tsx +9 -0
  113. package/templates/conditional/router/feature-based/src/app/App.jsx +6 -1
  114. package/templates/conditional/router/feature-based/src/app/App.tsx +6 -1
  115. package/templates/conditional/router/feature-based/src/app/router/guards/AuthGuard.jsx +8 -0
  116. package/templates/conditional/router/feature-based/src/app/router/guards/AuthGuard.tsx +14 -0
  117. package/templates/conditional/router/feature-based/src/app/router/guards/RoleGuard.jsx +8 -0
  118. package/templates/conditional/router/feature-based/src/app/router/guards/RoleGuard.tsx +15 -0
  119. package/templates/conditional/router/feature-based/src/app/router/index.jsx +16 -0
  120. package/templates/conditional/router/feature-based/src/app/router/index.tsx +16 -0
  121. package/templates/conditional/router/feature-based/src/app/router/routes/auth.routes.jsx +18 -0
  122. package/templates/conditional/router/feature-based/src/app/router/routes/auth.routes.tsx +18 -0
  123. package/templates/conditional/router/feature-based/src/app/router/routes/home.routes.jsx +8 -0
  124. package/templates/conditional/router/feature-based/src/app/router/routes/home.routes.tsx +8 -0
  125. package/templates/conditional/router/feature-based/src/shared/layouts/RootLayout.jsx +17 -0
  126. package/templates/conditional/router/feature-based/src/shared/layouts/RootLayout.tsx +17 -0
  127. package/templates/conditional/router/feature-based/tailwind/src/shared/layouts/RootLayout.jsx +9 -0
  128. package/templates/conditional/router/feature-based/tailwind/src/shared/layouts/RootLayout.tsx +9 -0
  129. package/templates/conditional/state/redux/feature-based/src/app/providers/StoreProvider.jsx +1 -1
  130. package/templates/conditional/state/redux/feature-based/src/app/providers/StoreProvider.tsx +1 -1
  131. package/templates/css/bootstrap/src/themes.css +14 -0
  132. package/templates/css/component-styles/bootstrap/component-based/src/components/common/Button.jsx +17 -0
  133. package/templates/css/component-styles/bootstrap/component-based/src/components/common/Button.tsx +22 -0
  134. package/templates/css/component-styles/bootstrap/component-based/src/layouts/MainLayout.jsx +15 -0
  135. package/templates/css/component-styles/bootstrap/component-based/src/layouts/MainLayout.tsx +19 -0
  136. package/templates/css/component-styles/bootstrap/component-based/src/pages/Home/Home.jsx +13 -0
  137. package/templates/css/component-styles/bootstrap/component-based/src/pages/Home/Home.tsx +13 -0
  138. package/templates/css/component-styles/bootstrap/feature-based/src/app/App.jsx +9 -0
  139. package/templates/css/component-styles/bootstrap/feature-based/src/app/App.tsx +9 -0
  140. package/templates/css/component-styles/bootstrap/feature-based/src/features/home/pages/HomePage.jsx +13 -0
  141. package/templates/css/component-styles/bootstrap/feature-based/src/features/home/pages/HomePage.tsx +13 -0
  142. package/templates/css/component-styles/bootstrap/feature-based/src/shared/components/ui/Button.jsx +17 -0
  143. package/templates/css/component-styles/bootstrap/feature-based/src/shared/components/ui/Button.tsx +22 -0
  144. package/templates/{architectures/feature-based/src/components/ui → css/component-styles/tailwind/component-based/src/components/common}/Button.jsx +1 -1
  145. package/templates/{architectures/feature-based/src/components/ui → css/component-styles/tailwind/component-based/src/components/common}/Button.tsx +1 -1
  146. package/templates/css/component-styles/tailwind/component-based/src/layouts/MainLayout.jsx +15 -0
  147. package/templates/css/component-styles/tailwind/component-based/src/layouts/MainLayout.tsx +19 -0
  148. package/templates/css/component-styles/tailwind/component-based/src/pages/Home/Home.jsx +13 -0
  149. package/templates/css/component-styles/tailwind/component-based/src/pages/Home/Home.tsx +13 -0
  150. package/templates/css/component-styles/tailwind/feature-based/src/app/App.jsx +9 -0
  151. package/templates/css/component-styles/tailwind/feature-based/src/app/App.tsx +9 -0
  152. package/templates/css/component-styles/tailwind/feature-based/src/features/home/pages/HomePage.jsx +13 -0
  153. package/templates/css/component-styles/tailwind/feature-based/src/features/home/pages/HomePage.tsx +13 -0
  154. package/templates/css/component-styles/tailwind/feature-based/src/shared/components/ui/Button.jsx +21 -0
  155. package/templates/css/component-styles/tailwind/feature-based/src/shared/components/ui/Button.tsx +26 -0
  156. package/templates/css/none/src/{index.css → main.css} +2 -0
  157. package/templates/css/none/src/themes.css +19 -0
  158. package/templates/css/tailwind/src/themes.css +9 -0
  159. package/templates/architectures/component-based/src/config/constants.js +0 -1
  160. package/templates/architectures/component-based/src/config/constants.ts +0 -1
  161. package/templates/architectures/component-based/src/config/routes.js +0 -7
  162. package/templates/architectures/component-based/src/config/routes.ts +0 -7
  163. package/templates/architectures/component-based/src/context/AppContext.jsx +0 -12
  164. package/templates/architectures/component-based/src/context/AppContext.tsx +0 -18
  165. package/templates/architectures/component-based/src/context/app-context.js +0 -5
  166. package/templates/architectures/component-based/src/hooks/index.js +0 -1
  167. package/templates/architectures/component-based/src/hooks/index.ts +0 -1
  168. package/templates/architectures/component-based/src/layouts/index.js +0 -1
  169. package/templates/architectures/component-based/src/layouts/index.ts +0 -1
  170. package/templates/architectures/component-based/src/styles/globals.css +0 -7
  171. package/templates/architectures/component-based/src/utils/index.js +0 -1
  172. package/templates/architectures/component-based/src/utils/index.ts +0 -1
  173. package/templates/architectures/feature-based/src/config/constants.js +0 -1
  174. package/templates/architectures/feature-based/src/config/constants.ts +0 -1
  175. package/templates/architectures/feature-based/src/hooks/index.js +0 -1
  176. package/templates/architectures/feature-based/src/hooks/index.ts +0 -1
  177. package/templates/architectures/feature-based/src/utils/index.js +0 -1
  178. package/templates/architectures/feature-based/src/utils/index.ts +0 -1
  179. package/templates/conditional/axios/component-based/src/services/axios.jsx +0 -19
  180. package/templates/conditional/axios/component-based/src/services/axios.ts +0 -19
  181. package/templates/conditional/axios/component-based/src/services/index.js +0 -1
  182. package/templates/conditional/axios/component-based/src/services/index.ts +0 -1
  183. package/templates/conditional/axios/feature-based/src/lib/axios.jsx +0 -19
  184. package/templates/conditional/axios/feature-based/src/lib/axios.ts +0 -19
  185. package/templates/conditional/axios/feature-based/src/lib/index.js +0 -1
  186. package/templates/conditional/axios/feature-based/src/lib/index.ts +0 -1
  187. package/templates/conditional/fetch/component-based/src/services/api.jsx +0 -27
  188. package/templates/conditional/fetch/component-based/src/services/api.ts +0 -27
  189. package/templates/conditional/fetch/component-based/src/services/index.js +0 -1
  190. package/templates/conditional/fetch/component-based/src/services/index.ts +0 -1
  191. package/templates/conditional/fetch/feature-based/src/lib/api.jsx +0 -27
  192. package/templates/conditional/fetch/feature-based/src/lib/api.ts +0 -27
  193. package/templates/conditional/fetch/feature-based/src/lib/index.js +0 -1
  194. package/templates/conditional/fetch/feature-based/src/lib/index.ts +0 -1
  195. package/templates/conditional/router/component-based/src/routes/index.jsx +0 -12
  196. package/templates/conditional/router/component-based/src/routes/index.tsx +0 -12
  197. package/templates/conditional/router/feature-based/src/app/router.jsx +0 -13
  198. package/templates/conditional/router/feature-based/src/app/router.tsx +0 -13
  199. package/templates/css/tailwind/src/index.css +0 -1
  200. /package/templates/architectures/component-based/src/{components/layout → config}/.gitkeep +0 -0
  201. /package/templates/architectures/{feature-based/src/features/home/interfaces → component-based/src/providers}/.gitkeep +0 -0
  202. /package/templates/architectures/{feature-based/src/lib → component-based/src/styles}/.gitkeep +0 -0
  203. /package/templates/architectures/feature-based/src/{stores → features/home/types}/.gitkeep +0 -0
  204. /package/templates/architectures/feature-based/src/{components → shared/components}/ui/index.js +0 -0
  205. /package/templates/architectures/feature-based/src/{components → shared/components}/ui/index.ts +0 -0
  206. /package/templates/architectures/feature-based/src/{hooks → shared/hooks}/useLocalStorage.jsx +0 -0
  207. /package/templates/architectures/feature-based/src/{hooks → shared/hooks}/useLocalStorage.ts +0 -0
  208. /package/templates/architectures/feature-based/src/{utils → shared/utils}/cn.jsx +0 -0
  209. /package/templates/architectures/feature-based/src/{utils → shared/utils}/cn.ts +0 -0
  210. /package/templates/conditional/state/redux/component-based/src/{context → providers}/StoreProvider.jsx +0 -0
  211. /package/templates/conditional/state/redux/component-based/src/{context → providers}/StoreProvider.tsx +0 -0
  212. /package/templates/conditional/state/redux/feature-based/src/{stores → shared/stores}/hooks.js +0 -0
  213. /package/templates/conditional/state/redux/feature-based/src/{stores → shared/stores}/hooks.ts +0 -0
  214. /package/templates/conditional/state/redux/feature-based/src/{stores → shared/stores}/index.js +0 -0
  215. /package/templates/conditional/state/redux/feature-based/src/{stores → shared/stores}/index.ts +0 -0
  216. /package/templates/css/bootstrap/src/{index.css → globals.css} +0 -0
  217. /package/templates/{architectures/feature-based/src/styles → css/tailwind/src}/globals.css +0 -0
@@ -0,0 +1,24 @@
1
+ import axios from "axios";
2
+ import { axiosConfig } from "@/config/axios.config";
3
+
4
+ const api = axios.create(axiosConfig);
5
+
6
+ api.interceptors.request.use((config) => {
7
+ const token = localStorage.getItem("access_token");
8
+ if (token) {
9
+ config.headers.Authorization = `Bearer ${token}`;
10
+ }
11
+ return config;
12
+ });
13
+
14
+ api.interceptors.response.use(
15
+ (response) => response,
16
+ (error) => {
17
+ if (error.response?.status === 401) {
18
+ localStorage.removeItem("access_token");
19
+ }
20
+ return Promise.reject(error);
21
+ },
22
+ );
23
+
24
+ export default api;
@@ -0,0 +1,24 @@
1
+ import axios from "axios";
2
+ import { axiosConfig } from "@/config/axios.config";
3
+
4
+ const api = axios.create(axiosConfig);
5
+
6
+ api.interceptors.request.use((config) => {
7
+ const token = localStorage.getItem("access_token");
8
+ if (token) {
9
+ config.headers.Authorization = `Bearer ${token}`;
10
+ }
11
+ return config;
12
+ });
13
+
14
+ api.interceptors.response.use(
15
+ (response) => response,
16
+ (error) => {
17
+ if (error.response?.status === 401) {
18
+ localStorage.removeItem("access_token");
19
+ }
20
+ return Promise.reject(error);
21
+ },
22
+ );
23
+
24
+ export default api;
@@ -0,0 +1,33 @@
1
+ /**
2
+ * @typedef {import("@/types").ApiResponse} ApiResponse
3
+ * @typedef {import("@/types").CreateUserPayload} CreateUserPayload
4
+ * @typedef {import("@/types").User} User
5
+ */
6
+ import api from "@/services/axios.client";
7
+
8
+ export const userService = {
9
+ async getAll() {
10
+ const { data } = await api.get("/users");
11
+ return data;
12
+ },
13
+
14
+ async getById(id) {
15
+ const { data } = await api.get(`/users/${id}`);
16
+ return data;
17
+ },
18
+
19
+ async create(payload) {
20
+ const { data } = await api.post("/users", payload);
21
+ return data;
22
+ },
23
+
24
+ async update(id, payload) {
25
+ const { data } = await api.put(`/users/${id}`, payload);
26
+ return data;
27
+ },
28
+
29
+ async remove(id) {
30
+ const { data } = await api.delete(`/users/${id}`);
31
+ return data;
32
+ },
33
+ };
@@ -0,0 +1,29 @@
1
+ import api from "@/services/axios.client";
2
+ import type { ApiResponse, CreateUserPayload, User } from "@/types";
3
+
4
+ export const userService = {
5
+ async getAll(): Promise<ApiResponse<User[]>> {
6
+ const { data } = await api.get<ApiResponse<User[]>>("/users");
7
+ return data;
8
+ },
9
+
10
+ async getById(id: string): Promise<ApiResponse<User>> {
11
+ const { data } = await api.get<ApiResponse<User>>(`/users/${id}`);
12
+ return data;
13
+ },
14
+
15
+ async create(payload: CreateUserPayload): Promise<ApiResponse<User>> {
16
+ const { data } = await api.post<ApiResponse<User>>("/users", payload);
17
+ return data;
18
+ },
19
+
20
+ async update(id: string, payload: CreateUserPayload): Promise<ApiResponse<User>> {
21
+ const { data } = await api.put<ApiResponse<User>>(`/users/${id}`, payload);
22
+ return data;
23
+ },
24
+
25
+ async remove(id: string): Promise<ApiResponse<null>> {
26
+ const { data } = await api.delete<ApiResponse<null>>(`/users/${id}`);
27
+ return data;
28
+ },
29
+ };
@@ -0,0 +1,33 @@
1
+ /**
2
+ * @typedef {import("@/shared/types").ApiResponse} ApiResponse
3
+ * @typedef {import("@/shared/types").CreateUserPayload} CreateUserPayload
4
+ * @typedef {import("@/shared/types").User} User
5
+ */
6
+ import { api } from "@/shared/lib/axios";
7
+
8
+ export const userService = {
9
+ async getAll() {
10
+ const { data } = await api.get("/users");
11
+ return data;
12
+ },
13
+
14
+ async getById(id) {
15
+ const { data } = await api.get(`/users/${id}`);
16
+ return data;
17
+ },
18
+
19
+ async create(payload) {
20
+ const { data } = await api.post("/users", payload);
21
+ return data;
22
+ },
23
+
24
+ async update(id, payload) {
25
+ const { data } = await api.put(`/users/${id}`, payload);
26
+ return data;
27
+ },
28
+
29
+ async remove(id) {
30
+ const { data } = await api.delete(`/users/${id}`);
31
+ return data;
32
+ },
33
+ };
@@ -0,0 +1,29 @@
1
+ import { api } from "@/shared/lib/axios";
2
+ import type { ApiResponse, CreateUserPayload, User } from "@/shared/types";
3
+
4
+ export const userService = {
5
+ async getAll(): Promise<ApiResponse<User[]>> {
6
+ const { data } = await api.get<ApiResponse<User[]>>("/users");
7
+ return data;
8
+ },
9
+
10
+ async getById(id: string): Promise<ApiResponse<User>> {
11
+ const { data } = await api.get<ApiResponse<User>>(`/users/${id}`);
12
+ return data;
13
+ },
14
+
15
+ async create(payload: CreateUserPayload): Promise<ApiResponse<User>> {
16
+ const { data } = await api.post<ApiResponse<User>>("/users", payload);
17
+ return data;
18
+ },
19
+
20
+ async update(id: string, payload: CreateUserPayload): Promise<ApiResponse<User>> {
21
+ const { data } = await api.put<ApiResponse<User>>(`/users/${id}`, payload);
22
+ return data;
23
+ },
24
+
25
+ async remove(id: string): Promise<ApiResponse<null>> {
26
+ const { data } = await api.delete<ApiResponse<null>>(`/users/${id}`);
27
+ return data;
28
+ },
29
+ };
@@ -0,0 +1,24 @@
1
+ import axios from "axios";
2
+ import { axiosConfig } from "./api.config";
3
+
4
+ const api = axios.create(axiosConfig);
5
+
6
+ api.interceptors.request.use((config) => {
7
+ const token = localStorage.getItem("access_token");
8
+ if (token) {
9
+ config.headers.Authorization = `Bearer ${token}`;
10
+ }
11
+ return config;
12
+ });
13
+
14
+ api.interceptors.response.use(
15
+ (response) => response,
16
+ (error) => {
17
+ if (error.response?.status === 401) {
18
+ localStorage.removeItem("access_token");
19
+ }
20
+ return Promise.reject(error);
21
+ },
22
+ );
23
+
24
+ export default api;
@@ -0,0 +1,24 @@
1
+ import axios from "axios";
2
+ import { axiosConfig } from "./api.config";
3
+
4
+ const api = axios.create(axiosConfig);
5
+
6
+ api.interceptors.request.use((config) => {
7
+ const token = localStorage.getItem("access_token");
8
+ if (token) {
9
+ config.headers.Authorization = `Bearer ${token}`;
10
+ }
11
+ return config;
12
+ });
13
+
14
+ api.interceptors.response.use(
15
+ (response) => response,
16
+ (error) => {
17
+ if (error.response?.status === 401) {
18
+ localStorage.removeItem("access_token");
19
+ }
20
+ return Promise.reject(error);
21
+ },
22
+ );
23
+
24
+ export default api;
@@ -0,0 +1,7 @@
1
+ export const axiosConfig = {
2
+ baseURL: import.meta.env.VITE_API_URL || "http://localhost:3000",
3
+ timeout: 10000,
4
+ headers: {
5
+ "Content-Type": "application/json",
6
+ },
7
+ };
@@ -0,0 +1,7 @@
1
+ export const axiosConfig = {
2
+ baseURL: import.meta.env.VITE_API_URL || "http://localhost:3000",
3
+ timeout: 10000,
4
+ headers: {
5
+ "Content-Type": "application/json",
6
+ },
7
+ };
@@ -0,0 +1 @@
1
+ export { default as api } from "./api.client";
@@ -0,0 +1 @@
1
+ export { default as api } from "./api.client";
@@ -0,0 +1,7 @@
1
+ export const apiConfig = {
2
+ baseURL: import.meta.env.VITE_API_URL || "http://localhost:3000",
3
+ timeout: 10000,
4
+ headers: {
5
+ "Content-Type": "application/json",
6
+ },
7
+ };
@@ -0,0 +1,7 @@
1
+ export const apiConfig = {
2
+ baseURL: import.meta.env.VITE_API_URL || "http://localhost:3000",
3
+ timeout: 10000,
4
+ headers: {
5
+ "Content-Type": "application/json",
6
+ },
7
+ };
@@ -0,0 +1,51 @@
1
+ import { apiConfig } from "@/config/api.config";
2
+
3
+ async function request(endpoint, options = {}) {
4
+ const token = localStorage.getItem("access_token");
5
+
6
+ const headers = {
7
+ "Content-Type": "application/json",
8
+ ...options.headers,
9
+ };
10
+
11
+ if (token) {
12
+ headers["Authorization"] = `Bearer ${token}`;
13
+ }
14
+
15
+ const response = await fetch(`${apiConfig.baseURL}${endpoint}`, {
16
+ ...options,
17
+ headers,
18
+ });
19
+
20
+ if (response.status === 401) {
21
+ localStorage.removeItem("access_token");
22
+ }
23
+
24
+ if (!response.ok) {
25
+ throw new Error(`HTTP error! status: ${response.status}`);
26
+ }
27
+
28
+ const data = await response.json();
29
+
30
+ return { data };
31
+ }
32
+
33
+ const api = {
34
+ get(endpoint) {
35
+ return request(endpoint);
36
+ },
37
+
38
+ post(endpoint, body) {
39
+ return request(endpoint, { method: "POST", body: JSON.stringify(body) });
40
+ },
41
+
42
+ put(endpoint, body) {
43
+ return request(endpoint, { method: "PUT", body: JSON.stringify(body) });
44
+ },
45
+
46
+ delete(endpoint) {
47
+ return request(endpoint, { method: "DELETE" });
48
+ },
49
+ };
50
+
51
+ export default api;
@@ -0,0 +1,55 @@
1
+ import { apiConfig } from "@/config/api.config";
2
+
3
+ type FetchOptions = Omit<RequestInit, "headers"> & {
4
+ headers?: Record<string, string>;
5
+ };
6
+
7
+ async function request<T>(endpoint: string, options: FetchOptions = {}): Promise<{ data: T }> {
8
+ const token = localStorage.getItem("access_token");
9
+
10
+ const headers: Record<string, string> = {
11
+ "Content-Type": "application/json",
12
+ ...options.headers,
13
+ };
14
+
15
+ if (token) {
16
+ headers["Authorization"] = `Bearer ${token}`;
17
+ }
18
+
19
+ const response = await fetch(`${apiConfig.baseURL}${endpoint}`, {
20
+ ...options,
21
+ headers,
22
+ });
23
+
24
+ if (response.status === 401) {
25
+ localStorage.removeItem("access_token");
26
+ }
27
+
28
+ if (!response.ok) {
29
+ throw new Error(`HTTP error! status: ${response.status}`);
30
+ }
31
+
32
+ const data = (await response.json()) as T;
33
+
34
+ return { data };
35
+ }
36
+
37
+ const api = {
38
+ get<T>(endpoint: string): Promise<{ data: T }> {
39
+ return request<T>(endpoint);
40
+ },
41
+
42
+ post<T>(endpoint: string, body?: unknown): Promise<{ data: T }> {
43
+ return request<T>(endpoint, { method: "POST", body: JSON.stringify(body) });
44
+ },
45
+
46
+ put<T>(endpoint: string, body?: unknown): Promise<{ data: T }> {
47
+ return request<T>(endpoint, { method: "PUT", body: JSON.stringify(body) });
48
+ },
49
+
50
+ delete<T>(endpoint: string): Promise<{ data: T }> {
51
+ return request<T>(endpoint, { method: "DELETE" });
52
+ },
53
+ };
54
+
55
+ export default api;
@@ -0,0 +1,33 @@
1
+ /**
2
+ * @typedef {import("@/types").ApiResponse} ApiResponse
3
+ * @typedef {import("@/types").CreateUserPayload} CreateUserPayload
4
+ * @typedef {import("@/types").User} User
5
+ */
6
+ import api from "@/services/api.client";
7
+
8
+ export const userService = {
9
+ async getAll() {
10
+ const { data } = await api.get("/users");
11
+ return data;
12
+ },
13
+
14
+ async getById(id) {
15
+ const { data } = await api.get(`/users/${id}`);
16
+ return data;
17
+ },
18
+
19
+ async create(payload) {
20
+ const { data } = await api.post("/users", payload);
21
+ return data;
22
+ },
23
+
24
+ async update(id, payload) {
25
+ const { data } = await api.put(`/users/${id}`, payload);
26
+ return data;
27
+ },
28
+
29
+ async remove(id) {
30
+ const { data } = await api.delete(`/users/${id}`);
31
+ return data;
32
+ },
33
+ };
@@ -0,0 +1,29 @@
1
+ import api from "@/services/api.client";
2
+ import type { ApiResponse, CreateUserPayload, User } from "@/types";
3
+
4
+ export const userService = {
5
+ async getAll(): Promise<ApiResponse<User[]>> {
6
+ const { data } = await api.get<ApiResponse<User[]>>("/users");
7
+ return data;
8
+ },
9
+
10
+ async getById(id: string): Promise<ApiResponse<User>> {
11
+ const { data } = await api.get<ApiResponse<User>>(`/users/${id}`);
12
+ return data;
13
+ },
14
+
15
+ async create(payload: CreateUserPayload): Promise<ApiResponse<User>> {
16
+ const { data } = await api.post<ApiResponse<User>>("/users", payload);
17
+ return data;
18
+ },
19
+
20
+ async update(id: string, payload: CreateUserPayload): Promise<ApiResponse<User>> {
21
+ const { data } = await api.put<ApiResponse<User>>(`/users/${id}`, payload);
22
+ return data;
23
+ },
24
+
25
+ async remove(id: string): Promise<ApiResponse<null>> {
26
+ const { data } = await api.delete<ApiResponse<null>>(`/users/${id}`);
27
+ return data;
28
+ },
29
+ };
@@ -0,0 +1,33 @@
1
+ /**
2
+ * @typedef {import("@/shared/types").ApiResponse} ApiResponse
3
+ * @typedef {import("@/shared/types").CreateUserPayload} CreateUserPayload
4
+ * @typedef {import("@/shared/types").User} User
5
+ */
6
+ import { api } from "@/shared/api";
7
+
8
+ export const userService = {
9
+ async getAll() {
10
+ const { data } = await api.get("/users");
11
+ return data;
12
+ },
13
+
14
+ async getById(id) {
15
+ const { data } = await api.get(`/users/${id}`);
16
+ return data;
17
+ },
18
+
19
+ async create(payload) {
20
+ const { data } = await api.post("/users", payload);
21
+ return data;
22
+ },
23
+
24
+ async update(id, payload) {
25
+ const { data } = await api.put(`/users/${id}`, payload);
26
+ return data;
27
+ },
28
+
29
+ async remove(id) {
30
+ const { data } = await api.delete(`/users/${id}`);
31
+ return data;
32
+ },
33
+ };
@@ -0,0 +1,29 @@
1
+ import { api } from "@/shared/api";
2
+ import type { ApiResponse, CreateUserPayload, User } from "@/shared/types";
3
+
4
+ export const userService = {
5
+ async getAll(): Promise<ApiResponse<User[]>> {
6
+ const { data } = await api.get<ApiResponse<User[]>>("/users");
7
+ return data;
8
+ },
9
+
10
+ async getById(id: string): Promise<ApiResponse<User>> {
11
+ const { data } = await api.get<ApiResponse<User>>(`/users/${id}`);
12
+ return data;
13
+ },
14
+
15
+ async create(payload: CreateUserPayload): Promise<ApiResponse<User>> {
16
+ const { data } = await api.post<ApiResponse<User>>("/users", payload);
17
+ return data;
18
+ },
19
+
20
+ async update(id: string, payload: CreateUserPayload): Promise<ApiResponse<User>> {
21
+ const { data } = await api.put<ApiResponse<User>>(`/users/${id}`, payload);
22
+ return data;
23
+ },
24
+
25
+ async remove(id: string): Promise<ApiResponse<null>> {
26
+ const { data } = await api.delete<ApiResponse<null>>(`/users/${id}`);
27
+ return data;
28
+ },
29
+ };
@@ -0,0 +1,51 @@
1
+ import { apiConfig } from "./api.config";
2
+
3
+ async function request(endpoint, options = {}) {
4
+ const token = localStorage.getItem("access_token");
5
+
6
+ const headers = {
7
+ "Content-Type": "application/json",
8
+ ...options.headers,
9
+ };
10
+
11
+ if (token) {
12
+ headers["Authorization"] = `Bearer ${token}`;
13
+ }
14
+
15
+ const response = await fetch(`${apiConfig.baseURL}${endpoint}`, {
16
+ ...options,
17
+ headers,
18
+ });
19
+
20
+ if (response.status === 401) {
21
+ localStorage.removeItem("access_token");
22
+ }
23
+
24
+ if (!response.ok) {
25
+ throw new Error(`HTTP error! status: ${response.status}`);
26
+ }
27
+
28
+ const data = await response.json();
29
+
30
+ return { data };
31
+ }
32
+
33
+ const api = {
34
+ get(endpoint) {
35
+ return request(endpoint);
36
+ },
37
+
38
+ post(endpoint, body) {
39
+ return request(endpoint, { method: "POST", body: JSON.stringify(body) });
40
+ },
41
+
42
+ put(endpoint, body) {
43
+ return request(endpoint, { method: "PUT", body: JSON.stringify(body) });
44
+ },
45
+
46
+ delete(endpoint) {
47
+ return request(endpoint, { method: "DELETE" });
48
+ },
49
+ };
50
+
51
+ export default api;
@@ -0,0 +1,55 @@
1
+ import { apiConfig } from "./api.config";
2
+
3
+ type FetchOptions = Omit<RequestInit, "headers"> & {
4
+ headers?: Record<string, string>;
5
+ };
6
+
7
+ async function request<T>(endpoint: string, options: FetchOptions = {}): Promise<{ data: T }> {
8
+ const token = localStorage.getItem("access_token");
9
+
10
+ const headers: Record<string, string> = {
11
+ "Content-Type": "application/json",
12
+ ...options.headers,
13
+ };
14
+
15
+ if (token) {
16
+ headers["Authorization"] = `Bearer ${token}`;
17
+ }
18
+
19
+ const response = await fetch(`${apiConfig.baseURL}${endpoint}`, {
20
+ ...options,
21
+ headers,
22
+ });
23
+
24
+ if (response.status === 401) {
25
+ localStorage.removeItem("access_token");
26
+ }
27
+
28
+ if (!response.ok) {
29
+ throw new Error(`HTTP error! status: ${response.status}`);
30
+ }
31
+
32
+ const data = (await response.json()) as T;
33
+
34
+ return { data };
35
+ }
36
+
37
+ const api = {
38
+ get<T>(endpoint: string): Promise<{ data: T }> {
39
+ return request<T>(endpoint);
40
+ },
41
+
42
+ post<T>(endpoint: string, body?: unknown): Promise<{ data: T }> {
43
+ return request<T>(endpoint, { method: "POST", body: JSON.stringify(body) });
44
+ },
45
+
46
+ put<T>(endpoint: string, body?: unknown): Promise<{ data: T }> {
47
+ return request<T>(endpoint, { method: "PUT", body: JSON.stringify(body) });
48
+ },
49
+
50
+ delete<T>(endpoint: string): Promise<{ data: T }> {
51
+ return request<T>(endpoint, { method: "DELETE" });
52
+ },
53
+ };
54
+
55
+ export default api;
@@ -0,0 +1,7 @@
1
+ export const apiConfig = {
2
+ baseURL: import.meta.env.VITE_API_URL || "http://localhost:3000",
3
+ timeout: 10000,
4
+ headers: {
5
+ "Content-Type": "application/json",
6
+ },
7
+ };
@@ -0,0 +1,7 @@
1
+ export const apiConfig = {
2
+ baseURL: import.meta.env.VITE_API_URL || "http://localhost:3000",
3
+ timeout: 10000,
4
+ headers: {
5
+ "Content-Type": "application/json",
6
+ },
7
+ };
@@ -0,0 +1 @@
1
+ export { default as api } from "./api.client";
@@ -0,0 +1 @@
1
+ export { default as api } from "./api.client";
@@ -0,0 +1,20 @@
1
+ import { HugeiconsIcon } from "@hugeicons/react";
2
+ import { Sun01Icon, Moon01Icon, Github01Icon } from "@hugeicons/core-free-icons";
3
+ import { Button } from "@/components/common";
4
+
5
+ export function HomePage() {
6
+ return (
7
+ <div className="text-center">
8
+ <div className="d-flex justify-content-center gap-3 mb-4">
9
+ <HugeiconsIcon icon={Sun01Icon} style={{ width: 32, height: 32 }} className="text-warning" />
10
+ <HugeiconsIcon icon={Moon01Icon} style={{ width: 32, height: 32 }} className="text-primary" />
11
+ <HugeiconsIcon icon={Github01Icon} style={{ width: 32, height: 32 }} className="text-dark" />
12
+ </div>
13
+ <h1 className="h1 fw-bold text-dark mb-4">Welcome to Lumen</h1>
14
+ <p className="text-muted mb-5">
15
+ Your React + Vite project is ready. Start building!
16
+ </p>
17
+ <Button>Get Started</Button>
18
+ </div>
19
+ );
20
+ }