Skip to content

Commit dec3a96

Browse files
committed
fix: repair auth and table flows
1 parent 7522fb5 commit dec3a96

13 files changed

Lines changed: 235 additions & 40 deletions

File tree

config/routes.ts

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,26 @@ export const routes = [
1212
icon: 'HomeFilled',
1313
component: './Home',
1414
},
15+
{
16+
name: 'login',
17+
path: '/login',
18+
component: './Login',
19+
hideInMenu: true,
20+
},
21+
{
22+
name: 'access',
23+
path: '/access',
24+
icon: 'LockOutlined',
25+
component: './Access',
26+
access: 'canSeeAdmin',
27+
},
28+
{
29+
name: 'table',
30+
path: '/table',
31+
icon: 'TableOutlined',
32+
component: './Table',
33+
access: 'canSeeAdmin',
34+
},
1535
{
1636
name: 'feature',
1737
path: '/feature',

mock/userAPI.ts

Lines changed: 55 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,19 +1,69 @@
1-
const users = [
2-
{ id: 0, name: 'Umi', nickName: 'U', gender: 'MALE' },
3-
{ id: 1, name: 'Fish', nickName: 'B', gender: 'FEMALE' },
1+
let users = [
2+
{ id: '0', name: 'Umi', nickName: 'U', gender: 'MALE', email: 'umi@example.com' },
3+
{ id: '1', name: 'Fish', nickName: 'B', gender: 'FEMALE', email: 'fish@example.com' },
44
];
55

66
export default {
77
'GET /api/v1/queryUserList': (req: any, res: any) => {
8+
const { current = 1, pageSize = 20, keyword } = req.query || {};
9+
const list = keyword
10+
? users.filter((user) => user.name.includes(keyword) || user.nickName.includes(keyword))
11+
: users;
12+
const start = (Number(current) - 1) * Number(pageSize);
13+
const end = start + Number(pageSize);
14+
15+
res.json({
16+
success: true,
17+
data: {
18+
current: Number(current),
19+
pageSize: Number(pageSize),
20+
total: list.length,
21+
list: list.slice(start, end),
22+
},
23+
errorCode: 0,
24+
});
25+
},
26+
'POST /api/v1/user': (req: any, res: any) => {
27+
const user = {
28+
id: `${Date.now()}`,
29+
gender: 'MALE',
30+
...req.body,
31+
};
32+
users = [user, ...users];
33+
res.json({
34+
success: true,
35+
data: user,
36+
errorCode: 0,
37+
});
38+
},
39+
'PUT /api/v1/user/:userId': (req: any, res: any) => {
40+
const { userId } = req.params;
41+
const index = users.findIndex((user) => user.id === userId);
42+
if (index < 0) {
43+
res.status(404).json({
44+
success: false,
45+
errorCode: 404,
46+
message: '用户不存在',
47+
});
48+
return;
49+
}
50+
51+
users[index] = {
52+
...users[index],
53+
...req.body,
54+
};
855
res.json({
956
success: true,
10-
data: { list: users },
57+
data: users[index],
1158
errorCode: 0,
1259
});
1360
},
14-
'PUT /api/v1/user/': (req: any, res: any) => {
61+
'DELETE /api/v1/user/:userId': (req: any, res: any) => {
62+
const { userId } = req.params;
63+
users = users.filter((user) => user.id !== userId);
1564
res.json({
1665
success: true,
66+
data: userId,
1767
errorCode: 0,
1868
});
1969
},

src/access.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
// 参考文档 https://umijs.org/docs/max/access
22
export default (initialState: API.UserInfo) => {
33
// 'dontHaveAccess' 是约定的禁止访问标识符,由后端登录接口返回以拒绝特定用户进入管理后台
4-
const canSeeAdmin = !!(initialState && initialState.name !== 'dontHaveAccess');
4+
const canSeeAdmin = !!initialState?.name && initialState.name !== 'dontHaveAccess';
55
return {
66
canSeeAdmin,
77
};

src/constants/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,2 @@
11
export const DEFAULT_NAME = 'Umi Max';
2+
export const AUTH_TOKEN_KEY = 'umi-react-admin-token';

src/layouts/RightContent.tsx

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,16 @@
1+
import { AUTH_TOKEN_KEY } from '@/constants';
12
import { GithubOutlined, GlobalOutlined, SkinOutlined, UserOutlined } from '@ant-design/icons';
2-
import { setLocale, useIntl } from '@umijs/max';
3+
import { history, setLocale, useIntl } from '@umijs/max';
34
import { Avatar, Button, Popover, message } from 'antd';
45
import { useEffect, useState } from 'react';
56

67
const safeLocalStorage = {
78
getItem: (key: string) => (typeof window !== 'undefined' ? localStorage.getItem(key) : null),
9+
removeItem: (key: string) => {
10+
if (typeof window !== 'undefined') {
11+
localStorage.removeItem(key);
12+
}
13+
},
814
};
915

1016
const RightContent = () => {
@@ -54,7 +60,9 @@ const RightContent = () => {
5460
<div
5561
className="w-24 px-2 py-1 text-center rounded-md cursor-pointer hover:bg-zinc-200"
5662
onClick={() => {
57-
// TODO: 实现登出功能
63+
safeLocalStorage.removeItem(AUTH_TOKEN_KEY);
64+
messageApi.success(intl.formatMessage({ id: 'Logout' }));
65+
history.push('/login');
5866
}}
5967
>
6068
{intl.formatMessage({ id: 'Logout' })}

src/locales/en-US.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
export default {
22
'menu.home': 'home',
3+
'menu.login': 'login',
4+
'menu.access': 'access',
5+
'menu.table': 'table',
36
'menu.NotFound': 'NotFound',
47
'menu.NotAccessible': 'NotAccessible',
58
// NOTE 功能

src/locales/zh-CN.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
export default {
22
'menu.home': '首页',
3+
'menu.login': '登录',
4+
'menu.access': '权限',
5+
'menu.table': '表格',
36
'menu.NotFound': '找不到页面',
47
'menu.NotAccessible': '无权限访问',
58
// NOTE 功能

src/pages/Login/index.tsx

Lines changed: 29 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,33 @@
1+
import { AUTH_TOKEN_KEY } from '@/constants';
2+
import { history } from '@umijs/max';
3+
import { Button, Card, Form, Input, message } from 'antd';
4+
15
const Login: React.FC = () => {
2-
return <div>login</div>;
6+
const [messageApi, contextHolder] = message.useMessage();
7+
8+
const handleFinish = (values: { name: string }) => {
9+
localStorage.setItem(AUTH_TOKEN_KEY, `${values.name || 'admin'}-demo-token`);
10+
messageApi.success('登录成功');
11+
history.push('/home');
12+
};
13+
14+
return (
15+
<div className="flex min-h-screen items-center justify-center bg-slate-50 px-4">
16+
{contextHolder}
17+
<Card title="React Admin" className="w-full max-w-sm">
18+
<Form initialValues={{ name: 'admin' }} layout="vertical" onFinish={handleFinish}>
19+
<Form.Item label="用户名" name="name" rules={[{ required: true, message: '请输入用户名' }]}>
20+
<Input autoComplete="username" />
21+
</Form.Item>
22+
<Form.Item>
23+
<Button block type="primary" htmlType="submit">
24+
登录
25+
</Button>
26+
</Form.Item>
27+
</Form>
28+
</Card>
29+
</div>
30+
);
331
};
432

533
export default Login;

src/pages/Table/components/UpdateForm.tsx

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -48,11 +48,13 @@ const UpdateForm: React.FC<UpdateFormProps> = (props) => (
4848
>
4949
<StepsForm.StepForm
5050
initialValues={{
51+
id: props.values.id,
5152
name: props.values.name,
5253
nickName: props.values.nickName,
5354
}}
5455
title="基本信息"
5556
>
57+
<ProFormText hidden name="id" />
5658
<ProFormText width="md" name="name" label="规则名称" rules={[{ required: true, message: '请输入规则名称!' }]} />
5759
<ProFormTextArea
5860
name="desc"

src/pages/Table/index.tsx

Lines changed: 43 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,13 @@
11
import services from '@/services/demo';
2-
import { ActionType, FooterToolbar, PageContainer, ProDescriptions, ProTable } from '@ant-design/pro-components';
2+
import {
3+
ActionType,
4+
FooterToolbar,
5+
PageContainer,
6+
ProColumns,
7+
ProDescriptions,
8+
ProDescriptionsItemProps,
9+
ProTable,
10+
} from '@ant-design/pro-components';
311
import { Button, Divider, Drawer, message } from 'antd';
412
import React, { useRef, useState } from 'react';
513
import CreateForm from './components/CreateForm';
@@ -59,11 +67,20 @@ const handleUpdate = async (fields: FormValueType) => {
5967
*/
6068
const handleRemove = async (selectedRows: API.UserInfo[]) => {
6169
const hide = message.loading('正在删除');
62-
if (!selectedRows) return true;
70+
if (!selectedRows.length) {
71+
hide();
72+
return true;
73+
}
74+
75+
const userIds = selectedRows.map((row) => row.id).filter(Boolean);
76+
if (!userIds.length) {
77+
hide();
78+
message.warning('未找到可删除的数据');
79+
return false;
80+
}
81+
6382
try {
64-
await deleteUser({
65-
userId: selectedRows.find((row) => row.id)?.id || '',
66-
});
83+
await Promise.all(userIds.map((userId) => deleteUser({ userId })));
6784
hide();
6885
message.success('删除成功,即将刷新');
6986
return true;
@@ -81,8 +98,7 @@ const TableList: React.FC<unknown> = () => {
8198
const actionRef = useRef<ActionType>();
8299
const [row, setRow] = useState<API.UserInfo>();
83100
const [selectedRowsState, setSelectedRows] = useState<API.UserInfo[]>([]);
84-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
85-
const columns: any[] = [
101+
const baseColumns: ProColumns<API.UserInfo>[] = [
86102
{
87103
title: '名称',
88104
dataIndex: 'name',
@@ -110,11 +126,14 @@ const TableList: React.FC<unknown> = () => {
110126
1: { text: '女', status: 'FEMALE' },
111127
},
112128
},
129+
];
130+
const columns: ProColumns<API.UserInfo>[] = [
131+
...baseColumns,
113132
{
114133
title: '操作',
115134
dataIndex: 'option',
116135
valueType: 'option',
117-
render: (_: any, record: API.UserInfo) => (
136+
render: (_, record) => (
118137
<>
119138
<a
120139
onClick={() => {
@@ -125,11 +144,25 @@ const TableList: React.FC<unknown> = () => {
125144
配置
126145
</a>
127146
<Divider type="vertical" />
128-
<a href="">订阅警报</a>
147+
<Button type="link" className="p-0">
148+
订阅警报
149+
</Button>
129150
</>
130151
),
131152
},
132153
];
154+
const descriptionColumns: ProDescriptionsItemProps<API.UserInfo>[] = [
155+
{ title: '名称', dataIndex: 'name' },
156+
{ title: '昵称', dataIndex: 'nickName', valueType: 'text' },
157+
{
158+
title: '性别',
159+
dataIndex: 'gender',
160+
valueEnum: {
161+
0: { text: '男', status: 'MALE' },
162+
1: { text: '女', status: 'FEMALE' },
163+
},
164+
},
165+
];
133166

134167
return (
135168
<PageContainer
@@ -236,7 +269,7 @@ const TableList: React.FC<unknown> = () => {
236269
params={{
237270
id: row?.name,
238271
}}
239-
columns={columns}
272+
columns={descriptionColumns}
240273
/>
241274
)}
242275
</Drawer>

0 commit comments

Comments
 (0)