@lobehub/lobehub 2.0.0-next.90 → 2.0.0-next.91

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.
@@ -1,8 +1,10 @@
1
1
  'use client';
2
2
 
3
+ import dynamic from 'next/dynamic';
3
4
  import { useEffect } from 'react';
4
- import { type LoaderFunction, createBrowserRouter, redirect, useNavigate } from 'react-router-dom';
5
+ import { createBrowserRouter, redirect, useNavigate, useRouteError } from 'react-router-dom';
5
6
 
7
+ import ErrorCapture from '@/components/Error';
6
8
  import Loading from '@/components/Loading/BrandTextLoading';
7
9
  import { useGlobalStore } from '@/store/global';
8
10
  import type { Locales } from '@/types/locale';
@@ -10,6 +12,233 @@ import type { Locales } from '@/types/locale';
10
12
  import { MobileMainLayout } from './(main)/layouts/mobile';
11
13
  import { idLoader, slugLoader } from './loaders/routeParams';
12
14
 
15
+ /**
16
+ * Mobile Router Configuration - Pure CSR Mode
17
+ *
18
+ * IMPORTANT: This router runs ONLY in the browser (client-side).
19
+ *
20
+ * Key characteristics:
21
+ * - createBrowserRouter uses window.history API (client-only)
22
+ * - All loaders execute in the browser during navigation
23
+ * - No server-side rendering or hydration involved
24
+ * - Route data fetching happens on-demand during client navigation
25
+ *
26
+ * The entire router tree is wrapped with Next.js dynamic import (ssr: false),
27
+ * ensuring this code never executes on the server.
28
+ */
29
+
30
+ // Chat components
31
+ const MobileChatPage = dynamic(() => import('./(main)/chat/index').then((m) => m.MobileChatPage), {
32
+ loading: () => <Loading />,
33
+ ssr: false,
34
+ });
35
+ const ChatSettings = dynamic(() => import('./(main)/chat/settings'), {
36
+ loading: () => <Loading />,
37
+ ssr: false,
38
+ });
39
+ const ChatLayout = dynamic(() => import('./(main)/chat/_layout/Mobile'), {
40
+ loading: () => <Loading />,
41
+ ssr: false,
42
+ });
43
+
44
+ // Discover List components
45
+ const MobileHomePage = dynamic(
46
+ () => import('./(main)/discover/(list)/(home)/index').then((m) => m.MobileHomePage),
47
+ {
48
+ loading: () => <Loading />,
49
+ ssr: false,
50
+ },
51
+ );
52
+ const MobileAssistantPage = dynamic(
53
+ () => import('./(main)/discover/(list)/assistant/index').then((m) => m.MobileAssistantPage),
54
+ {
55
+ loading: () => <Loading />,
56
+ ssr: false,
57
+ },
58
+ );
59
+ const DiscoverAssistantLayout = dynamic(
60
+ () => import('./(main)/discover/(list)/assistant/_layout/Mobile'),
61
+ {
62
+ loading: () => <Loading />,
63
+ ssr: false,
64
+ },
65
+ );
66
+ const DiscoverListMobileModelPage = dynamic(
67
+ () => import('./(main)/discover/(list)/model/index').then((m) => m.MobileModelPage),
68
+ {
69
+ loading: () => <Loading />,
70
+ ssr: false,
71
+ },
72
+ );
73
+ const DiscoverModelLayout = dynamic(() => import('./(main)/discover/(list)/model/_layout/Mobile'), {
74
+ loading: () => <Loading />,
75
+ ssr: false,
76
+ });
77
+ const DiscoverListMobileProviderPage = dynamic(
78
+ () => import('./(main)/discover/(list)/provider/index').then((m) => m.MobileProviderPage),
79
+ {
80
+ loading: () => <Loading />,
81
+ ssr: false,
82
+ },
83
+ );
84
+ const DiscoverListMobileMcpPage = dynamic(
85
+ () => import('./(main)/discover/(list)/mcp/index').then((m) => m.MobileMcpPage),
86
+ {
87
+ loading: () => <Loading />,
88
+ ssr: false,
89
+ },
90
+ );
91
+ const DiscoverMcpLayout = dynamic(() => import('./(main)/discover/(list)/mcp/_layout/Mobile'), {
92
+ loading: () => <Loading />,
93
+ ssr: false,
94
+ });
95
+ const DiscoverListLayout = dynamic(() => import('./(main)/discover/(list)/_layout/Mobile/index'), {
96
+ loading: () => <Loading />,
97
+ ssr: false,
98
+ });
99
+
100
+ // Discover Detail components
101
+ const MobileDiscoverAssistantDetailPage = dynamic(
102
+ () =>
103
+ import('./(main)/discover/(detail)/assistant/index').then(
104
+ (m) => m.MobileDiscoverAssistantDetailPage,
105
+ ),
106
+ {
107
+ loading: () => <Loading />,
108
+ ssr: false,
109
+ },
110
+ );
111
+ const DiscoverDetailMobileModelPage = dynamic(
112
+ () => import('./(main)/discover/(detail)/model/index').then((m) => m.MobileModelPage),
113
+ {
114
+ loading: () => <Loading />,
115
+ ssr: false,
116
+ },
117
+ );
118
+ const DiscoverDetailMobileProviderPage = dynamic(
119
+ () => import('./(main)/discover/(detail)/provider/index').then((m) => m.MobileProviderPage),
120
+ {
121
+ loading: () => <Loading />,
122
+ ssr: false,
123
+ },
124
+ );
125
+ const DiscoverDetailMobileMcpPage = dynamic(
126
+ () => import('./(main)/discover/(detail)/mcp/index').then((m) => m.MobileMcpPage),
127
+ {
128
+ loading: () => <Loading />,
129
+ ssr: false,
130
+ },
131
+ );
132
+ const DiscoverDetailLayout = dynamic(
133
+ () => import('./(main)/discover/(detail)/_layout/Mobile/index'),
134
+ {
135
+ loading: () => <Loading />,
136
+ ssr: false,
137
+ },
138
+ );
139
+ const DiscoverLayout = dynamic(() => import('./(main)/discover/_layout/Mobile/index'), {
140
+ loading: () => <Loading />,
141
+ ssr: false,
142
+ });
143
+
144
+ // Knowledge components
145
+ const KnowledgeHome = dynamic(() => import('./(main)/knowledge/routes/KnowledgeHome'), {
146
+ loading: () => <Loading />,
147
+ ssr: false,
148
+ });
149
+ const KnowledgeBasesList = dynamic(() => import('./(main)/knowledge/routes/KnowledgeBasesList'), {
150
+ loading: () => <Loading />,
151
+ ssr: false,
152
+ });
153
+ const KnowledgeBaseDetail = dynamic(() => import('./(main)/knowledge/routes/KnowledgeBaseDetail'), {
154
+ loading: () => <Loading />,
155
+ ssr: false,
156
+ });
157
+ const KnowledgeLayout = dynamic(() => import('./(main)/knowledge/_layout/Mobile'), {
158
+ loading: () => <Loading />,
159
+ ssr: false,
160
+ });
161
+
162
+ // Settings components
163
+ const SettingsLayout = dynamic(() => import('./(main)/settings/_layout/Mobile'), {
164
+ loading: () => <Loading />,
165
+ ssr: false,
166
+ });
167
+ const SettingsLayoutWrapper = dynamic(() => import('./(main)/settings/_layout/MobileWrapper'), {
168
+ loading: () => <Loading />,
169
+ ssr: false,
170
+ });
171
+
172
+ // Image components
173
+ const ImageComingSoon = dynamic(() => import('./(main)/image/ComingSoon'), {
174
+ loading: () => <Loading />,
175
+ ssr: false,
176
+ });
177
+ const ImageLayoutMobile = dynamic(() => import('./(main)/image/_layout/Mobile'), {
178
+ loading: () => <Loading />,
179
+ ssr: false,
180
+ });
181
+
182
+ // Labs components
183
+ const LabsPage = dynamic(() => import('./(main)/labs'), {
184
+ loading: () => <Loading />,
185
+ ssr: false,
186
+ });
187
+
188
+ // Profile components
189
+ const ProfileHomePage = dynamic(() => import('./(main)/profile/(home)'), {
190
+ loading: () => <Loading />,
191
+ ssr: false,
192
+ });
193
+ const ProfileApikeyPage = dynamic(() => import('./(main)/profile/apikey/index'), {
194
+ loading: () => <Loading />,
195
+ ssr: false,
196
+ });
197
+ const MobileProfileSecurityPage = dynamic(
198
+ () => import('./(main)/profile/security').then((m) => m.MobileProfileSecurityPage),
199
+ {
200
+ loading: () => <Loading />,
201
+ ssr: false,
202
+ },
203
+ );
204
+ const MobileProfileStatsPage = dynamic(
205
+ () => import('./(main)/profile/stats').then((m) => m.MobileProfileStatsPage),
206
+ {
207
+ loading: () => <Loading />,
208
+ ssr: false,
209
+ },
210
+ );
211
+ const ProfileLayoutMobile = dynamic(() => import('./(main)/profile/_layout/Mobile'), {
212
+ loading: () => <Loading />,
213
+ ssr: false,
214
+ });
215
+
216
+ // Me (mobile personal center) components
217
+ const MeHomePage = dynamic(() => import('./(main)/(mobile)/me/(home)'), {
218
+ loading: () => <Loading />,
219
+ ssr: false,
220
+ });
221
+ const MeHomeLayout = dynamic(() => import('./(main)/(mobile)/me/(home)/layout'), {
222
+ loading: () => <Loading />,
223
+ ssr: false,
224
+ });
225
+ const MeProfilePage = dynamic(() => import('./(main)/(mobile)/me/profile'), {
226
+ loading: () => <Loading />,
227
+ ssr: false,
228
+ });
229
+ const MeProfileLayout = dynamic(() => import('./(main)/(mobile)/me/profile/layout'), {
230
+ loading: () => <Loading />,
231
+ ssr: false,
232
+ });
233
+ const MeSettingsPage = dynamic(() => import('./(main)/(mobile)/me/settings'), {
234
+ loading: () => <Loading />,
235
+ ssr: false,
236
+ });
237
+ const MeSettingsLayout = dynamic(() => import('./(main)/(mobile)/me/settings/layout'), {
238
+ loading: () => <Loading />,
239
+ ssr: false,
240
+ });
241
+
13
242
  // Component to register navigate function in global store
