|
|
@@ -1,3 +1,79 @@
|
|
|
+import { fetchDeleteDept, fetchDeptTree } from '@/services/dept';
|
|
|
+import { PageContainer } from '@ant-design/pro-components';
|
|
|
+import { useIntl } from '@umijs/max';
|
|
|
+import { Button, Popconfirm, Space, Spin, Tree, message } from 'antd';
|
|
|
+import type { DataNode } from 'antd/es/tree';
|
|
|
+import { useEffect, useState } from 'react';
|
|
|
+import { DeptForm } from './components/Form';
|
|
|
+
|
|
|
export default function DeptPage() {
|
|
|
- return null;
|
|
|
+ const intl = useIntl();
|
|
|
+ const [loading, setLoading] = useState(false);
|
|
|
+ const [treeData, setTreeData] = useState<API.DeptItem[]>([]);
|
|
|
+
|
|
|
+ const loadTree = async () => {
|
|
|
+ setLoading(true);
|
|
|
+ try {
|
|
|
+ const res = await fetchDeptTree();
|
|
|
+ setTreeData(res.data ?? []);
|
|
|
+ } finally {
|
|
|
+ setLoading(false);
|
|
|
+ }
|
|
|
+ };
|
|
|
+
|
|
|
+ useEffect(() => {
|
|
|
+ loadTree();
|
|
|
+ }, []);
|
|
|
+
|
|
|
+ const handleDelete = async (id: number) => {
|
|
|
+ await fetchDeleteDept({ id });
|
|
|
+ message.success('删除成功');
|
|
|
+ loadTree();
|
|
|
+ };
|
|
|
+
|
|
|
+ const renderTitle = (node: API.DeptItem) => (
|
|
|
+ <Space>
|
|
|
+ <span>{node.name}</span>
|
|
|
+ <DeptForm
|
|
|
+ mode="edit"
|
|
|
+ initialValues={node}
|
|
|
+ onSuccess={loadTree}
|
|
|
+ trigger={<a className="text-xs">编辑</a>}
|
|
|
+ />
|
|
|
+ <DeptForm
|
|
|
+ mode="add"
|
|
|
+ initialValues={{ parentId: node.id }}
|
|
|
+ onSuccess={loadTree}
|
|
|
+ trigger={<a className="text-xs">新建子部门</a>}
|
|
|
+ />
|
|
|
+ <Popconfirm title="确认删除?" onConfirm={() => handleDelete(node.id)}>
|
|
|
+ <a className="text-xs text-red-500">删除</a>
|
|
|
+ </Popconfirm>
|
|
|
+ </Space>
|
|
|
+ );
|
|
|
+
|
|
|
+ const renderNodes = (items: API.DeptItem[]): DataNode[] =>
|
|
|
+ items.map((item) => ({
|
|
|
+ key: item.id,
|
|
|
+ title: renderTitle(item),
|
|
|
+ children: item.children ? renderNodes(item.children) : undefined,
|
|
|
+ }));
|
|
|
+
|
|
|
+ return (
|
|
|
+ <PageContainer title={intl.formatMessage({ id: 'admin.dept.title' })}>
|
|
|
+ <div className="mb-4">
|
|
|
+ <DeptForm
|
|
|
+ mode="add"
|
|
|
+ initialValues={{ parentId: 0 }}
|
|
|
+ onSuccess={loadTree}
|
|
|
+ trigger={
|
|
|
+ <Button type="primary">{intl.formatMessage({ id: 'admin.dept.createRoot' })}</Button>
|
|
|
+ }
|
|
|
+ />
|
|
|
+ </div>
|
|
|
+ <Spin spinning={loading}>
|
|
|
+ <Tree treeData={renderNodes(treeData)} defaultExpandAll showLine />
|
|
|
+ </Spin>
|
|
|
+ </PageContainer>
|
|
|
+ );
|
|
|
}
|