@tailor-platform/app-shell 0.17.1 → 0.19.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.
- package/dist/app-shell.css +1 -0
- package/dist/app-shell.js +1316 -0
- package/dist/index.d.ts +639 -407
- package/package.json +17 -16
- package/dist/index.css +0 -2
- package/dist/index.js +0 -1
package/dist/index.d.ts
CHANGED
|
@@ -1,407 +1,639 @@
|
|
|
1
|
-
import
|
|
2
|
-
import {
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
};
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
};
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
*
|
|
87
|
-
*
|
|
88
|
-
*
|
|
89
|
-
*/
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
/**
|
|
99
|
-
*
|
|
100
|
-
*
|
|
101
|
-
*
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
*
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
*
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
*
|
|
179
|
-
*
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
/**
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
*
|
|
197
|
-
*
|
|
198
|
-
*
|
|
199
|
-
*
|
|
200
|
-
*
|
|
201
|
-
*
|
|
202
|
-
*
|
|
203
|
-
*
|
|
204
|
-
*
|
|
205
|
-
*
|
|
206
|
-
*
|
|
207
|
-
*
|
|
208
|
-
*
|
|
209
|
-
*
|
|
210
|
-
*
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
*
|
|
238
|
-
*
|
|
239
|
-
*
|
|
240
|
-
*
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
|
|
293
|
-
}
|
|
294
|
-
|
|
295
|
-
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
*
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
*
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
}
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
*
|
|
343
|
-
*
|
|
344
|
-
*
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
|
|
348
|
-
*
|
|
349
|
-
|
|
350
|
-
|
|
351
|
-
|
|
352
|
-
|
|
353
|
-
|
|
354
|
-
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
}
|
|
369
|
-
|
|
370
|
-
*
|
|
371
|
-
|
|
372
|
-
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
|
|
377
|
-
|
|
378
|
-
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
}
|
|
382
|
-
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
/**
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
/**
|
|
397
|
-
*
|
|
398
|
-
*
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
1
|
+
import { AuthState } from '@tailor-platform/auth-browser-client';
|
|
2
|
+
import { DocumentNode } from 'graphql';
|
|
3
|
+
import { JSX } from 'react/jsx-runtime';
|
|
4
|
+
import { Link } from 'react-router';
|
|
5
|
+
import { ReactNode } from 'react';
|
|
6
|
+
import { useLocation } from 'react-router';
|
|
7
|
+
import { useNavigate } from 'react-router';
|
|
8
|
+
import { useParams } from 'react-router';
|
|
9
|
+
import { useRouteError } from 'react-router';
|
|
10
|
+
import { useSearchParams } from 'react-router';
|
|
11
|
+
|
|
12
|
+
export declare const AppShell: (props: AppShellProps) => JSX.Element | null;
|
|
13
|
+
|
|
14
|
+
declare type AppShellContextType = {
|
|
15
|
+
title?: string;
|
|
16
|
+
icon?: ReactNode;
|
|
17
|
+
configurations: RootConfiguration;
|
|
18
|
+
navItems: Array<NavItem>;
|
|
19
|
+
};
|
|
20
|
+
|
|
21
|
+
export declare type AppShellProps = React.PropsWithChildren<{
|
|
22
|
+
/**
|
|
23
|
+
* App shell title
|
|
24
|
+
*/
|
|
25
|
+
title?: string;
|
|
26
|
+
/**
|
|
27
|
+
* App shell icon
|
|
28
|
+
*/
|
|
29
|
+
icon?: React.ReactNode;
|
|
30
|
+
/**
|
|
31
|
+
* Base path for the app shell
|
|
32
|
+
*/
|
|
33
|
+
basePath?: string;
|
|
34
|
+
/**
|
|
35
|
+
* A component to be rendered at the root level of AppShell,
|
|
36
|
+
* or a redirect configuration
|
|
37
|
+
*
|
|
38
|
+
* @example
|
|
39
|
+
* ```tsx
|
|
40
|
+
* // Render a component
|
|
41
|
+
* rootComponent: () => <DashboardHome />
|
|
42
|
+
*
|
|
43
|
+
* // Redirect to a resource
|
|
44
|
+
* rootComponent: redirectToResource("dashboard/overview")
|
|
45
|
+
* ```
|
|
46
|
+
*/
|
|
47
|
+
rootComponent?: (() => React.ReactNode) | RedirectConfig;
|
|
48
|
+
/**
|
|
49
|
+
* Navigation configuration
|
|
50
|
+
*/
|
|
51
|
+
modules: Modules;
|
|
52
|
+
/**
|
|
53
|
+
* Settings resources to be included in the settings menu
|
|
54
|
+
*/
|
|
55
|
+
settingsResources?: Array<Resource>;
|
|
56
|
+
/**
|
|
57
|
+
* Locale code used for built-in UI strings.
|
|
58
|
+
*
|
|
59
|
+
* If not provided, auto-detects from browser preferences.
|
|
60
|
+
* No browser locale information avilable, "en" used as default.
|
|
61
|
+
*/
|
|
62
|
+
locale?: string;
|
|
63
|
+
/**
|
|
64
|
+
* Global error boundary component applied to all routes.
|
|
65
|
+
*
|
|
66
|
+
* When an error occurs in any route component, this component will render.
|
|
67
|
+
* Module and resource-level error boundaries take precedence over this.
|
|
68
|
+
* Use the `useRouteError` hook to access error details within the component.
|
|
69
|
+
*
|
|
70
|
+
* @example
|
|
71
|
+
* ```tsx
|
|
72
|
+
* import { useRouteError } from "@tailor-platform/app-shell";
|
|
73
|
+
*
|
|
74
|
+
* const GlobalErrorBoundary = () => {
|
|
75
|
+
* const error = useRouteError() as Error;
|
|
76
|
+
* return (
|
|
77
|
+
* <div>
|
|
78
|
+
* <h1>Something went wrong</h1>
|
|
79
|
+
* <p>{error.message}</p>
|
|
80
|
+
* </div>
|
|
81
|
+
* );
|
|
82
|
+
* };
|
|
83
|
+
*
|
|
84
|
+
* <AppShell
|
|
85
|
+
* modules: [...],
|
|
86
|
+
* errorBoundary: <GlobalErrorBoundary />,
|
|
87
|
+
* />
|
|
88
|
+
* ```
|
|
89
|
+
*/
|
|
90
|
+
errorBoundary?: ErrorBoundaryComponent;
|
|
91
|
+
}>;
|
|
92
|
+
|
|
93
|
+
declare type AuthContextType = {
|
|
94
|
+
/**
|
|
95
|
+
* Current authentication state.
|
|
96
|
+
*/
|
|
97
|
+
authState: AuthState<User>;
|
|
98
|
+
/**
|
|
99
|
+
* Initiates the login process.
|
|
100
|
+
*
|
|
101
|
+
* This redirects the user to the Tailor Platform authentication page.
|
|
102
|
+
*/
|
|
103
|
+
login: () => Promise<void>;
|
|
104
|
+
/**
|
|
105
|
+
* Logs out the current user.
|
|
106
|
+
*
|
|
107
|
+
* This clears the authentication tokens and user session.
|
|
108
|
+
*/
|
|
109
|
+
logout: () => Promise<void>;
|
|
110
|
+
/**
|
|
111
|
+
* Checks the current authentication status.
|
|
112
|
+
*
|
|
113
|
+
* Remember that this method always makes a network request to verify the auth status.
|
|
114
|
+
* If the user is authenticated, returns the user information and updates `authState` in the context.
|
|
115
|
+
*
|
|
116
|
+
* This also attempts to refresh tokens internally if they are expired.
|
|
117
|
+
*/
|
|
118
|
+
checkAuthStatus: () => Promise<AuthState<User>>;
|
|
119
|
+
/**
|
|
120
|
+
* OAuth callback handler.
|
|
121
|
+
*/
|
|
122
|
+
handleCallback: () => Promise<void>;
|
|
123
|
+
};
|
|
124
|
+
|
|
125
|
+
/**
|
|
126
|
+
* Authentication provider component.
|
|
127
|
+
*
|
|
128
|
+
* Wrap your application with this component to provide authentication context.
|
|
129
|
+
*
|
|
130
|
+
* @example
|
|
131
|
+
* ```tsx
|
|
132
|
+
* import { AuthProvider } from "@tailor-platform/app-shell";
|
|
133
|
+
*
|
|
134
|
+
* function App() {
|
|
135
|
+
* return (
|
|
136
|
+
* <AuthProvider
|
|
137
|
+
* apiEndpoint="https://xyz.erp.dev"
|
|
138
|
+
* clientId="your-client-id"
|
|
139
|
+
* >
|
|
140
|
+
* <YourAppComponents />
|
|
141
|
+
* </AuthProvider>
|
|
142
|
+
* );
|
|
143
|
+
* }
|
|
144
|
+
* ```
|
|
145
|
+
*/
|
|
146
|
+
export declare const AuthProvider: (props: React.PropsWithChildren<AuthProviderProps>) => JSX.Element;
|
|
147
|
+
|
|
148
|
+
declare type AuthProviderProps = {
|
|
149
|
+
/**
|
|
150
|
+
* API endpoint of your Tailor Platform application. No `/query` suffix needed.
|
|
151
|
+
*
|
|
152
|
+
* @example https://xyz.erp.dev
|
|
153
|
+
*/
|
|
154
|
+
apiEndpoint: string;
|
|
155
|
+
/**
|
|
156
|
+
* OAuth2 Client ID of your Tailor Platform application.
|
|
157
|
+
*/
|
|
158
|
+
clientId: string;
|
|
159
|
+
/**
|
|
160
|
+
* GraphQL query to fetch the current authenticated user.
|
|
161
|
+
*
|
|
162
|
+
* The result of this query should return the user object.
|
|
163
|
+
* If you override `AuthRegister["user"]`, make sure to have the fields match your custom user type.
|
|
164
|
+
*
|
|
165
|
+
* @defaults
|
|
166
|
+
* ```graphql
|
|
167
|
+
* query {
|
|
168
|
+
* me {
|
|
169
|
+
* id
|
|
170
|
+
* email
|
|
171
|
+
* name
|
|
172
|
+
* }
|
|
173
|
+
* }
|
|
174
|
+
* ```
|
|
175
|
+
*/
|
|
176
|
+
meQuery?: string | DocumentNode;
|
|
177
|
+
/**
|
|
178
|
+
* Redirect URI after login is successful.
|
|
179
|
+
*
|
|
180
|
+
* @defaults `window.location.origin`
|
|
181
|
+
*/
|
|
182
|
+
redirectUri?: string;
|
|
183
|
+
/**
|
|
184
|
+
* Enable automatic login on initialization.
|
|
185
|
+
*/
|
|
186
|
+
autoLogin?: boolean;
|
|
187
|
+
/**
|
|
188
|
+
* Guard UI component to show when loading or unauthenticated.
|
|
189
|
+
*
|
|
190
|
+
* If not provided, children will be just rendered in any auth state.
|
|
191
|
+
*/
|
|
192
|
+
guardComponent?: () => React.ReactNode;
|
|
193
|
+
};
|
|
194
|
+
|
|
195
|
+
/**
|
|
196
|
+
* Registerable interface for type extension via module augmentation.
|
|
197
|
+
*
|
|
198
|
+
* @example
|
|
199
|
+
* // In your project's TypeScript file (e.g., app-shell.d.ts, App.tsx, etc.)
|
|
200
|
+
* declare module "@tailor-platform/app-shell" {
|
|
201
|
+
* interface AuthRegister {
|
|
202
|
+
* user: {
|
|
203
|
+
* id: string;
|
|
204
|
+
* email: string;
|
|
205
|
+
* name?: string;
|
|
206
|
+
* role: "admin" | "user";
|
|
207
|
+
* organizationId: string;
|
|
208
|
+
* }
|
|
209
|
+
* }
|
|
210
|
+
* }
|
|
211
|
+
*/
|
|
212
|
+
export declare interface AuthRegister {
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
declare type CommonModuleProps = {
|
|
216
|
+
/**
|
|
217
|
+
* Resource associated to the module.
|
|
218
|
+
*/
|
|
219
|
+
resources: Array<Resource>;
|
|
220
|
+
meta: CommonProps["meta"] & {
|
|
221
|
+
icon?: ReactNode;
|
|
222
|
+
};
|
|
223
|
+
};
|
|
224
|
+
|
|
225
|
+
declare type CommonPageResource = {
|
|
226
|
+
path: string;
|
|
227
|
+
type: "component";
|
|
228
|
+
component: () => ReactNode;
|
|
229
|
+
meta: {
|
|
230
|
+
title: LocalizedString;
|
|
231
|
+
icon?: ReactNode;
|
|
232
|
+
};
|
|
233
|
+
};
|
|
234
|
+
|
|
235
|
+
declare type CommonProps = {
|
|
236
|
+
/**
|
|
237
|
+
* Path of the resource.
|
|
238
|
+
*
|
|
239
|
+
* The path will be used to generate the URL for the resource.
|
|
240
|
+
* This also supports dynamic parameters using the syntax `:paramName`.
|
|
241
|
+
*/
|
|
242
|
+
path: string;
|
|
243
|
+
/**
|
|
244
|
+
* Metadata for the resource.
|
|
245
|
+
*/
|
|
246
|
+
meta?: ResourceMetaProps;
|
|
247
|
+
};
|
|
248
|
+
|
|
249
|
+
export declare const DefaultSidebar: (props: DefaultSidebarProps) => JSX.Element;
|
|
250
|
+
|
|
251
|
+
declare type DefaultSidebarProps = {
|
|
252
|
+
header?: React.ReactNode;
|
|
253
|
+
footer?: React.ReactNode;
|
|
254
|
+
};
|
|
255
|
+
|
|
256
|
+
/**
|
|
257
|
+
* Default user type when no custom user type is registered.
|
|
258
|
+
*
|
|
259
|
+
* You can extend this type via module augmentation:
|
|
260
|
+
* @example
|
|
261
|
+
* declare module "@tailor-platform/app-shell" {
|
|
262
|
+
* interface Register {
|
|
263
|
+
* user: DefaultUser & {
|
|
264
|
+
* role: "admin" | "user";
|
|
265
|
+
* organizationId: string;
|
|
266
|
+
* }
|
|
267
|
+
* }
|
|
268
|
+
* }
|
|
269
|
+
*/
|
|
270
|
+
export declare type DefaultUser = {
|
|
271
|
+
id: string;
|
|
272
|
+
email: string;
|
|
273
|
+
name?: string;
|
|
274
|
+
};
|
|
275
|
+
|
|
276
|
+
/**
|
|
277
|
+
* Defines internationalization labels for multiple locales.
|
|
278
|
+
*
|
|
279
|
+
* `en` locale is required as the default locale.
|
|
280
|
+
* Labels can be either static strings or dynamic functions that take props.
|
|
281
|
+
*
|
|
282
|
+
* @example
|
|
283
|
+
* ```tsx
|
|
284
|
+
* import { defineI18nLabels } from "@tailor-platform/app-shell";
|
|
285
|
+
*
|
|
286
|
+
* export const labels = defineI18nLabels({
|
|
287
|
+
* en: {
|
|
288
|
+
* hello: "Hello",
|
|
289
|
+
* welcome: (props: { name: string }) => `Welcome, ${props.name}!`,
|
|
290
|
+
* },
|
|
291
|
+
* ja: {
|
|
292
|
+
* hello: "こんにちは",
|
|
293
|
+
* welcome: (props: { name: string }) => `ようこそ、${props.name}さん!`,
|
|
294
|
+
* },
|
|
295
|
+
* });
|
|
296
|
+
*
|
|
297
|
+
* // Hook to get the translated label resolver function
|
|
298
|
+
* export const useT = labels.useT;
|
|
299
|
+
*
|
|
300
|
+
* // Usage in component
|
|
301
|
+
* const t = useT();
|
|
302
|
+
* t("hello"); // "Hello"
|
|
303
|
+
* t("welcome", { name: "John" }); // "Welcome, John!"
|
|
304
|
+
* ```
|
|
305
|
+
*/
|
|
306
|
+
export declare const defineI18nLabels: <const L extends Exclude<string, "en">, const Def extends Record<string, LabelValue>>(labels: {
|
|
307
|
+
en: Def;
|
|
308
|
+
} & { [K in L]: LabelDefinition<Def>; } & DynamicLocales<Def>) => {
|
|
309
|
+
/**
|
|
310
|
+
* Hook to get the translated label resolver function.
|
|
311
|
+
*
|
|
312
|
+
* @example
|
|
313
|
+
* ```tsx
|
|
314
|
+
* import { useT } from "./i18n-labels";
|
|
315
|
+
*
|
|
316
|
+
* const YourComponent = () => {
|
|
317
|
+
* const t = useT();
|
|
318
|
+
*
|
|
319
|
+
* return (
|
|
320
|
+
* <div>
|
|
321
|
+
* {t("staticLabel")}
|
|
322
|
+
* {t("dynamicLabel", { name: "John" })}
|
|
323
|
+
* </div>
|
|
324
|
+
* );
|
|
325
|
+
* }
|
|
326
|
+
* ```
|
|
327
|
+
*/
|
|
328
|
+
useT: () => <K extends keyof Def & string>(key: K, ...args: Def[K] extends (props: infer P) => string ? [props: P] : []) => string;
|
|
329
|
+
/**
|
|
330
|
+
* A function to get the translater for a specific label key.
|
|
331
|
+
* This is expected to be used in `meta.title` in module/resource definitions.
|
|
332
|
+
*
|
|
333
|
+
* Note: When using dynamic labels with props in meta.title, the props are
|
|
334
|
+
* bound at definition time (when calling labels.t), not at render time.
|
|
335
|
+
*
|
|
336
|
+
* @example
|
|
337
|
+
* ```tsx
|
|
338
|
+
* import { labels } from "./i18n-labels";
|
|
339
|
+
*
|
|
340
|
+
* const resource = defineResource({
|
|
341
|
+
* path: "example",
|
|
342
|
+
* meta: {
|
|
343
|
+
* title: labels.t("someLabelKey"),
|
|
344
|
+
* // or with props for dynamic labels
|
|
345
|
+
* title: labels.t("dynamicKey", { id: "123" }),
|
|
346
|
+
* },
|
|
347
|
+
* component: ExampleComponent,
|
|
348
|
+
* });
|
|
349
|
+
* ```
|
|
350
|
+
*/
|
|
351
|
+
t: <K extends keyof Def & string>(key: K, ...args: Def[K] extends (props: infer P) => string ? [props: P] : []) => LocalizedString;
|
|
352
|
+
};
|
|
353
|
+
|
|
354
|
+
/**
|
|
355
|
+
* Define a root-level resource that renders a React component.
|
|
356
|
+
*
|
|
357
|
+
* @example
|
|
358
|
+
* ```
|
|
359
|
+
* // Define a minimal resource
|
|
360
|
+
* defineReactResource({
|
|
361
|
+
* path: "custom-page",
|
|
362
|
+
* component: () => {
|
|
363
|
+
* return (
|
|
364
|
+
* <div>
|
|
365
|
+
* <p>This is a custom page.</p>
|
|
366
|
+
* </div>
|
|
367
|
+
* );
|
|
368
|
+
* },
|
|
369
|
+
* });
|
|
370
|
+
* ```
|
|
371
|
+
*/
|
|
372
|
+
export declare function defineModule(props: DefineModuleProps): Module;
|
|
373
|
+
|
|
374
|
+
declare type DefineModuleProps = CommonProps & CommonModuleProps & {
|
|
375
|
+
/**
|
|
376
|
+
* React component to render or redirect configuration
|
|
377
|
+
*
|
|
378
|
+
* @example
|
|
379
|
+
* ```tsx
|
|
380
|
+
* // Render a component
|
|
381
|
+
* component: (props) => <div>{props.title}</div>
|
|
382
|
+
*
|
|
383
|
+
* // Redirect to a resource
|
|
384
|
+
* component: redirectToResource("dashboard/overview")
|
|
385
|
+
* ```
|
|
386
|
+
*/
|
|
387
|
+
component: ((props: ResourceComponentProps) => ReactNode) | RedirectConfig;
|
|
388
|
+
/**
|
|
389
|
+
* Error boundary component for this module and its child resources.
|
|
390
|
+
* When an error occurs in this module or its resources, this component will render.
|
|
391
|
+
* Use the `useRouteError` hook to access error details within the component.
|
|
392
|
+
*/
|
|
393
|
+
errorBoundary?: ErrorBoundaryComponent;
|
|
394
|
+
};
|
|
395
|
+
|
|
396
|
+
/**
|
|
397
|
+
* Define a resource that renders a React component.
|
|
398
|
+
*
|
|
399
|
+
* This resource can be used as a sub-resource of a module or as a root-level resource.
|
|
400
|
+
*
|
|
401
|
+
* @example
|
|
402
|
+
* ```
|
|
403
|
+
* // Define a minimal resource
|
|
404
|
+
* defineResource({
|
|
405
|
+
* path: "custom-page",
|
|
406
|
+
* component: () => {
|
|
407
|
+
* return (
|
|
408
|
+
* <div>
|
|
409
|
+
* <p>This is a custom page.</p>
|
|
410
|
+
* </div>
|
|
411
|
+
* );
|
|
412
|
+
* },
|
|
413
|
+
* subResources: [
|
|
414
|
+
* defineResource({
|
|
415
|
+
* path: "sub-page",
|
|
416
|
+
* component: () => {
|
|
417
|
+
* return (
|
|
418
|
+
* <div>
|
|
419
|
+
* <p>This is a sub page.</p>
|
|
420
|
+
* </div>
|
|
421
|
+
* );
|
|
422
|
+
* },
|
|
423
|
+
* }),
|
|
424
|
+
* ]
|
|
425
|
+
* });
|
|
426
|
+
* ```
|
|
427
|
+
*
|
|
428
|
+
*/
|
|
429
|
+
export declare function defineResource(props: DefineResourceProps): Resource;
|
|
430
|
+
|
|
431
|
+
declare type DefineResourceProps = CommonProps & ReactResourceProps & {
|
|
432
|
+
/**
|
|
433
|
+
* Sub-resources of the resource.
|
|
434
|
+
*/
|
|
435
|
+
subResources?: Array<Resource>;
|
|
436
|
+
/**
|
|
437
|
+
* Error boundary component for this resource and its sub-resources.
|
|
438
|
+
* When an error occurs in this resource, this component will render.
|
|
439
|
+
* Overrides module-level or global error boundaries.
|
|
440
|
+
* Use the `useRouteError` hook to access error details within the component.
|
|
441
|
+
*/
|
|
442
|
+
errorBoundary?: ErrorBoundaryComponent;
|
|
443
|
+
};
|
|
444
|
+
|
|
445
|
+
declare type DynamicLocales<Def extends Record<string, LabelValue>> = {
|
|
446
|
+
[locale: string]: Partial<LabelDefinition<Def>> | undefined;
|
|
447
|
+
};
|
|
448
|
+
|
|
449
|
+
/**
|
|
450
|
+
* Error boundary element type for route error handling.
|
|
451
|
+
*
|
|
452
|
+
* Pass a JSX element that will render when an error occurs.
|
|
453
|
+
* Use the `useRouteError` hook from react-router to access the error.
|
|
454
|
+
*
|
|
455
|
+
* @example
|
|
456
|
+
* ```tsx
|
|
457
|
+
* import { useRouteError } from "@tailor-platform/app-shell";
|
|
458
|
+
*
|
|
459
|
+
* const MyErrorBoundary = () => {
|
|
460
|
+
* const error = useRouteError() as Error;
|
|
461
|
+
* return <div>Error: {error.message}</div>;
|
|
462
|
+
* };
|
|
463
|
+
*
|
|
464
|
+
* // In config:
|
|
465
|
+
* errorBoundary: <MyErrorBoundary />
|
|
466
|
+
* // Or with props:
|
|
467
|
+
* errorBoundary: <MyErrorBoundary theme="dark" onReport={handleReport} />
|
|
468
|
+
* ```
|
|
469
|
+
*/
|
|
470
|
+
export declare type ErrorBoundaryComponent = ReactNode;
|
|
471
|
+
|
|
472
|
+
export declare type I18nLabels<Def extends Record<string, LabelValue> = Record<string, LabelValue>, L extends string = never> = {
|
|
473
|
+
en: Def;
|
|
474
|
+
} & {
|
|
475
|
+
[K in L]: LabelDefinition<Def>;
|
|
476
|
+
} & DynamicLocales<Def>;
|
|
477
|
+
|
|
478
|
+
/**
|
|
479
|
+
* Ensures that other locales have the same label structure as the base definition.
|
|
480
|
+
* For dynamic labels (functions), the props type must match.
|
|
481
|
+
*/
|
|
482
|
+
declare type LabelDefinition<Def extends Record<string, LabelValue>> = {
|
|
483
|
+
[K in keyof Def]: Def[K] extends (props: infer P) => string ? (props: P) => string : string;
|
|
484
|
+
};
|
|
485
|
+
|
|
486
|
+
/**
|
|
487
|
+
* Label value can be either a static string or a dynamic function that takes props.
|
|
488
|
+
*/
|
|
489
|
+
declare type LabelValue = string | ((props: any) => string);
|
|
490
|
+
|
|
491
|
+
export { Link }
|
|
492
|
+
|
|
493
|
+
declare type LocalizedString = string | ((locale: string) => string);
|
|
494
|
+
|
|
495
|
+
/**
|
|
496
|
+
* A resource that can be included in the root-level content in the navigation.
|
|
497
|
+
*/
|
|
498
|
+
declare type Module = Omit<CommonPageResource, "meta"> & {
|
|
499
|
+
_type: "module";
|
|
500
|
+
meta: CommonPageResource["meta"] & {
|
|
501
|
+
icon?: ReactNode;
|
|
502
|
+
menuItemClickable: boolean;
|
|
503
|
+
};
|
|
504
|
+
resources: Array<Resource>;
|
|
505
|
+
loader?: () => Response;
|
|
506
|
+
errorBoundary: ErrorBoundaryComponent;
|
|
507
|
+
};
|
|
508
|
+
|
|
509
|
+
declare type Modules = Array<Module>;
|
|
510
|
+
|
|
511
|
+
declare type NavChildItem = {
|
|
512
|
+
title: string;
|
|
513
|
+
url: string;
|
|
514
|
+
};
|
|
515
|
+
|
|
516
|
+
declare type NavItem = {
|
|
517
|
+
title: string;
|
|
518
|
+
url: string | undefined;
|
|
519
|
+
icon: ReactNode;
|
|
520
|
+
isActive?: boolean;
|
|
521
|
+
items?: Array<NavChildItem>;
|
|
522
|
+
};
|
|
523
|
+
|
|
524
|
+
declare type ReactResourceProps = {
|
|
525
|
+
/**
|
|
526
|
+
* React component to render.
|
|
527
|
+
*/
|
|
528
|
+
component: (props: ResourceComponentProps) => ReactNode;
|
|
529
|
+
};
|
|
530
|
+
|
|
531
|
+
/**
|
|
532
|
+
* Redirect configuration for module or root component
|
|
533
|
+
*/
|
|
534
|
+
declare type RedirectConfig = {
|
|
535
|
+
/**
|
|
536
|
+
* Path to redirect to (under /resources/)
|
|
537
|
+
*/
|
|
538
|
+
redirectTo: string;
|
|
539
|
+
};
|
|
540
|
+
|
|
541
|
+
/**
|
|
542
|
+
* Helper function to define a redirect to a resource path
|
|
543
|
+
*
|
|
544
|
+
* @param path - Path under `/resources/` (e.g., "dashboard/overview")
|
|
545
|
+
*
|
|
546
|
+
* @example
|
|
547
|
+
* ```tsx
|
|
548
|
+
* defineModule({
|
|
549
|
+
* path: "dashboard",
|
|
550
|
+
* component: redirectToResource("dashboard/overview"),
|
|
551
|
+
* resources: [overviewResource],
|
|
552
|
+
* });
|
|
553
|
+
* ```
|
|
554
|
+
*/
|
|
555
|
+
export declare function redirectToResource(path: string): RedirectConfig;
|
|
556
|
+
|
|
557
|
+
/**
|
|
558
|
+
* A resource that can be included in the sub-content in the root resource.
|
|
559
|
+
*
|
|
560
|
+
* This resource does not have `category` metadata.
|
|
561
|
+
*/
|
|
562
|
+
declare type Resource = CommonPageResource & {
|
|
563
|
+
_type: "resource";
|
|
564
|
+
subResources?: Array<Resource>;
|
|
565
|
+
errorBoundary: ErrorBoundaryComponent;
|
|
566
|
+
};
|
|
567
|
+
|
|
568
|
+
export declare type ResourceComponentProps = {
|
|
569
|
+
title: string;
|
|
570
|
+
icon?: ReactNode;
|
|
571
|
+
resources?: Array<Resource>;
|
|
572
|
+
};
|
|
573
|
+
|
|
574
|
+
declare type ResourceMetaProps = {
|
|
575
|
+
/**
|
|
576
|
+
* Title of the resource used in navigation.
|
|
577
|
+
*
|
|
578
|
+
* If not provided, the title will be generated from the path.
|
|
579
|
+
*/
|
|
580
|
+
title?: LocalizedString;
|
|
581
|
+
icon?: ReactNode;
|
|
582
|
+
/**
|
|
583
|
+
* Custom breadcrumb segment title for this resource. Can be a string or a function.
|
|
584
|
+
*/
|
|
585
|
+
breadcrumbTitle?: string | ((segment: string) => string);
|
|
586
|
+
};
|
|
587
|
+
|
|
588
|
+
declare type RootConfiguration = {
|
|
589
|
+
modules: Modules;
|
|
590
|
+
settingsResources: Resource[];
|
|
591
|
+
basePath?: string;
|
|
592
|
+
errorBoundary: ErrorBoundaryComponent;
|
|
593
|
+
locale: string;
|
|
594
|
+
};
|
|
595
|
+
|
|
596
|
+
export declare const SidebarLayout: (props: SidebarLayoutProps) => JSX.Element;
|
|
597
|
+
|
|
598
|
+
declare type SidebarLayoutProps = {
|
|
599
|
+
children?: (props: {
|
|
600
|
+
Outlet: () => React.ReactNode;
|
|
601
|
+
}) => React.ReactNode;
|
|
602
|
+
sidebar?: React.ReactNode;
|
|
603
|
+
};
|
|
604
|
+
|
|
605
|
+
declare type Theme = "dark" | "light" | "system";
|
|
606
|
+
|
|
607
|
+
declare type ThemeProviderState = {
|
|
608
|
+
theme: Theme;
|
|
609
|
+
resolvedTheme: Omit<Theme, "system">;
|
|
610
|
+
setTheme: (theme: Theme) => void;
|
|
611
|
+
};
|
|
612
|
+
|
|
613
|
+
export declare const useAppShell: () => AppShellContextType;
|
|
614
|
+
|
|
615
|
+
export declare const useAuth: () => AuthContextType;
|
|
616
|
+
|
|
617
|
+
export { useLocation }
|
|
618
|
+
|
|
619
|
+
export { useNavigate }
|
|
620
|
+
|
|
621
|
+
export { useParams }
|
|
622
|
+
|
|
623
|
+
/**
|
|
624
|
+
* User type that can be extended via the AuthRegister interface.
|
|
625
|
+
*
|
|
626
|
+
* If `AuthRegister["user"]` is defined, it will be used as the User type.
|
|
627
|
+
* Otherwise, the DefaultUser type will be used.
|
|
628
|
+
*/
|
|
629
|
+
declare type User = AuthRegister extends {
|
|
630
|
+
user: infer TUser;
|
|
631
|
+
} ? TUser : DefaultUser;
|
|
632
|
+
|
|
633
|
+
export { useRouteError }
|
|
634
|
+
|
|
635
|
+
export { useSearchParams }
|
|
636
|
+
|
|
637
|
+
export declare const useTheme: () => ThemeProviderState;
|
|
638
|
+
|
|
639
|
+
export { }
|