14
243
  const NavigatorRegistrar = () => {
15
244
  const navigate = useNavigate();
@@ -25,8 +254,32 @@ const NavigatorRegistrar = () => {
25
254
  return null;
26
255
  };
27
256
 
28
- // Root layout wrapper component - just registers navigator and renders outlet
29
- // Note: Mobile layout is provided by individual route components
257
+ // Error boundary factory for React Router errorElement
258
+ const createErrorBoundary = (resetPath: string) => {
259
+ const ErrorBoundary = () => {
260
+ const error = useRouteError() as Error;
261
+ const navigate = useNavigate();
262
+
263
+ const reset = () => {
264
+ navigate(resetPath);
265
+ };
266
+
267
+ return <ErrorCapture error={error} reset={reset} />;
268
+ };
269
+ return ErrorBoundary;
270
+ };
271
+
272
+ // Create error boundaries for each route
273
+ const ChatErrorBoundary = createErrorBoundary('/chat');
274
+ const DiscoverErrorBoundary = createErrorBoundary('/discover');
275
+ const KnowledgeErrorBoundary = createErrorBoundary('/knowledge');
276
+ const SettingsErrorBoundary = createErrorBoundary('/settings');
277
+ const ImageErrorBoundary = createErrorBoundary('/image');
278
+ const ProfileErrorBoundary = createErrorBoundary('/profile');
279
+ const MeErrorBoundary = createErrorBoundary('/me'); // Mobile only
280
+ const RootErrorBoundary = createErrorBoundary('/chat'); // Root level falls back to chat
281
+
282
+ // Root layout wrapper component
30
283
  const RootLayout = (props: { locale: Locales }) => (
31
284
  <>
32
285
  <NavigatorRegistrar />
@@ -34,39 +287,25 @@ const RootLayout = (props: { locale: Locales }) => (
34
287
  </>
35
288
  );
36
289
 
37
- // Hydration gate loader -always return true to bypass hydration gate
38
- const hydrationGateLoader: LoaderFunction = () => {
39
- return true
40
- };
41
-
42
290
  // Create mobile router configuration
43
291
  export const createMobileRouter = (locale: Locales) =>
44
292
  createBrowserRouter([
45
293
  {
46
- HydrateFallback: () => <Loading />,
47
294
  children: [
48
295
  // Chat routes
49
296
  {
50
297
  children: [
51
298
  {
299
+ element: <MobileChatPage />,
52
300
  index: true,
53
- lazy: () =>
54
- import('./(main)/chat/index').then((m) => ({
55
- Component: m.MobileChatPage,
56
- })),
57
301
  },
58
302
  {
59
- lazy: () =>
60
- import('./(main)/chat/settings').then((m) => ({
61
- Component: m.default,
62
- })),
303
+ element: <ChatSettings />,
63
304
  path: 'settings',
64
305
  },
65
306
  ],
66
- lazy: () =>
67
- import('./(main)/chat/_layout/Mobile').then((m) => ({
68
- Component: m.default,
69
- })),
307
+ element: <ChatLayout />,
308
+ errorElement: <ChatErrorBoundary />,
70
309
  path: 'chat',
71
310
  },
72
311
 
@@ -77,116 +316,72 @@ export const createMobileRouter = (locale: Locales) =>
77
316
  {
78
317
  children: [
79
318
  {
319
+ element: <MobileHomePage />,
80
320
  index: true,
81
- lazy: () =>
82
- import('./(main)/discover/(list)/(home)/index').then((m) => ({
83
- Component: m.MobileHomePage,
84
- })),
85
321
  },
86
322
  {
87
323
  children: [
88
324
  {
89
- lazy: () =>
90
- import('./(main)/discover/(list)/assistant/index').then((m) => ({
91
- Component: m.MobileAssistantPage,
92
- })),
325
+ element: <MobileAssistantPage />,
93
326
  path: 'assistant',
94
327
  },
95
328
  ],
96
- lazy: () =>
97
- import('./(main)/discover/(list)/assistant/_layout/Mobile').then((m) => ({
98
- Component: m.default,
99
- })),
329
+ element: <DiscoverAssistantLayout />,
100
330
  },
101
331
  {
102
332
  children: [
103
333
  {
104
- lazy: () =>
105
- import('./(main)/discover/(list)/model/index').then((m) => ({
106
- Component: m.MobileModelPage,
107
- })),
334
+ element: <DiscoverListMobileModelPage />,
108
335
  path: 'model',
109
336
  },
110
337
  ],
111
- lazy: () =>
112
- import('./(main)/discover/(list)/model/_layout/Mobile').then((m) => ({
113
- Component: m.default,
114
- })),
338
+ element: <DiscoverModelLayout />,
115
339
  },
116
340
  {
117
- lazy: () =>
118
- import('./(main)/discover/(list)/provider/index').then((m) => ({
119
- Component: m.MobileProviderPage,
120
- })),
341
+ element: <DiscoverListMobileProviderPage />,
121
342
  path: 'provider',
122
343
  },
123
344
  {
124
345
  children: [
125
346
  {
126
- lazy: () =>
127
- import('./(main)/discover/(list)/mcp/index').then((m) => ({
128
- Component: m.MobileMcpPage,
129
- })),
347
+ element: <DiscoverListMobileMcpPage />,
130
348
  path: 'mcp',
131
349
  },
132
350
  ],
133
- lazy: () =>
134
- import('./(main)/discover/(list)/mcp/_layout/Mobile').then((m) => ({
135
- Component: m.default,
136
- })),
351
+ element: <DiscoverMcpLayout />,
137
352
  },
138
353
  ],
139
- lazy: () =>
140
- import('./(main)/discover/(list)/_layout/Mobile/index').then((m) => ({
141
- Component: m.default,
142
- })),
354
+ element: <DiscoverListLayout />,
143
355
  },
144
356
  // Detail routes (with DetailLayout)
145
357
  {
146
358
  children: [
147
359
  {
148
- lazy: () =>
149
- import('./(main)/discover/(detail)/assistant/index').then((m) => ({
150
- Component: m.MobileDiscoverAssistantDetailPage,
151
- })),
360
+ element: <MobileDiscoverAssistantDetailPage />,
152
361
  loader: slugLoader,
153
362
  path: 'assistant/:slug',
154
363
  },
155
364
  {
156
- lazy: () =>
157
- import('./(main)/discover/(detail)/model/index').then((m) => ({
158
- Component: m.MobileModelPage,
159
- })),
365
+ element: <DiscoverDetailMobileModelPage />,
160
366
  loader: slugLoader,
161
367
  path: 'model/:slug',
162
368
  },
163
369
  {
164
- lazy: () =>
165
- import('./(main)/discover/(detail)/provider/index').then((m) => ({
166
- Component: m.MobileProviderPage,
167
- })),
370
+ element: <DiscoverDetailMobileProviderPage />,
168
371
  loader: slugLoader,
169
372
  path: 'provider/:slug',
170
373
  },
171
374
  {
172
- lazy: () =>
173
- import('./(main)/discover/(detail)/mcp/index').then((m) => ({
174
- Component: m.MobileMcpPage,
175
- })),
375
+ element: <DiscoverDetailMobileMcpPage />,
176
376
  loader: slugLoader,
177
377
  path: 'mcp/:slug',
178
378
  },
179
379
  ],
180
- lazy: () =>
181
- import('./(main)/discover/(detail)/_layout/Mobile/index').then((m) => ({
182
- Component: m.default,
183
- })),
380
+ element: <DiscoverDetailLayout />,
184
381
  },
185
382
  ],
186
- lazy: () =>
187
- import('./(main)/discover/_layout/Mobile/index').then((m) => ({
188
- Component: m.default,
189
- })),
383
+ element: <DiscoverLayout />,
384
+ errorElement: <DiscoverErrorBoundary />,
190
385
  path: 'discover',
191
386
  },
192
387
 
@@ -194,32 +389,21 @@ export const createMobileRouter = (locale: Locales) =>
194
389
  {
195
390
  children: [
196
391
  {
392
+ element: <KnowledgeHome />,
197
393
  index: true,
198
- lazy: () =>
199
- import('./(main)/knowledge/routes/KnowledgeHome').then((m) => ({
200
- Component: m.default,
201
- })),
202
394
  },
203
395
  {
204
- lazy: () =>
205
- import('./(main)/knowledge/routes/KnowledgeBasesList').then((m) => ({
206
- Component: m.default,
207
- })),
396
+ element: <KnowledgeBasesList />,
208
397
  path: 'bases',
209
398
  },
210
399
  {
211
- lazy: () =>
212
- import('./(main)/knowledge/routes/KnowledgeBaseDetail').then((m) => ({
213
- Component: m.default,
214
- })),
400
+ element: <KnowledgeBaseDetail />,
215
401
  loader: idLoader,
216
402
  path: 'bases/:id',
217
403
  },
218
404
  ],
219
- lazy: () =>
220
- import('./(main)/knowledge/_layout/Mobile').then((m) => ({
221
- Component: m.default,
222
- })),
405
+ element: <KnowledgeLayout />,
406
+ errorElement: <KnowledgeErrorBoundary />,
223
407
  path: 'knowledge',
224
408
  },
225
409
 
@@ -227,17 +411,12 @@ export const createMobileRouter = (locale: Locales) =>
227
411
  {
228
412
  children: [
229
413
  {
414
+ element: <SettingsLayout />,
230
415
  index: true,
231
- lazy: () =>
232
- import('./(main)/settings/_layout/Mobile').then((m) => ({
233
- Component: m.default,
234
- })),
235
416
  },
236
417
  ],
237
- lazy: () =>
238
- import('./(main)/settings/_layout/MobileWrapper').then((m) => ({
239
- Component: m.default,
240
- })),
418
+ element: <SettingsLayoutWrapper />,
419
+ errorElement: <SettingsErrorBoundary />,
241
420
  path: 'settings',
242
421
  },
243
422
 
@@ -245,26 +424,18 @@ export const createMobileRouter = (locale: Locales) =>
245
424
  {
246
425
  children: [
247
426
  {
427
+ element: <ImageComingSoon />,
248
428
  index: true,
249
- lazy: () =>
250
- import('./(main)/image/ComingSoon').then((m) => ({
251
- Component: m.default,
252
- })),
253
429
  },
254
430
  ],
255
- lazy: () =>
256
- import('./(main)/image/_layout/Mobile').then((m) => ({
257
- Component: m.default,
258
- })),
431
+ element: <ImageLayoutMobile />,
432
+ errorElement: <ImageErrorBoundary />,
259
433
  path: 'image',
260
434
  },
261
435
 
262
436
  // Labs routes
263
437
  {
264
- lazy: () =>
265
- import('./(main)/labs').then((m) => ({
266
- Component: m.default,
267
- })),
438
+ element: <LabsPage />,
268
439
  path: 'labs',
269
440
  },
270
441
 
@@ -272,38 +443,24 @@ export const createMobileRouter = (locale: Locales) =>
272
443
  {
273
444
  children: [
274
445
  {
446
+ element: <ProfileHomePage />,
275
447
  index: true,
276
- lazy: () =>
277
- import('./(main)/profile/(home)').then((m) => ({
278
- Component: m.default,
279
- })),
280
448
  },
281
449
  {
282
- lazy: () =>
283
- import('./(main)/profile/apikey/index').then((m) => ({
284
- Component: m.default,
285
- })),
450
+ element: <ProfileApikeyPage />,
286
451
  path: 'apikey',
287
452
  },
288
453
  {
289
- lazy: () =>
290
- import('./(main)/profile/security').then((m) => ({
291
- Component: m.MobileProfileSecurityPage,
292
- })),
454
+ element: <MobileProfileSecurityPage />,
293
455
  path: 'security',
294
456
  },
295
457
  {
296
- lazy: () =>
297
- import('./(main)/profile/stats').then((m) => ({
298
- Component: m.MobileProfileStatsPage,
299
- })),
458
+ element: <MobileProfileStatsPage />,
300
459
  path: 'stats',
301
460
  },
302
461
  ],
303
- lazy: () =>
304
- import('./(main)/profile/_layout/Mobile').then((m) => ({
305
- Component: m.default,
306
- })),
462
+ element: <ProfileLayoutMobile />,
463
+ errorElement: <ProfileErrorBoundary />,
307
464
  path: 'profile',
308
465
  },
309
466
 
@@ -313,49 +470,32 @@ export const createMobileRouter = (locale: Locales) =>
313
470
  {
314
471
  children: [
315
472
  {
473
+ element: <MeHomePage />,
316
474
  index: true,
317
- lazy: () =>
318
- import('./(main)/(mobile)/me/(home)').then((m) => ({
319
- Component: m.default,
320
- })),
321
475
  },
322
476
  ],
323
- lazy: () =>
324
- import('./(main)/(mobile)/me/(home)/layout').then((m) => ({
325
- Component: m.default,
326
- })),
477
+ element: <MeHomeLayout />,
327
478
  },
328
479
  {
329
480
  children: [
330
481
  {
331
- lazy: () =>
332
- import('./(main)/(mobile)/me/profile').then((m) => ({
333
- Component: m.default,
334
- })),
482
+ element: <MeProfilePage />,
335
483
  path: 'profile',
336
484
  },
337
485
  ],
338
- lazy: () =>
339
- import('./(main)/(mobile)/me/profile/layout').then((m) => ({
340
- Component: m.default,
341
- })),
486
+ element: <MeProfileLayout />,
342
487
  },
343
488
  {
344
489
  children: [
345
490
  {
346
- lazy: () =>
347
- import('./(main)/(mobile)/me/settings').then((m) => ({
348
- Component: m.default,
349
- })),
491
+ element: <MeSettingsPage />,
350
492
  path: 'settings',
351
493
  },
352
494
  ],
353
- lazy: () =>
354
- import('./(main)/(mobile)/me/settings/layout').then((m) => ({
355
- Component: m.default,
356
- })),
495
+ element: <MeSettingsLayout />,
357
496
  },
358
497
  ],
498
+ errorElement: <MeErrorBoundary />,
359
499
  path: 'me',
360
500
  },
361
501
 
@@ -372,7 +512,7 @@ export const createMobileRouter = (locale: Locales) =>
372
512
  },
373
513
  ],
