@spacego/fe-components 0.0.1-alpha.1 → 0.0.1-alpha.3
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/lib/fe-layouts/auth-layout/index.js +1 -1
- package/lib/fe-layouts/layout.js +8 -8
- package/lib/index.js +23 -21
- package/lib/store/modules/layout-config.store.js +1 -1
- package/lib/store/modules/theme.store.js +1 -1
- package/lib/types/index.d.ts +2 -0
- package/lib/types/router/index.d.ts +1 -1
- package/package.json +9 -1
- package/src/assets/styles/animate.css +0 -62
- package/src/assets/styles/index.css +0 -49
- package/src/assets/svg/chrome-bg-after.svg +0 -1
- package/src/assets/svg/chrome-bg-before.svg +0 -1
- package/src/assets/svg/icon-arrows-right.svg +0 -1
- package/src/assets/svg/icon-bell.svg +0 -1
- package/src/assets/svg/icon-custom.svg +0 -1
- package/src/assets/svg/icon-sun-moon.svg +0 -1
- package/src/assets/svg/icon-system.svg +0 -1
- package/src/assets/svg/loading.svg +0 -13
- package/src/assets/svg/login-view.svg +0 -193
- package/src/config/constants.ts +0 -19
- package/src/config/index.ts +0 -2
- package/src/config/theme.ts +0 -20
- package/src/fe-layouts/auth-layout/index.scss +0 -34
- package/src/fe-layouts/auth-layout/index.tsx +0 -121
- package/src/fe-layouts/basics-layout/components/basics-layout/header.tsx +0 -148
- package/src/fe-layouts/basics-layout/components/basics-layout/setting-custom-color.tsx +0 -52
- package/src/fe-layouts/basics-layout/components/basics-layout/setting-drawer.tsx +0 -165
- package/src/fe-layouts/basics-layout/components/basics-layout/sidebar.tsx +0 -88
- package/src/fe-layouts/basics-layout/components/basics-layout/tabs.tsx +0 -94
- package/src/fe-layouts/basics-layout/components/utils/index.ts +0 -142
- package/src/fe-layouts/basics-layout/index.scss +0 -110
- package/src/fe-layouts/basics-layout/index.tsx +0 -207
- package/src/fe-layouts/blank-layout/index.tsx +0 -12
- package/src/fe-layouts/context/context.ts +0 -11
- package/src/fe-layouts/context/global-context.d.ts +0 -241
- package/src/fe-layouts/context/global-context.provider.tsx +0 -81
- package/src/fe-layouts/context/index.ts +0 -10
- package/src/fe-layouts/index.ts +0 -13
- package/src/fe-layouts/layout.tsx +0 -74
- package/src/hooks/index.ts +0 -1
- package/src/hooks/use-auth.hook.ts +0 -54
- package/src/index.ts +0 -21
- package/src/router/index.ts +0 -110
- package/src/router/permission.tsx +0 -134
- package/src/router/routes.tsx +0 -94
- package/src/router/utils.ts +0 -283
- package/src/store/index.ts +0 -9
- package/src/store/modules/layout-config.store.ts +0 -343
- package/src/store/modules/theme.store.ts +0 -99
- package/src/typings/index.d.ts +0 -59
- package/src/typings/shims-axios.d.ts +0 -38
- package/src/utils/icon.tsx +0 -32
- package/src/utils/index.ts +0 -9
- package/src/utils/theme.ts +0 -219
- package/tsconfig.json +0 -28
- package/vite.config.ts +0 -85
|
@@ -1,241 +0,0 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* @Author: dushuai
|
|
3
|
-
* @Date: 2026-01-30 23:02:55
|
|
4
|
-
* @LastEditors: dushuai
|
|
5
|
-
* @LastEditTime: 2026-02-01 12:45:00
|
|
6
|
-
* @description: global context
|
|
7
|
-
*/
|
|
8
|
-
import { MenuProps } from 'antd';
|
|
9
|
-
import { ReactNode } from 'react';
|
|
10
|
-
import { RouteObject } from 'react-router-dom';
|
|
11
|
-
|
|
12
|
-
import { MenuItem } from '@/router';
|
|
13
|
-
|
|
14
|
-
export interface IUserInfo {
|
|
15
|
-
username?: string;
|
|
16
|
-
avatar?: string;
|
|
17
|
-
roleName?: string;
|
|
18
|
-
[key: string]: any;
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
export interface IGlobalContextProps {
|
|
22
|
-
/**
|
|
23
|
-
* @name 项目名称
|
|
24
|
-
*/
|
|
25
|
-
appName?: ReactNode;
|
|
26
|
-
/**
|
|
27
|
-
* @name 项目logo
|
|
28
|
-
*/
|
|
29
|
-
logo?: ReactNode;
|
|
30
|
-
/**
|
|
31
|
-
* @name 通知的reactNode
|
|
32
|
-
*/
|
|
33
|
-
noticeRender?: ReactNode;
|
|
34
|
-
/**
|
|
35
|
-
* @name 项目说明
|
|
36
|
-
*/
|
|
37
|
-
description?: ReactNode;
|
|
38
|
-
/**
|
|
39
|
-
* @name 项目详细说明
|
|
40
|
-
*/
|
|
41
|
-
descriptionDetail?: ReactNode;
|
|
42
|
-
/**
|
|
43
|
-
* @name Copyright
|
|
44
|
-
*/
|
|
45
|
-
copyright?: ReactNode;
|
|
46
|
-
/**
|
|
47
|
-
* @name 用户菜单
|
|
48
|
-
*/
|
|
49
|
-
userMenuItems?: MenuProps['items'];
|
|
50
|
-
/**
|
|
51
|
-
* @name 用户信息
|
|
52
|
-
*/
|
|
53
|
-
userInfo?: IUserInfo;
|
|
54
|
-
/**
|
|
55
|
-
* @name 侧边栏前置内容
|
|
56
|
-
*/
|
|
57
|
-
sidebarBefore?: ReactNode;
|
|
58
|
-
/**
|
|
59
|
-
* @name 侧边栏后置内容
|
|
60
|
-
*/
|
|
61
|
-
sidebarAfter?: ReactNode;
|
|
62
|
-
/**
|
|
63
|
-
* @name tabs前置内容
|
|
64
|
-
*/
|
|
65
|
-
tabsBefore?: ReactNode;
|
|
66
|
-
/**
|
|
67
|
-
* @name tabs后置内容
|
|
68
|
-
*/
|
|
69
|
-
tabsAfter?: ReactNode;
|
|
70
|
-
/**
|
|
71
|
-
* @name header按钮组render
|
|
72
|
-
*/
|
|
73
|
-
headerActionsRender?: ReactNode;
|
|
74
|
-
/**
|
|
75
|
-
* @name 搜索框render
|
|
76
|
-
*/
|
|
77
|
-
searchRender?: ReactNode;
|
|
78
|
-
/**
|
|
79
|
-
* @name 面包屑前置render
|
|
80
|
-
*/
|
|
81
|
-
breadcrumbBeforeRender?: ReactNode;
|
|
82
|
-
/**
|
|
83
|
-
* @name 登录凭证
|
|
84
|
-
*/
|
|
85
|
-
token?: string;
|
|
86
|
-
/**
|
|
87
|
-
* @name 菜单列表
|
|
88
|
-
*/
|
|
89
|
-
menus?: MenuItem[];
|
|
90
|
-
/**
|
|
91
|
-
* @name 路由配置
|
|
92
|
-
*/
|
|
93
|
-
routes?: RouteObject[];
|
|
94
|
-
}
|
|
95
|
-
|
|
96
|
-
export interface IGlobalContext {
|
|
97
|
-
/**
|
|
98
|
-
* @name 项目名称
|
|
99
|
-
*/
|
|
100
|
-
appName?: ReactNode;
|
|
101
|
-
/**
|
|
102
|
-
* @name 通知的reactNode
|
|
103
|
-
*/
|
|
104
|
-
noticeRender?: ReactNode;
|
|
105
|
-
/**
|
|
106
|
-
* @name 项目logo
|
|
107
|
-
*/
|
|
108
|
-
logo?: ReactNode;
|
|
109
|
-
/**
|
|
110
|
-
* @name 项目说明
|
|
111
|
-
*/
|
|
112
|
-
description?: ReactNode;
|
|
113
|
-
/**
|
|
114
|
-
* @name 项目详细说明
|
|
115
|
-
*/
|
|
116
|
-
descriptionDetail?: ReactNode;
|
|
117
|
-
/**
|
|
118
|
-
* @name Copyright
|
|
119
|
-
*/
|
|
120
|
-
copyright?: ReactNode;
|
|
121
|
-
/**
|
|
122
|
-
* @name 用户菜单
|
|
123
|
-
*/
|
|
124
|
-
userMenuItems?: MenuProps['items'];
|
|
125
|
-
/**
|
|
126
|
-
* @name 用户信息
|
|
127
|
-
*/
|
|
128
|
-
userInfo?: IUserInfo;
|
|
129
|
-
/**
|
|
130
|
-
* @name 设置项目名称
|
|
131
|
-
*/
|
|
132
|
-
setAppName: (name?: ReactNode) => void;
|
|
133
|
-
/**
|
|
134
|
-
* @name 设置通知的reactNode,用于在顶部通知图标点击显示通知
|
|
135
|
-
*/
|
|
136
|
-
setNoticeRender: (render?: ReactNode) => void;
|
|
137
|
-
/**
|
|
138
|
-
* @name 设置项目logo
|
|
139
|
-
*/
|
|
140
|
-
setLogo: (logo?: ReactNode) => void;
|
|
141
|
-
/**
|
|
142
|
-
* @name 设置项目说明
|
|
143
|
-
*/
|
|
144
|
-
setDescription: (description?: ReactNode) => void;
|
|
145
|
-
/**
|
|
146
|
-
* @name 设置项目详细说明
|
|
147
|
-
*/
|
|
148
|
-
setDescriptionDetail: (descriptionDetail?: ReactNode) => void;
|
|
149
|
-
/**
|
|
150
|
-
* @name 设置Copyright
|
|
151
|
-
*/
|
|
152
|
-
setCopyright: (copyright?: ReactNode) => void;
|
|
153
|
-
/**
|
|
154
|
-
* @name 设置用户菜单
|
|
155
|
-
*/
|
|
156
|
-
setUserMenuItems: (items?: MenuProps['items']) => void;
|
|
157
|
-
/**
|
|
158
|
-
* @name 设置用户信息
|
|
159
|
-
*/
|
|
160
|
-
setUserInfo: (info?: IUserInfo) => void;
|
|
161
|
-
/**
|
|
162
|
-
* @name 侧边栏前置内容
|
|
163
|
-
*/
|
|
164
|
-
sidebarBefore?: ReactNode;
|
|
165
|
-
/**
|
|
166
|
-
* @name 侧边栏后置内容
|
|
167
|
-
*/
|
|
168
|
-
sidebarAfter?: ReactNode;
|
|
169
|
-
/**
|
|
170
|
-
* @name tabs前置内容
|
|
171
|
-
*/
|
|
172
|
-
tabsBefore?: ReactNode;
|
|
173
|
-
/**
|
|
174
|
-
* @name tabs后置内容
|
|
175
|
-
*/
|
|
176
|
-
tabsAfter?: ReactNode;
|
|
177
|
-
/**
|
|
178
|
-
* @name header按钮组render
|
|
179
|
-
*/
|
|
180
|
-
headerActionsRender?: ReactNode;
|
|
181
|
-
/**
|
|
182
|
-
* @name 搜索框render
|
|
183
|
-
*/
|
|
184
|
-
searchRender?: ReactNode;
|
|
185
|
-
/**
|
|
186
|
-
* @name 面包屑前置render
|
|
187
|
-
*/
|
|
188
|
-
breadcrumbBeforeRender?: ReactNode;
|
|
189
|
-
/**
|
|
190
|
-
* @name 设置侧边栏前置内容
|
|
191
|
-
*/
|
|
192
|
-
setSidebarBefore: (content?: ReactNode) => void;
|
|
193
|
-
/**
|
|
194
|
-
* @name 设置侧边栏后置内容
|
|
195
|
-
*/
|
|
196
|
-
setSidebarAfter: (content?: ReactNode) => void;
|
|
197
|
-
/**
|
|
198
|
-
* @name 设置tabs前置内容
|
|
199
|
-
*/
|
|
200
|
-
setTabsBefore: (content?: ReactNode) => void;
|
|
201
|
-
/**
|
|
202
|
-
* @name 设置tabs后置内容
|
|
203
|
-
*/
|
|
204
|
-
setTabsAfter: (content?: ReactNode) => void;
|
|
205
|
-
/**
|
|
206
|
-
* @name 设置header按钮组render
|
|
207
|
-
*/
|
|
208
|
-
setHeaderActionsRender: (render?: ReactNode) => void;
|
|
209
|
-
/**
|
|
210
|
-
* @name 设置搜索框render
|
|
211
|
-
*/
|
|
212
|
-
setSearchRender: (render?: ReactNode) => void;
|
|
213
|
-
/**
|
|
214
|
-
* @name 设置面包屑前置render
|
|
215
|
-
*/
|
|
216
|
-
setBreadcrumbBeforeRender: (render?: ReactNode) => void;
|
|
217
|
-
/**
|
|
218
|
-
* @name 登录凭证
|
|
219
|
-
*/
|
|
220
|
-
token?: string;
|
|
221
|
-
/**
|
|
222
|
-
* @name 菜单列表
|
|
223
|
-
*/
|
|
224
|
-
menus?: MenuItem[];
|
|
225
|
-
/**
|
|
226
|
-
* @name 路由配置
|
|
227
|
-
*/
|
|
228
|
-
routes?: RouteObject[];
|
|
229
|
-
/**
|
|
230
|
-
* @name 设置登录凭证
|
|
231
|
-
*/
|
|
232
|
-
setToken: (token?: string) => void;
|
|
233
|
-
/**
|
|
234
|
-
* @name 设置菜单列表
|
|
235
|
-
*/
|
|
236
|
-
setMenus: (menus?: MenuItem[]) => void;
|
|
237
|
-
/**
|
|
238
|
-
* @name 设置路由配置
|
|
239
|
-
*/
|
|
240
|
-
setRoutes: (routes?: RouteObject[]) => void;
|
|
241
|
-
}
|
|
@@ -1,81 +0,0 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* @Author: dushuai
|
|
3
|
-
* @Date: 2026-01-30 23:57:35
|
|
4
|
-
* @LastEditors: dushuai
|
|
5
|
-
* @LastEditTime: 2026-02-01 12:50:00
|
|
6
|
-
* @description: 心平气和
|
|
7
|
-
*/
|
|
8
|
-
import type { MenuProps } from 'antd';
|
|
9
|
-
import { type ReactNode, useState } from 'react';
|
|
10
|
-
import type { RouteObject } from 'react-router-dom';
|
|
11
|
-
|
|
12
|
-
import type { MenuItem } from '@/router';
|
|
13
|
-
|
|
14
|
-
import { GlobalContext, type IGlobalContextProps, type IUserInfo } from '.';
|
|
15
|
-
|
|
16
|
-
export default function GlobalContextProvider(props: React.PropsWithChildren<IGlobalContextProps>) {
|
|
17
|
-
|
|
18
|
-
const [appName, setAppName] = useState<ReactNode | undefined>(props.appName);
|
|
19
|
-
const [logo, setLogo] = useState<ReactNode | undefined>(props.logo);
|
|
20
|
-
const [noticeRender, setNoticeRender] = useState<ReactNode | undefined>(props.noticeRender);
|
|
21
|
-
const [description, setDescription] = useState<ReactNode | undefined>(props.description);
|
|
22
|
-
const [descriptionDetail, setDescriptionDetail] = useState<ReactNode | undefined>(props.descriptionDetail);
|
|
23
|
-
const [copyright, setCopyright] = useState<ReactNode | undefined>(props.copyright);
|
|
24
|
-
const [userMenuItems, setUserMenuItems] = useState<MenuProps['items'] | undefined>(props.userMenuItems);
|
|
25
|
-
const [userInfo, setUserInfo] = useState<IUserInfo | undefined>(props.userInfo);
|
|
26
|
-
const [sidebarBefore, setSidebarBefore] = useState<ReactNode | undefined>(props.sidebarBefore);
|
|
27
|
-
const [sidebarAfter, setSidebarAfter] = useState<ReactNode | undefined>(props.sidebarAfter);
|
|
28
|
-
const [tabsBefore, setTabsBefore] = useState<ReactNode | undefined>(props.tabsBefore);
|
|
29
|
-
const [tabsAfter, setTabsAfter] = useState<ReactNode | undefined>(props.tabsAfter);
|
|
30
|
-
const [headerActionsRender, setHeaderActionsRender] = useState<ReactNode | undefined>(props.headerActionsRender);
|
|
31
|
-
const [searchRender, setSearchRender] = useState<ReactNode | undefined>(props.searchRender);
|
|
32
|
-
const [breadcrumbBeforeRender, setBreadcrumbBeforeRender] = useState<ReactNode | undefined>(props.breadcrumbBeforeRender);
|
|
33
|
-
const [token, setToken] = useState<string | undefined>(props.token);
|
|
34
|
-
const [menus, setMenus] = useState<MenuItem[] | undefined>(props.menus);
|
|
35
|
-
const [routes, setRoutes] = useState<RouteObject[] | undefined>(props.routes);
|
|
36
|
-
|
|
37
|
-
return (
|
|
38
|
-
<GlobalContext.Provider
|
|
39
|
-
value={{
|
|
40
|
-
appName,
|
|
41
|
-
logo,
|
|
42
|
-
noticeRender,
|
|
43
|
-
description,
|
|
44
|
-
descriptionDetail,
|
|
45
|
-
copyright,
|
|
46
|
-
userMenuItems,
|
|
47
|
-
userInfo,
|
|
48
|
-
sidebarBefore,
|
|
49
|
-
sidebarAfter,
|
|
50
|
-
tabsBefore,
|
|
51
|
-
tabsAfter,
|
|
52
|
-
headerActionsRender,
|
|
53
|
-
searchRender,
|
|
54
|
-
breadcrumbBeforeRender,
|
|
55
|
-
token,
|
|
56
|
-
menus,
|
|
57
|
-
routes,
|
|
58
|
-
setAppName,
|
|
59
|
-
setLogo,
|
|
60
|
-
setNoticeRender,
|
|
61
|
-
setDescription,
|
|
62
|
-
setDescriptionDetail,
|
|
63
|
-
setCopyright,
|
|
64
|
-
setUserMenuItems,
|
|
65
|
-
setUserInfo,
|
|
66
|
-
setSidebarBefore,
|
|
67
|
-
setSidebarAfter,
|
|
68
|
-
setTabsBefore,
|
|
69
|
-
setTabsAfter,
|
|
70
|
-
setHeaderActionsRender,
|
|
71
|
-
setSearchRender,
|
|
72
|
-
setBreadcrumbBeforeRender,
|
|
73
|
-
setToken,
|
|
74
|
-
setMenus,
|
|
75
|
-
setRoutes
|
|
76
|
-
}}
|
|
77
|
-
>
|
|
78
|
-
{props.children}
|
|
79
|
-
</GlobalContext.Provider>
|
|
80
|
-
);
|
|
81
|
-
}
|
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* @Author: dushuai
|
|
3
|
-
* @Date: 2026-01-30 23:00:18
|
|
4
|
-
* @LastEditors: dushuai
|
|
5
|
-
* @LastEditTime: 2026-02-01 01:53:57
|
|
6
|
-
* @description: global context
|
|
7
|
-
*/
|
|
8
|
-
export * from './context';
|
|
9
|
-
export * from './global-context.d';
|
|
10
|
-
export { default as GlobalContextProvider } from './global-context.provider';
|
package/src/fe-layouts/index.ts
DELETED
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* @Author: dushuai
|
|
3
|
-
* @Date: 2026-01-31 23:23:24
|
|
4
|
-
* @LastEditors: dushuai
|
|
5
|
-
* @LastEditTime: 2026-02-01 12:37:31
|
|
6
|
-
* @description: fe-layouts
|
|
7
|
-
*/
|
|
8
|
-
export { default as AuthLayout } from './auth-layout';
|
|
9
|
-
export { default as BasicsLayout } from './basics-layout';
|
|
10
|
-
export { default as BlankLayout } from './blank-layout';
|
|
11
|
-
export * from './context';
|
|
12
|
-
export type { IFeLayoutProps } from './layout';
|
|
13
|
-
export { default as FeLayout } from './layout';
|
|
@@ -1,74 +0,0 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* @Author: dushuai
|
|
3
|
-
* @Date: 2024-04-07 10:25:43
|
|
4
|
-
* @LastEditors: dushuai
|
|
5
|
-
* @LastEditTime: 2026-02-01 01:39:31
|
|
6
|
-
* @description: BasicsLayout
|
|
7
|
-
*/
|
|
8
|
-
import { useSelector } from '@spacego/zustand';
|
|
9
|
-
import { ConfigProvider, Spin, theme, type ThemeConfig } from 'antd';
|
|
10
|
-
import { useMemo } from 'react';
|
|
11
|
-
|
|
12
|
-
import { useLayoutConfigStore, useThemeStore } from '../';
|
|
13
|
-
import themeConfig from '../config/theme';
|
|
14
|
-
import { getRealTheme } from '../utils/theme';
|
|
15
|
-
import AuthLayout from './auth-layout';
|
|
16
|
-
import BasicsLayout from './basics-layout';
|
|
17
|
-
import BlankLayout from './blank-layout';
|
|
18
|
-
import { GlobalContextProvider } from './context';
|
|
19
|
-
|
|
20
|
-
type ComponentType = () => JSX.Element;
|
|
21
|
-
|
|
22
|
-
export interface IFeLayoutProps {
|
|
23
|
-
/**
|
|
24
|
-
* 布局类型,空白布局和后台布局
|
|
25
|
-
*/
|
|
26
|
-
layoutType: 'blank' | 'basic' | 'auth';
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
export default function FeLayout(props: IFeLayoutProps) {
|
|
30
|
-
const { layoutType } = props;
|
|
31
|
-
|
|
32
|
-
const { loadingConfig } = useLayoutConfigStore(useSelector(['loadingConfig']));
|
|
33
|
-
const { theme: themeMode, themeColor } = useThemeStore(useSelector(['theme', 'themeColor']));
|
|
34
|
-
|
|
35
|
-
const sysTheme: Partial<ThemeConfig> = useMemo(() => {
|
|
36
|
-
// 获取实际主题(system 会转换为 light/dark)
|
|
37
|
-
const realTheme = getRealTheme(themeMode);
|
|
38
|
-
return {
|
|
39
|
-
cssVar: {
|
|
40
|
-
prefix: 'ant'
|
|
41
|
-
}, // 启用 CSS 变量模式,生成 --ant-color-primary 等变量
|
|
42
|
-
algorithm: realTheme === 'dark' ? theme.darkAlgorithm : theme.defaultAlgorithm,
|
|
43
|
-
token: {
|
|
44
|
-
colorPrimary: themeColor,
|
|
45
|
-
...themeConfig.token
|
|
46
|
-
},
|
|
47
|
-
components: {
|
|
48
|
-
...themeConfig.components
|
|
49
|
-
}
|
|
50
|
-
};
|
|
51
|
-
}, [themeMode, themeColor]);
|
|
52
|
-
|
|
53
|
-
const ComponentMap = new Map<IFeLayoutProps['layoutType'], ComponentType>([
|
|
54
|
-
['blank', BlankLayout],
|
|
55
|
-
['basic', BasicsLayout],
|
|
56
|
-
['auth', AuthLayout]
|
|
57
|
-
]);
|
|
58
|
-
const Component = ComponentMap.get(layoutType);
|
|
59
|
-
|
|
60
|
-
return (
|
|
61
|
-
<ConfigProvider theme={sysTheme}>
|
|
62
|
-
<GlobalContextProvider>
|
|
63
|
-
<Spin
|
|
64
|
-
spinning={loadingConfig.show && layoutType !== 'basic'}
|
|
65
|
-
wrapperClassName="spin-wrapper-full"
|
|
66
|
-
>
|
|
67
|
-
{
|
|
68
|
-
Component && <Component key={layoutType} />
|
|
69
|
-
}
|
|
70
|
-
</Spin>
|
|
71
|
-
</GlobalContextProvider>
|
|
72
|
-
</ConfigProvider>
|
|
73
|
-
);
|
|
74
|
-
}
|
package/src/hooks/index.ts
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export * from './use-auth.hook';
|
|
@@ -1,54 +0,0 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* @Author: dushuai
|
|
3
|
-
* @Date: 2026-01-25 21:30:00
|
|
4
|
-
* @LastEditors: dushuai
|
|
5
|
-
* @LastEditTime: 2026-02-01 01:46:53
|
|
6
|
-
* @description: 登录和退出登录的 hook
|
|
7
|
-
*/
|
|
8
|
-
import { useFetcher, useSearchParams, useSubmit } from 'react-router-dom';
|
|
9
|
-
|
|
10
|
-
import { useLayoutConfigStore } from '@/store';
|
|
11
|
-
|
|
12
|
-
import { useGlobal } from '../fe-layouts/context';
|
|
13
|
-
|
|
14
|
-
/**
|
|
15
|
-
* 登录和退出登录的 hook
|
|
16
|
-
* @returns
|
|
17
|
-
*/
|
|
18
|
-
export function useAuth() {
|
|
19
|
-
const submit = useSubmit();
|
|
20
|
-
const fetcher = useFetcher();
|
|
21
|
-
const [searchParams] = useSearchParams();
|
|
22
|
-
const { setToken } = useGlobal();
|
|
23
|
-
|
|
24
|
-
/**
|
|
25
|
-
* 登录
|
|
26
|
-
* @param token 登录 token
|
|
27
|
-
* @param redirectTo 登录成功后跳转的路径,默认为 '/' 或从 URL 参数 'from' 获取
|
|
28
|
-
*/
|
|
29
|
-
const login = (token: string, redirectTo?: string) => {
|
|
30
|
-
const targetPath = redirectTo || searchParams.get('from') || '/';
|
|
31
|
-
submit({ token, redirectTo: targetPath }, { method: 'post', replace: true });
|
|
32
|
-
};
|
|
33
|
-
|
|
34
|
-
/**
|
|
35
|
-
* 退出登录
|
|
36
|
-
*/
|
|
37
|
-
const logout = () => {
|
|
38
|
-
// 1. 调用 GlobalContext 中的 setToken 清空 token
|
|
39
|
-
setToken(void 0);
|
|
40
|
-
|
|
41
|
-
// 2. 触发后端的 logout action (如果需要)
|
|
42
|
-
fetcher.submit(null, { action: '/logout', method: 'post' });
|
|
43
|
-
|
|
44
|
-
// 3. 重置布局配置等其他状态
|
|
45
|
-
setTimeout(() => {
|
|
46
|
-
useLayoutConfigStore.getState().RESET();
|
|
47
|
-
}, 300);
|
|
48
|
-
};
|
|
49
|
-
|
|
50
|
-
return {
|
|
51
|
-
login,
|
|
52
|
-
logout
|
|
53
|
-
};
|
|
54
|
-
}
|
package/src/index.ts
DELETED
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* @Author: dushuai
|
|
3
|
-
* @Date: 2026-01-31 23:07:12
|
|
4
|
-
* @LastEditors: dushuai
|
|
5
|
-
* @LastEditTime: 2026-02-01 12:38:34
|
|
6
|
-
* @description: export
|
|
7
|
-
*/
|
|
8
|
-
/**------------------------------------------- utils ------------------------------------------- */
|
|
9
|
-
export * from './utils';
|
|
10
|
-
|
|
11
|
-
/**------------------------------------------- store ------------------------------------------- */
|
|
12
|
-
export * from './store';
|
|
13
|
-
|
|
14
|
-
/**------------------------------------------- config ------------------------------------------- */
|
|
15
|
-
export * from './config';
|
|
16
|
-
|
|
17
|
-
/**------------------------------------------- router ------------------------------------------- */
|
|
18
|
-
export * from './router';
|
|
19
|
-
|
|
20
|
-
/**------------------------------------------- components ------------------------------------------- */
|
|
21
|
-
export * from './fe-layouts';
|
package/src/router/index.ts
DELETED
|
@@ -1,110 +0,0 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* @Author: dushuai
|
|
3
|
-
* @Date: 2024-03-29 16:05:16
|
|
4
|
-
* @LastEditors: dushuai
|
|
5
|
-
* @LastEditTime: 2026-02-01 01:14:48
|
|
6
|
-
* @description: router
|
|
7
|
-
*/
|
|
8
|
-
import type { ComponentType } from 'react';
|
|
9
|
-
import { createBrowserRouter, type RouteObject } from 'react-router-dom';
|
|
10
|
-
|
|
11
|
-
import { createPermissionHelpers, type TokenHelpers } from './permission';
|
|
12
|
-
import { createDefaultRoutes } from './routes';
|
|
13
|
-
import { type TModule } from './utils';
|
|
14
|
-
|
|
15
|
-
export interface CreateRouterOptions {
|
|
16
|
-
/** 页面模块集合 import.meta.glob的结果 */
|
|
17
|
-
modules: TModule;
|
|
18
|
-
/** token 操作方法 */
|
|
19
|
-
token: TokenHelpers;
|
|
20
|
-
/** 基础布局组件 */
|
|
21
|
-
BaseLayout: ComponentType<any>;
|
|
22
|
-
/** 外部传入的路由配置(第一层,RouteObject结构) */
|
|
23
|
-
routes?: RouteObject[];
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
/**
|
|
27
|
-
* 创建路由器配置(第一层)
|
|
28
|
-
* @param options
|
|
29
|
-
* @returns { routes, permissionHelpers }
|
|
30
|
-
*/
|
|
31
|
-
export function createRouter(options: CreateRouterOptions) {
|
|
32
|
-
const { modules, token, BaseLayout, routes: customRoutes = [] } = options;
|
|
33
|
-
|
|
34
|
-
// 1. 初始化权限帮助函数
|
|
35
|
-
const permissionHelpers = createPermissionHelpers(token);
|
|
36
|
-
|
|
37
|
-
// 2. 创建默认路由(登录、注册、错误页等)
|
|
38
|
-
const defaultRoutes = createDefaultRoutes(modules, permissionHelpers, BaseLayout);
|
|
39
|
-
|
|
40
|
-
// 3. 合并路由
|
|
41
|
-
const finalRoutes = mergeRoutes(defaultRoutes, customRoutes);
|
|
42
|
-
|
|
43
|
-
return {
|
|
44
|
-
/** 最终合并后的路由配置 */
|
|
45
|
-
routes: finalRoutes,
|
|
46
|
-
/** 权限帮助函数,包含 ProtectedLoader 等,用于外部调用 processRoutes */
|
|
47
|
-
permissionHelpers
|
|
48
|
-
};
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
/**
|
|
52
|
-
* 合并路由(支持 id 去重,优先使用 customRoutes)
|
|
53
|
-
* @param defaultRoutes 默认路由
|
|
54
|
-
* @param customRoutes 自定义路由(已处理为 RouteObject[])
|
|
55
|
-
* @returns 合并后的路由数组
|
|
56
|
-
*/
|
|
57
|
-
function mergeRoutes(defaultRoutes: RouteObject[], customRoutes: RouteObject[]): RouteObject[] {
|
|
58
|
-
const routeMap = new Map<string, RouteObject>();
|
|
59
|
-
|
|
60
|
-
// 先放入 defaultRoutes
|
|
61
|
-
defaultRoutes.forEach(route => {
|
|
62
|
-
if(route.id) {
|
|
63
|
-
routeMap.set(route.id, route);
|
|
64
|
-
}
|
|
65
|
-
});
|
|
66
|
-
|
|
67
|
-
// 再放入 customRoutes,如果有相同 id 则覆盖(除了 root 特殊处理)
|
|
68
|
-
customRoutes.forEach(route => {
|
|
69
|
-
if(route.id) {
|
|
70
|
-
if(route.id === 'root' && routeMap.has('root')) {
|
|
71
|
-
// 特殊处理 root 路由:合并 children
|
|
72
|
-
const defaultRoot = routeMap.get('root')!;
|
|
73
|
-
const customRoot = route;
|
|
74
|
-
|
|
75
|
-
// 合并 children
|
|
76
|
-
const mergedChildren = [
|
|
77
|
-
...(defaultRoot.children || []),
|
|
78
|
-
...(customRoot.children || [])
|
|
79
|
-
];
|
|
80
|
-
|
|
81
|
-
routeMap.set('root', {
|
|
82
|
-
...defaultRoot,
|
|
83
|
-
...customRoot, // 属性以 customRoot 为准
|
|
84
|
-
children: mergedChildren
|
|
85
|
-
} as RouteObject);
|
|
86
|
-
} else {
|
|
87
|
-
// 其他路由直接覆盖
|
|
88
|
-
routeMap.set(route.id, route as RouteObject);
|
|
89
|
-
}
|
|
90
|
-
} else {
|
|
91
|
-
// 没有 id 的路由,直接添加?
|
|
92
|
-
// 为了安全起见,这里可以考虑生成一个临时 id 或者直接追加,但 React Router 建议有 id
|
|
93
|
-
}
|
|
94
|
-
});
|
|
95
|
-
|
|
96
|
-
return Array.from(routeMap.values());
|
|
97
|
-
}
|
|
98
|
-
|
|
99
|
-
/**
|
|
100
|
-
* 生成路由表
|
|
101
|
-
* @param routes 路由数组
|
|
102
|
-
* @returns
|
|
103
|
-
*/
|
|
104
|
-
export function generateRouter(routes: RouteObject[]) {
|
|
105
|
-
return createBrowserRouter(routes);
|
|
106
|
-
}
|
|
107
|
-
|
|
108
|
-
export * from './permission';
|
|
109
|
-
export * from './routes';
|
|
110
|
-
export * from './utils';
|