create-secra 0.1.11 → 1.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 (97) hide show
  1. package/antd-adapter-template/README.md +24 -0
  2. package/antd-adapter-template/index.html +16 -0
  3. package/antd-adapter-template/package-lock.json +3420 -0
  4. package/antd-adapter-template/package.json +20 -47
  5. package/antd-adapter-template/src/app/App.tsx +7 -0
  6. package/antd-adapter-template/src/app/layouts/AppLayout.tsx +163 -0
  7. package/antd-adapter-template/src/app/router.ts +26 -0
  8. package/antd-adapter-template/src/app/routes/RouteTitleSync.tsx +26 -0
  9. package/antd-adapter-template/src/app/routes/dynamic-routes.ts +52 -0
  10. package/antd-adapter-template/src/app/routes/route-modules.ts +4 -0
  11. package/antd-adapter-template/src/app/routes/static-routes.tsx +110 -0
  12. package/antd-adapter-template/src/app/routes/types.ts +9 -0
  13. package/antd-adapter-template/src/features/auth/api/auth-api.ts +61 -0
  14. package/antd-adapter-template/src/features/auth/auth-store.ts +125 -0
  15. package/antd-adapter-template/src/features/auth/auth-types.ts +29 -0
  16. package/antd-adapter-template/src/features/auth/authorization.ts +46 -0
  17. package/antd-adapter-template/src/features/auth/use-auth.ts +10 -0
  18. package/antd-adapter-template/src/main.tsx +79 -0
  19. package/antd-adapter-template/src/pages/dashboard/DashboardPage.tsx +105 -0
  20. package/antd-adapter-template/src/pages/errors/ForbiddenPage.tsx +36 -0
  21. package/antd-adapter-template/src/pages/errors/NotFoundPage.tsx +36 -0
  22. package/antd-adapter-template/src/pages/home/HomePage.tsx +129 -0
  23. package/antd-adapter-template/src/pages/login/LoginPage.tsx +128 -0
  24. package/antd-adapter-template/src/pages/permission-test/PermissionTestPage.tsx +55 -0
  25. package/antd-adapter-template/src/pages/restricted/RestrictedDemoPage.tsx +17 -0
  26. package/antd-adapter-template/src/shared/kernel/app-kernel.ts +10 -0
  27. package/antd-adapter-template/src/shared/request/client.ts +46 -0
  28. package/antd-adapter-template/src/shared/request/contracts.ts +6 -0
  29. package/antd-adapter-template/src/shared/request/kv-adapter.ts +14 -0
  30. package/antd-adapter-template/src/shared/request/kv-backend.ts +244 -0
  31. package/antd-adapter-template/src/shared/request/ky-browser-stub.ts +6 -0
  32. package/antd-adapter-template/src/shared/request/undici-browser-stub.ts +4 -0
  33. package/antd-adapter-template/src/styles/global.css +185 -0
  34. package/antd-adapter-template/src/vite-env.d.ts +2 -0
  35. package/antd-adapter-template/tsconfig.app.json +10 -13
  36. package/antd-adapter-template/tsconfig.json +7 -2
  37. package/antd-adapter-template/tsconfig.node.json +6 -16
  38. package/antd-adapter-template/vite.config.ts +24 -0
  39. package/bin/index.mjs +29 -5
  40. package/package.json +2 -2
  41. package/template/apps/core/src/main.tsx +34 -13
  42. package/template/package.json +6 -2
  43. package/template/packages/sdk/package.json +3 -0
  44. package/template/packages/sdk/src/request/index.ts +1 -1
  45. package/template/pnpm-lock.yaml +67 -88
  46. package/antd-adapter-template/apps/core/index.html +0 -13
  47. package/antd-adapter-template/apps/core/package.json +0 -18
  48. package/antd-adapter-template/apps/core/public/favicon.ico +0 -1
  49. package/antd-adapter-template/apps/core/public/favicon.svg +0 -1
  50. package/antd-adapter-template/apps/core/public/logo.svg +0 -1
  51. package/antd-adapter-template/apps/core/src/api/auth.ts +0 -49
  52. package/antd-adapter-template/apps/core/src/assets/react.svg +0 -1
  53. package/antd-adapter-template/apps/core/src/components/AntdGlobalProvider.tsx +0 -87
  54. package/antd-adapter-template/apps/core/src/components/AntdRootLayout.tsx +0 -10
  55. package/antd-adapter-template/apps/core/src/components/layout.tsx +0 -387
  56. package/antd-adapter-template/apps/core/src/guards/auth-route-guard.ts +0 -45
  57. package/antd-adapter-template/apps/core/src/main.tsx +0 -65
  58. package/antd-adapter-template/apps/core/src/pages/auth/components/account-login-fields.tsx +0 -60
  59. package/antd-adapter-template/apps/core/src/pages/auth/components/phone-login-fields.tsx +0 -60
  60. package/antd-adapter-template/apps/core/src/pages/auth/login.tsx +0 -169
  61. package/antd-adapter-template/apps/core/src/pages/index.tsx +0 -156
  62. package/antd-adapter-template/apps/core/src/router.ts +0 -42
  63. package/antd-adapter-template/apps/core/src/shims/use-sync-external-store-shim.ts +0 -3
  64. package/antd-adapter-template/apps/core/src/theme/theme.css +0 -48
  65. package/antd-adapter-template/apps/core/src/types/crypto-js.d.ts +0 -5
  66. package/antd-adapter-template/apps/core/src/utils/index.ts +0 -12
  67. package/antd-adapter-template/apps/core/src/utils/md5.ts +0 -6
  68. package/antd-adapter-template/apps/core/tsconfig.app.json +0 -11
  69. package/antd-adapter-template/apps/core/tsconfig.json +0 -13
  70. package/antd-adapter-template/apps/core/tsconfig.node.json +0 -7
  71. package/antd-adapter-template/apps/core/vite.config.ts +0 -118
  72. package/antd-adapter-template/eslint.config.js +0 -23
  73. package/antd-adapter-template/packages/sdk/.swcrc +0 -18
  74. package/antd-adapter-template/packages/sdk/package.json +0 -52
  75. package/antd-adapter-template/packages/sdk/src/build/index.ts +0 -28
  76. package/antd-adapter-template/packages/sdk/src/build/plugins/auto-import.ts +0 -46
  77. package/antd-adapter-template/packages/sdk/src/build/plugins/bundle-analyzer.ts +0 -33
  78. package/antd-adapter-template/packages/sdk/src/build/plugins/remove-console.ts +0 -23
  79. package/antd-adapter-template/packages/sdk/src/build/plugins/unocss.ts +0 -202
  80. package/antd-adapter-template/packages/sdk/src/build/plugins/unplugin-icon.ts +0 -43
  81. package/antd-adapter-template/packages/sdk/src/components/i18n-switch-dropdown.tsx +0 -139
  82. package/antd-adapter-template/packages/sdk/src/components/index.ts +0 -2
  83. package/antd-adapter-template/packages/sdk/src/components/theme-switch-dropdown.tsx +0 -131
  84. package/antd-adapter-template/packages/sdk/src/hooks/auth/core.ts +0 -101
  85. package/antd-adapter-template/packages/sdk/src/hooks/auth/index.ts +0 -139
  86. package/antd-adapter-template/packages/sdk/src/hooks/auth/with-auth.tsx +0 -41
  87. package/antd-adapter-template/packages/sdk/src/hooks/index.ts +0 -1
  88. package/antd-adapter-template/packages/sdk/src/i18n/index.ts +0 -150
  89. package/antd-adapter-template/packages/sdk/src/index.ts +0 -11
  90. package/antd-adapter-template/packages/sdk/src/request/index.ts +0 -436
  91. package/antd-adapter-template/packages/sdk/src/storage/README.md +0 -30
  92. package/antd-adapter-template/packages/sdk/src/storage/index.ts +0 -57
  93. package/antd-adapter-template/packages/sdk/src/styles/reset.css +0 -111
  94. package/antd-adapter-template/packages/sdk/src/theme/index.ts +0 -466
  95. package/antd-adapter-template/packages/sdk/tsconfig.json +0 -16
  96. package/antd-adapter-template/pnpm-workspace.yaml +0 -3
  97. package/antd-adapter-template/turbo.json +0 -17