374
514
  element: <RootLayout locale={locale} />,
375
- loader: hydrationGateLoader,
515
+ errorElement: <RootErrorBoundary />,
376
516
  path: '/',
377
517
  },
378
518
  ]);
@@ -12,6 +12,9 @@ export default async (props: DynamicLayoutProps) => {
12
12
  // Conditionally load and render based on device type
13
13
  // Using native dynamic import ensures complete code splitting
14
14
  // Mobile and Desktop bundles will be completely separate
15
+
16
+ console.log('isMobile', isMobile);
17
+ console.log('locale', locale);
15
18
  if (isMobile) {
16
19
  return <MobileRouter locale={locale} />;
17
20
  }
@@ -63,16 +63,7 @@ const StoreInitialization = memo(() => {
63
63
 
64
64
  // init user state
65
65
  useInitUserState(isLoginOnInit, serverConfig, {
66
- onError: () => {
67
- // 即使失败也要设置标志,避免应用卡住
68
- useGlobalStore.setState({ isAppHydrated: true });
69
- console.warn('[Hydration] Client state initialization failed.');
70
- },
71
66
  onSuccess: (state) => {
72
- // 设置水合完成标志
73
- useGlobalStore.setState({ isAppHydrated: true });
74
- console.log('[Hydration] Client state initialized successfully.');
75
-
76
67
  if (state.isOnboard === false) {
77
68
  router.push('/onboard');
78
69
  }