@@ -0,0 +1,46 @@
1
+ import type { RequestBody, RequestQuery } from "@vlian/request";
2
+ import { RequestClient, adapterRegistry } from "@vlian/request";
3
+ import { createKvAdapter } from "@/shared/request/kv-adapter";
4
+ import type { ApiEnvelope } from "@/shared/request/contracts";
5
+
6
+ const ADAPTER_NAME = "kv";
7
+
8
+ if (!adapterRegistry.has(ADAPTER_NAME)) {
9
+ adapterRegistry.register(ADAPTER_NAME, createKvAdapter);
10
+ }
11
+
12
+ const client = new RequestClient({
13
+ defaultAdapter: ADAPTER_NAME,
14
+ });
15
+
16
+ let initializePromise: Promise<void> | null = null;
17
+
18
+ const ensureInitialized = async () => {
19
+ if (!initializePromise) {
20
+ initializePromise = client.initialize();
21
+ }
22
+
23
+ await initializePromise;
24
+ };
25
+
26
+ export const kvRequestClient = {
27
+ async get<TResponse>(
28
+ url: string,
29
+ query?: RequestQuery,
30
+ ): Promise<ApiEnvelope<TResponse>> {
31
+ await ensureInitialized();
32
+ const response = await client.get<ApiEnvelope<TResponse>>(url, {
33
+ query,
34
+ });
35
+ return response.data;
36
+ },
37
+
38
+ async post<TResponse, TBody = RequestBody>(
39
+ url: string,
40
+ body?: TBody,
41
+ ): Promise<ApiEnvelope<TResponse>> {
42
+ await ensureInitialized();
43
+ const response = await client.post<ApiEnvelope<TResponse>>(url, body as RequestBody);
44
+ return response.data;
45
+ },
46
+ };
@@ -0,0 +1,6 @@
1
+ export interface ApiEnvelope<T> {
2
+ code: number;
3
+ message: string;
4
+ data: T;
5
+ }
6
+
@@ -0,0 +1,14 @@
1
+ import type { RequestAdapter } from "@vlian/request";
2
+ import { handleKvRequest } from "@/shared/request/kv-backend";
3
+
4
+ export const createKvAdapter = (): RequestAdapter => ({
5
+ name: "kv",
6
+ capabilities: {
7
+ supportsAbort: true,
8
+ supportsTimeout: false,
9
+ supportsProgress: false,
10
+ supportsInterceptors: false,
11
+ },
12
+ request: handleKvRequest,
13
+ });
14
+
@@ -0,0 +1,244 @@
1
+ import { generateTraceId, logger } from "@vlian/logger";
2
+ import type { RequestOptions, Response } from "@vlian/request";
3
+ import { createStorage } from "@vlian/utils";
4
+ import type {
5
+ AuthSession,
6
+ DynamicRouteManifestItem,
7
+ LoginPayload,
8
+ } from "@/features/auth/auth-types";
9
+ import type { ApiEnvelope } from "@/shared/request/contracts";
10
+
11
+ interface MockUserRecord {
12
+ username: string;
13
+ password: string;
14
+ displayName: string;
15
+ permissions: string[];
16
+ }
17
+
18
+ const USERS_KEY = "mock-users";
19
+ const ROUTES_KEY = "mock-routes";
20
+ const SESSION_KEY = "mock-session";
21
+
22
+ const kvStorage = createStorage({
23
+ type: "local",
24
+ prefix: "secra-antd-kv",
25
+ defaultExpire: -1,
26
+ secret: "secra-demo",
27
+ });
28
+
29
+ const defaultUsers: MockUserRecord[] = [
30
+ {
31
+ username: "admin",
32
+ password: "admin123",
33
+ displayName: "管理员",
34
+ permissions: ["dashboard:view"],
35
+ },
36
+ {
37
+ username: "editor",
38
+ password: "editor123",
39
+ displayName: "内容编辑",
40
+ permissions: ["dashboard:view"],
41
+ },
42
+ ];
43
+
44
+ const defaultRoutes: DynamicRouteManifestItem[] = [
45
+ {
46
+ code: "dashboard.route",
47
+ path: "/dashboard",
48
+ title: "仪表盘",
49
+ component: "dashboard",
50
+ requiresAuth: true,
51
+ },
52
+ ];
53
+
54
+ let seedPromise: Promise<void> | null = null;
55
+ let seeded = false;
56
+
57
+ const createEnvelope = <T>(
58
+ data: T,
59
+ message = "OK",
60
+ code = 0,
61
+ ): ApiEnvelope<T> => ({
62
+ code,
63
+ message,
64
+ data,
65
+ });
66
+
67
+ const createResponse = <T>(
68
+ data: ApiEnvelope<T>,
69
+ status = 200,
70
+ statusText = "OK",
71
+ ): Response<ApiEnvelope<T>> => ({
72
+ data,
73
+ status,
74
+ statusText,
75
+ headers: {
76
+ "x-mock-adapter": "kv",
77
+ },
78
+ raw: null,
79
+ });
80
+
81
+ const ensureSeedData = async () => {
82
+ if (seeded) {
83
+ return;
84
+ }
85
+
86
+ if (!seedPromise) {
87
+ seedPromise = (async () => {
88
+ const users = await kvStorage.get<MockUserRecord[]>(USERS_KEY);
89
+ if (!users) {
90
+ await kvStorage.set(USERS_KEY, defaultUsers, {
91
+ expire: -1,
92
+ });
93
+ }
94
+
95
+ const routes = await kvStorage.get<DynamicRouteManifestItem[]>(ROUTES_KEY);
96
+ if (!routes) {
97
+ await kvStorage.set(ROUTES_KEY, defaultRoutes, {
98
+ expire: -1,
99
+ });
100
+ }
101
+
102
+ seeded = true;
103
+ })().finally(() => {
104
+ seedPromise = null;
105
+ });
106
+ }
107
+
108
+ await seedPromise;
109
+ };
110
+
111
+ const delay = async (timeout: number, signal?: AbortSignal) => {
112
+ if (signal?.aborted) {
113
+ throw new DOMException("Request aborted", "AbortError");
114
+ }
115
+
116
+ await new Promise<void>((resolve, reject) => {
117
+ const timer = window.setTimeout(() => {
118
+ cleanup();
119
+ resolve();
120
+ }, timeout);
121
+
122
+ const cleanup = () => {
123
+ window.clearTimeout(timer);
124
+ signal?.removeEventListener("abort", onAbort);
125
+ };
126
+
127
+ const onAbort = () => {
128
+ cleanup();
129
+ reject(new DOMException("Request aborted", "AbortError"));
130
+ };
131
+
132
+ signal?.addEventListener("abort", onAbort, {
133
+ once: true,
134
+ });
135
+ });
136
+ };
137
+
138
+ const readUsers = async () => {
139
+ const users = await kvStorage.get<MockUserRecord[]>(USERS_KEY, {
140
+ defaultValue: defaultUsers,
141
+ });
142
+ return users || defaultUsers;
143
+ };
144
+
145
+ const readRoutes = async () => {
146
+ const routes = await kvStorage.get<DynamicRouteManifestItem[]>(ROUTES_KEY, {
147
+ defaultValue: defaultRoutes,
148
+ });
149
+ return routes || defaultRoutes;
150
+ };
151
+
152
+ const readSession = async () =>
153
+ kvStorage.get<AuthSession | null>(SESSION_KEY, {
154
+ defaultValue: null,
155
+ });
156
+
157
+ const writeSession = async (session: AuthSession) => {
158
+ await kvStorage.set(SESSION_KEY, session, {
159
+ expire: -1,
160
+ });
161
+ };
162
+
163
+ const handleLogin = async (body: unknown) => {
164
+ const payload = (body || {}) as Partial<LoginPayload>;
165
+ const users = await readUsers();
166
+ const matchedUser = users.find(
167
+ (user) =>
168
+ user.username === payload.username && user.password === payload.password,
169
+ );
170
+
171
+ if (!matchedUser) {
172
+ return createResponse(
173
+ createEnvelope<null>(null, "账号或密码错误", 401),
174
+ );
175
+ }
176
+
177
+ const session: AuthSession = {
178
+ token: generateTraceId(),
179
+ username: matchedUser.username,
180
+ displayName: matchedUser.displayName,
181
+ permissions: matchedUser.permissions,
182
+ loginAt: new Date().toLocaleString("zh-CN"),
183
+ };
184
+
185
+ await writeSession(session);
186
+
187
+ return createResponse(
188
+ createEnvelope(session, "登录成功"),
189
+ );
190
+ };
191
+
192
+ const handleSession = async () => {
193
+ const session = await readSession();
194
+ return createResponse(
195
+ createEnvelope(session, "读取会话成功"),
196
+ );
197
+ };
198
+
199
+ const handleLogout = async () => {
200
+ await kvStorage.remove(SESSION_KEY);
201
+
202
+ return createResponse(
203
+ createEnvelope<null>(null, "退出成功"),
204
+ );
205
+ };
206
+
207
+ const handleRoutes = async () => {
208
+ const routes = await readRoutes();
209
+ return createResponse(
210
+ createEnvelope(routes, "读取动态路由成功"),
211
+ );
212
+ };
213
+
214
+ export const handleKvRequest = async <TResponse>(
215
+ options: RequestOptions<TResponse>,
216
+ ): Promise<Response<TResponse>> => {
217
+ await ensureSeedData();
218
+ await delay(180, options.signal);
219
+
220
+ const method = (options.method || "GET").toUpperCase();
221
+ const url = options.url;
222
+
223
+ logger.debug("request.kv", {
224
+ method,
225
+ url,
226
+ });
227
+
228
+ switch (`${method} ${url}`) {
229
+ case "POST /api/auth/login":
230
+ return (await handleLogin(options.body)) as Response<TResponse>;
231
+ case "GET /api/auth/session":
232
+ return (await handleSession()) as Response<TResponse>;
233
+ case "POST /api/auth/logout":
234
+ return (await handleLogout()) as Response<TResponse>;
235
+ case "GET /api/routes":
236
+ return (await handleRoutes()) as Response<TResponse>;
237
+ default:
238
+ return createResponse(
239
+ createEnvelope<null>(null, `Mock API not found: ${method} ${url}`, 404),
240
+ 404,
241
+ "Not Found",
242
+ ) as Response<TResponse>;
243
+ }
244
+ };
@@ -0,0 +1,6 @@
1
+ const ky = async () => {
2
+ throw new Error("ky adapter is not available in this template build.");
3
+ };
4
+
5
+ export default ky;
6
+
@@ -0,0 +1,4 @@
1
+ export const request = async () => {
2
+ throw new Error("undici adapter is not available in browser builds.");
3
+ };
4
+
@@ -0,0 +1,185 @@
1
+ :root {
2
+ color: #102a43;
3
+ background:
4
+ radial-gradient(circle at top left, rgba(21, 94, 239, 0.18), transparent 28%),
5
+ radial-gradient(circle at right 10%, rgba(13, 148, 136, 0.16), transparent 25%),
6
+ linear-gradient(180deg, #f3f7fb 0%, #eef4ff 100%);
7
+ }
8
+
9
+ html,
10
+ body,
11
+ #root {
12
+ min-height: 100%;
13
+ margin: 0;
14
+ }
15
+
16
+ body {
17
+ font-family:
18
+ "Segoe UI",
19
+ "PingFang SC",
20
+ "Hiragino Sans GB",
21
+ "Microsoft YaHei",
22
+ sans-serif;
23
+ }
24
+
25
+ .app-shell {
26
+ min-height: 100vh;
27
+ background: transparent;
28
+ }
29
+
30
+ .app-shell__header {
31
+ position: sticky;
32
+ top: 0;
33
+ z-index: 20;
34
+ display: grid;
35
+ grid-template-columns: auto 1fr auto;
36
+ align-items: center;
37
+ gap: 24px;
38
+ height: auto;
39
+ padding: 18px 28px;
40
+ background: rgba(255, 255, 255, 0.82);
41
+ border-bottom: 1px solid rgba(16, 42, 67, 0.08);
42
+ backdrop-filter: blur(16px);
43
+ }
44
+
45
+ .app-shell__brand {
46
+ display: flex;
47
+ align-items: center;
48
+ gap: 14px;
49
+ }
50
+
51
+ .app-shell__brand-badge {
52
+ display: grid;
53
+ place-items: center;
54
+ width: 44px;
55
+ height: 44px;
56
+ color: #fff;
57
+ font-weight: 700;
58
+ font-size: 22px;
59
+ background: linear-gradient(135deg, #155eef 0%, #0f8b8d 100%);
60
+ border-radius: 14px;
61
+ box-shadow: 0 14px 30px rgba(21, 94, 239, 0.24);
62
+ }
63
+
64
+ .app-shell__brand-title.ant-typography {
65
+ margin: 0;
66
+ }
67
+
68
+ .app-shell__brand-subtitle.ant-typography {
69
+ display: block;
70
+ color: #486581;
71
+ }
72
+
73
+ .app-shell__menu {
74
+ min-width: 0;
75
+ background: transparent;
76
+ border-bottom: none !important;
77
+ }
78
+
79
+ .app-shell__content {
80
+ padding: 28px;
81
+ }
82
+
83
+ .app-shell__user {
84
+ display: flex;
85
+ flex-direction: column;
86
+ line-height: 1.2;
87
+ }
88
+
89
+ .page-shell {
90
+ max-width: 1240px;
91
+ margin: 0 auto;
92
+ }
93
+
94
+ .page-stack {
95
+ display: flex;
96
+ width: 100%;
97
+ }
98
+
99
+ .page-hero.ant-card,
100
+ .surface-card.ant-card,
101
+ .login-card.ant-card,
102
+ .login-helper.ant-card {
103
+ background: rgba(255, 255, 255, 0.86);
104
+ border: 1px solid rgba(16, 42, 67, 0.08);
105
+ box-shadow: 0 18px 48px rgba(15, 23, 42, 0.08);
106
+ }
107
+
108
+ .page-hero.ant-card {
109
+ overflow: hidden;
110
+ border-radius: 28px;
111
+ }
112
+
113
+ .surface-card.ant-card {
114
+ border-radius: 24px;
115
+ }
116
+
117
+ .feature-icon {
118
+ display: grid;
119
+ place-items: center;
120
+ width: 52px;
121
+ height: 52px;
122
+ color: #155eef;
123
+ font-size: 22px;
124
+ background: rgba(21, 94, 239, 0.12);
125
+ border-radius: 18px;
126
+ }
127
+
128
+ .compact-text.ant-typography {
129
+ margin-bottom: 0;
130
+ color: #486581;
131
+ }
132
+
133
+ .center-page {
134
+ display: grid;
135
+ min-height: 80vh;
136
+ place-items: center;
137
+ }
138
+
139
+ .login-page {
140
+ position: relative;
141
+ display: grid;
142
+ min-height: 100vh;
143
+ padding: 24px;
144
+ place-items: center;
145
+ overflow: hidden;
146
+ }
147
+
148
+ .login-page__backdrop {
149
+ position: absolute;
150
+ inset: 0;
151
+ background:
152
+ radial-gradient(circle at 20% 20%, rgba(21, 94, 239, 0.25), transparent 30%),
153
+ radial-gradient(circle at 80% 15%, rgba(15, 139, 141, 0.28), transparent 24%),
154
+ linear-gradient(135deg, #102a43 0%, #243b53 40%, #d9e2ec 140%);
155
+ }
156
+
157
+ .login-card {
158
+ position: relative;
159
+ z-index: 1;
160
+ width: min(100%, 480px);
161
+ border-radius: 30px;
162
+ }
163
+
164
+ .login-card__badge {
165
+ display: grid;
166
+ place-items: center;
167
+ width: 54px;
168
+ height: 54px;
169
+ color: #fff;
170
+ font-size: 24px;
171
+ background: linear-gradient(135deg, #155eef 0%, #0f8b8d 100%);
172
+ border-radius: 18px;
173
+ }
174
+
175
+ @media (max-width: 960px) {
176
+ .app-shell__header {
177
+ grid-template-columns: 1fr;
178
+ gap: 16px;
179
+ padding: 16px;
180
+ }
181
+
182
+ .app-shell__content {
183
+ padding: 16px;
184
+ }
185
+ }
@@ -0,0 +1,2 @@
1
+ /// <reference types="vite/client" />
2
+
@@ -1,29 +1,26 @@
1
1
  {
2
2
  "compilerOptions": {
3
- "tsBuildInfoFile": "./node_modules/.tmp/tsconfig.app.tsbuildinfo",
4
- "composite": true,
5
3
  "target": "ES2022",
6
4
  "useDefineForClassFields": true,
7
5
  "lib": ["ES2022", "DOM", "DOM.Iterable"],
8
6
  "module": "ESNext",
9
- "types": ["vite/client"],
10
7
  "skipLibCheck": true,
11
-
12
- /* Bundler mode */
13
- "moduleResolution": "bundler",
14
- "allowImportingTsExtensions": true,
15
- "verbatimModuleSyntax": true,
16
- "moduleDetection": "force",
8
+ "moduleResolution": "Bundler",
9
+ "allowImportingTsExtensions": false,
10
+ "resolveJsonModule": true,
11
+ "isolatedModules": true,
17
12
  "noEmit": true,
18
13
  "jsx": "react-jsx",
19
-
20
- /* Linting */
21
14
  "strict": true,
22
15
  "noUnusedLocals": true,
23
16
  "noUnusedParameters": true,
24
- "erasableSyntaxOnly": true,
25
17
  "noFallthroughCasesInSwitch": true,
26
- "noUncheckedSideEffectImports": true
18
+ "baseUrl": ".",
19
+ "paths": {
20
+ "@/*": ["./src/*"]
21
+ },
22
+ "tsBuildInfoFile": "./node_modules/.tmp/tsconfig.app.tsbuildinfo"
27
23
  },
28
24
  "include": ["src"]
29
25
  }
26
+
@@ -1,7 +1,12 @@
1
1
  {
2
2
  "files": [],
3
3
  "references": [
4
- { "path": "./tsconfig.app.json" },
5
- { "path": "./tsconfig.node.json" }
4
+ {
5
+ "path": "./tsconfig.app.json"
6
+ },
7
+ {
8
+ "path": "./tsconfig.node.json"
9
+ }
6
10
  ]
7
11
  }
12
+
@@ -1,27 +1,17 @@
1
1
  {
2
2
  "compilerOptions": {
3
- "tsBuildInfoFile": "./node_modules/.tmp/tsconfig.node.tsbuildinfo",
4
- "composite": true,
5
3
  "target": "ES2023",
6
4
  "lib": ["ES2023"],
7
5
  "module": "ESNext",
8
- "types": ["node"],
9
6
  "skipLibCheck": true,
10
-
11
- /* Bundler mode */
12
- "moduleResolution": "bundler",
13
- "allowImportingTsExtensions": true,
14
- "verbatimModuleSyntax": true,
15
- "moduleDetection": "force",
7
+ "moduleResolution": "Bundler",
8
+ "allowSyntheticDefaultImports": true,
9
+ "resolveJsonModule": true,
10
+ "isolatedModules": true,
16
11
  "noEmit": true,
17
-
18
- /* Linting */
19
12
  "strict": true,
20
- "noUnusedLocals": true,
21
- "noUnusedParameters": true,
22
- "erasableSyntaxOnly": true,
23
- "noFallthroughCasesInSwitch": true,
24
- "noUncheckedSideEffectImports": true
13
+ "tsBuildInfoFile": "./node_modules/.tmp/tsconfig.node.tsbuildinfo"
25
14
  },
26
15
  "include": ["vite.config.ts"]
27
16
  }
17
+
@@ -0,0 +1,24 @@
1
+ import path from "node:path";
2
+ import { defineConfig } from "vite";
3
+ import react from "@vitejs/plugin-react";
4
+
5
+ export default defineConfig({
6
+ plugins: [react()],
7
+ resolve: {
8
+ alias: {
9
+ "@": path.resolve(__dirname, "./src"),
10
+ ky: path.resolve(
11
+ __dirname,
12
+ "./src/shared/request/ky-browser-stub.ts",
13
+ ),
14
+ undici: path.resolve(
15
+ __dirname,
16
+ "./src/shared/request/undici-browser-stub.ts",
17
+ ),
18
+ },
19
+ },
20
+ server: {
21
+ host: "127.0.0.1",
22
+ port: 5173,
23
+ },
24
+ });