mirror of
https://github.com/PlayEdu/backend
synced 2025-06-16 01:07:02 +08:00
ldap开关联动部门、学员的新建、编辑、删除、排序、导入
This commit is contained in:
parent
3d29dd8963
commit
4122a2ac39
@ -32,6 +32,9 @@ const DepartmentPage = () => {
|
|||||||
const [updateVisible, setUpdateVisible] = useState(false);
|
const [updateVisible, setUpdateVisible] = useState(false);
|
||||||
const [did, setDid] = useState<number>(0);
|
const [did, setDid] = useState<number>(0);
|
||||||
const [modal, contextHolder] = Modal.useModal();
|
const [modal, contextHolder] = Modal.useModal();
|
||||||
|
const ldapEnabled = useSelector(
|
||||||
|
(state: any) => state.systemConfig.value["ldap-enabled"]
|
||||||
|
);
|
||||||
|
|
||||||
const onSelect = (selectedKeys: any, info: any) => {
|
const onSelect = (selectedKeys: any, info: any) => {
|
||||||
setSelectKey(selectedKeys);
|
setSelectKey(selectedKeys);
|
||||||
@ -45,11 +48,11 @@ const DepartmentPage = () => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
|
setLoading(true);
|
||||||
getData();
|
getData();
|
||||||
}, [refresh, permissions]);
|
}, [refresh, permissions]);
|
||||||
|
|
||||||
const getData = () => {
|
const getData = () => {
|
||||||
setLoading(true);
|
|
||||||
department.departmentList().then((res: any) => {
|
department.departmentList().then((res: any) => {
|
||||||
const departments: DepartmentsBoxModel = res.data.departments;
|
const departments: DepartmentsBoxModel = res.data.departments;
|
||||||
if (JSON.stringify(departments) !== "{}") {
|
if (JSON.stringify(departments) !== "{}") {
|
||||||
@ -65,85 +68,108 @@ const DepartmentPage = () => {
|
|||||||
const arr = [];
|
const arr = [];
|
||||||
for (let i = 0; i < departments[id].length; i++) {
|
for (let i = 0; i < departments[id].length; i++) {
|
||||||
if (!departments[departments[id][i].id]) {
|
if (!departments[departments[id][i].id]) {
|
||||||
arr.push({
|
if (ldapEnabled) {
|
||||||
title: (
|
arr.push({
|
||||||
<>
|
title: (
|
||||||
<div className="tree-title-elli">{departments[id][i].name}</div>
|
<>
|
||||||
<div className="d-flex">
|
<div className="tree-title-elli">{departments[id][i].name}</div>
|
||||||
<Tooltip placement="top" title="可拖拽排序">
|
</>
|
||||||
<i
|
),
|
||||||
className="iconfont icon-icon-drag mr-16"
|
key: departments[id][i].id,
|
||||||
style={{ fontSize: 24 }}
|
});
|
||||||
/>
|
} else {
|
||||||
</Tooltip>
|
arr.push({
|
||||||
{through("department-cud") && (
|
title: (
|
||||||
<>
|
<>
|
||||||
|
<div className="tree-title-elli">{departments[id][i].name}</div>
|
||||||
|
<div className="d-flex">
|
||||||
|
<Tooltip placement="top" title="可拖拽排序">
|
||||||
<i
|
<i
|
||||||
className="iconfont icon-icon-edit mr-16"
|
className="iconfont icon-icon-drag mr-16"
|
||||||
style={{ fontSize: 24 }}
|
style={{ fontSize: 24 }}
|
||||||
onClick={() => {
|
|
||||||
setDid(departments[id][i].id);
|
|
||||||
setUpdateVisible(true);
|
|
||||||
}}
|
|
||||||
/>
|
/>
|
||||||
<i
|
</Tooltip>
|
||||||
className="iconfont icon-icon-delete"
|
{through("department-cud") && (
|
||||||
style={{ fontSize: 24 }}
|
<>
|
||||||
onClick={() =>
|
<i
|
||||||
removeItem(
|
className="iconfont icon-icon-edit mr-16"
|
||||||
departments[id][i].id,
|
style={{ fontSize: 24 }}
|
||||||
departments[id][i].name
|
onClick={() => {
|
||||||
)
|
setDid(departments[id][i].id);
|
||||||
}
|
setUpdateVisible(true);
|
||||||
/>
|
}}
|
||||||
</>
|
/>
|
||||||
)}
|
<i
|
||||||
</div>
|
className="iconfont icon-icon-delete"
|
||||||
</>
|
style={{ fontSize: 24 }}
|
||||||
),
|
onClick={() =>
|
||||||
key: departments[id][i].id,
|
removeItem(
|
||||||
});
|
departments[id][i].id,
|
||||||
|
departments[id][i].name
|
||||||
|
)
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
),
|
||||||
|
key: departments[id][i].id,
|
||||||
|
});
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
const new_arr: Option[] = checkArr(departments, departments[id][i].id);
|
const new_arr: Option[] = checkArr(departments, departments[id][i].id);
|
||||||
arr.push({
|
if (ldapEnabled) {
|
||||||
title: (
|
arr.push({
|
||||||
<>
|
title: (
|
||||||
<div className="tree-title-elli">{departments[id][i].name}</div>
|
<>
|
||||||
<div className="d-flex">
|
<div className="tree-title-elli">{departments[id][i].name}</div>
|
||||||
<Tooltip placement="top" title="可拖拽排序">
|
</>
|
||||||
<i
|
),
|
||||||
className="iconfont icon-icon-drag mr-16"
|
key: departments[id][i].id,
|
||||||
style={{ fontSize: 24 }}
|
children: new_arr,
|
||||||
/>
|
});
|
||||||
</Tooltip>
|
} else {
|
||||||
{through("department-cud") && (
|
arr.push({
|
||||||
<>
|
title: (
|
||||||
|
<>
|
||||||
|
<div className="tree-title-elli">{departments[id][i].name}</div>
|
||||||
|
<div className="d-flex">
|
||||||
|
<Tooltip placement="top" title="可拖拽排序">
|
||||||
<i
|
<i
|
||||||
className="iconfont icon-icon-edit mr-16"
|
className="iconfont icon-icon-drag mr-16"
|
||||||
style={{ fontSize: 24 }}
|
style={{ fontSize: 24 }}
|
||||||
onClick={() => {
|
|
||||||
setDid(departments[id][i].id);
|
|
||||||
setUpdateVisible(true);
|
|
||||||
}}
|
|
||||||
/>
|
/>
|
||||||
<i
|
</Tooltip>
|
||||||
className="iconfont icon-icon-delete"
|
{through("department-cud") && (
|
||||||
style={{ fontSize: 24 }}
|
<>
|
||||||
onClick={() =>
|
<i
|
||||||
removeItem(
|
className="iconfont icon-icon-edit mr-16"
|
||||||
departments[id][i].id,
|
style={{ fontSize: 24 }}
|
||||||
departments[id][i].name
|
onClick={() => {
|
||||||
)
|
setDid(departments[id][i].id);
|
||||||
}
|
setUpdateVisible(true);
|
||||||
/>
|
}}
|
||||||
</>
|
/>
|
||||||
)}
|
<i
|
||||||
</div>
|
className="iconfont icon-icon-delete"
|
||||||
</>
|
style={{ fontSize: 24 }}
|
||||||
),
|
onClick={() =>
|
||||||
key: departments[id][i].id,
|
removeItem(
|
||||||
children: new_arr,
|
departments[id][i].id,
|
||||||
});
|
departments[id][i].name
|
||||||
|
)
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
</>
|
||||||
|
),
|
||||||
|
key: departments[id][i].id,
|
||||||
|
children: new_arr,
|
||||||
|
});
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return arr;
|
return arr;
|
||||||
@ -365,22 +391,29 @@ const DepartmentPage = () => {
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<div className="playedu-main-top mb-24">
|
{!ldapEnabled && (
|
||||||
{contextHolder}
|
<div className="playedu-main-top mb-24">
|
||||||
<div className="d-flex">
|
{contextHolder}
|
||||||
<PerButton
|
<div className="d-flex">
|
||||||
type="primary"
|
<PerButton
|
||||||
text="新建部门"
|
type="primary"
|
||||||
class="mr-16"
|
text="新建部门"
|
||||||
icon={<PlusOutlined />}
|
class="mr-16"
|
||||||
p="department-cud"
|
icon={<PlusOutlined />}
|
||||||
onClick={() => setCreateVisible(true)}
|
p="department-cud"
|
||||||
disabled={null}
|
onClick={() => setCreateVisible(true)}
|
||||||
/>
|
disabled={null}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
)}
|
||||||
<div className="playedu-main-body">
|
<div className="playedu-main-body">
|
||||||
<div style={{ width: 366 }}>
|
{loading && (
|
||||||
|
<div className="float-left text-center mt-30">
|
||||||
|
<Spin></Spin>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
<div style={{ display: loading ? "none" : "block", width: 366 }}>
|
||||||
{treeData.length > 0 && (
|
{treeData.length > 0 && (
|
||||||
<Tree
|
<Tree
|
||||||
onSelect={onSelect}
|
onSelect={onSelect}
|
||||||
|
@ -19,6 +19,7 @@ const InitPage = (props: Props) => {
|
|||||||
|
|
||||||
if (props.configData) {
|
if (props.configData) {
|
||||||
let config: SystemConfigStoreInterface = {
|
let config: SystemConfigStoreInterface = {
|
||||||
|
"ldap-enabled": props.configData["ldap-enabled"],
|
||||||
systemName: props.configData["system.name"],
|
systemName: props.configData["system.name"],
|
||||||
systemLogo: props.configData["system.logo"],
|
systemLogo: props.configData["system.logo"],
|
||||||
systemApiUrl: props.configData["system.api_url"],
|
systemApiUrl: props.configData["system.api_url"],
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
import { useState, useEffect } from "react";
|
import { useState } from "react";
|
||||||
import styles from "./index.module.less";
|
import styles from "./index.module.less";
|
||||||
import { Input, Button, message } from "antd";
|
import { Input, Button, message } from "antd";
|
||||||
import { login as loginApi, system } from "../../api/index";
|
import { login as loginApi, system } from "../../api/index";
|
||||||
@ -59,6 +59,7 @@ const LoginPage = () => {
|
|||||||
const getSystemConfig = async () => {
|
const getSystemConfig = async () => {
|
||||||
let res: any = await system.getSystemConfig();
|
let res: any = await system.getSystemConfig();
|
||||||
let data: SystemConfigStoreInterface = {
|
let data: SystemConfigStoreInterface = {
|
||||||
|
"ldap-enabled": res.data["ldap-enabled"],
|
||||||
systemName: res.data["system.name"],
|
systemName: res.data["system.name"],
|
||||||
systemLogo: res.data["system.logo"],
|
systemLogo: res.data["system.logo"],
|
||||||
systemApiUrl: res.data["system.api_url"],
|
systemApiUrl: res.data["system.api_url"],
|
||||||
|
@ -21,6 +21,7 @@ import {
|
|||||||
import { user } from "../../api/index";
|
import { user } from "../../api/index";
|
||||||
import { dateFormat } from "../../utils/index";
|
import { dateFormat } from "../../utils/index";
|
||||||
import { Link, Navigate, useLocation } from "react-router-dom";
|
import { Link, Navigate, useLocation } from "react-router-dom";
|
||||||
|
import { useSelector } from "react-redux";
|
||||||
import { TreeDepartment, PerButton } from "../../compenents";
|
import { TreeDepartment, PerButton } from "../../compenents";
|
||||||
import { MemberCreate } from "./compenents/create";
|
import { MemberCreate } from "./compenents/create";
|
||||||
import { MemberUpdate } from "./compenents/update";
|
import { MemberUpdate } from "./compenents/update";
|
||||||
@ -66,6 +67,9 @@ const MemberPage = () => {
|
|||||||
const [user_dep_ids, setUserDepIds] = useState<DepIdsModel>({});
|
const [user_dep_ids, setUserDepIds] = useState<DepIdsModel>({});
|
||||||
const [departments, setDepartments] = useState<DepartmentsModel>({});
|
const [departments, setDepartments] = useState<DepartmentsModel>({});
|
||||||
const [did, setDid] = useState(Number(result.get("did")));
|
const [did, setDid] = useState(Number(result.get("did")));
|
||||||
|
const ldapEnabled = useSelector(
|
||||||
|
(state: any) => state.systemConfig.value["ldap-enabled"]
|
||||||
|
);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
setDid(Number(result.get("did")));
|
setDid(Number(result.get("did")));
|
||||||
@ -180,19 +184,23 @@ const MemberPage = () => {
|
|||||||
disabled={null}
|
disabled={null}
|
||||||
/>
|
/>
|
||||||
</Link>
|
</Link>
|
||||||
<div className="form-column"></div>
|
{!ldapEnabled && (
|
||||||
<Dropdown menu={{ items }}>
|
<>
|
||||||
<Button
|
<div className="form-column"></div>
|
||||||
type="link"
|
<Dropdown menu={{ items }}>
|
||||||
className="b-link c-red"
|
<Button
|
||||||
onClick={(e) => e.preventDefault()}
|
type="link"
|
||||||
>
|
className="b-link c-red"
|
||||||
<Space size="small" align="center">
|
onClick={(e) => e.preventDefault()}
|
||||||
更多
|
>
|
||||||
<DownOutlined />
|
<Space size="small" align="center">
|
||||||
</Space>
|
更多
|
||||||
</Button>
|
<DownOutlined />
|
||||||
</Dropdown>
|
</Space>
|
||||||
|
</Button>
|
||||||
|
</Dropdown>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
</Space>
|
</Space>
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
@ -297,16 +305,18 @@ const MemberPage = () => {
|
|||||||
</div>
|
</div>
|
||||||
<div className="float-left j-b-flex mb-24">
|
<div className="float-left j-b-flex mb-24">
|
||||||
<div className="d-flex">
|
<div className="d-flex">
|
||||||
<PerButton
|
{!ldapEnabled && (
|
||||||
type="primary"
|
<PerButton
|
||||||
text="添加学员"
|
type="primary"
|
||||||
class="mr-16"
|
text="添加学员"
|
||||||
icon={<PlusOutlined />}
|
class="mr-16"
|
||||||
p="user-store"
|
icon={<PlusOutlined />}
|
||||||
onClick={() => setCreateVisible(true)}
|
p="user-store"
|
||||||
disabled={null}
|
onClick={() => setCreateVisible(true)}
|
||||||
/>
|
disabled={null}
|
||||||
{dep_ids.length === 0 && (
|
/>
|
||||||
|
)}
|
||||||
|
{!ldapEnabled && dep_ids.length === 0 && (
|
||||||
<Link style={{ textDecoration: "none" }} to={`/member/import`}>
|
<Link style={{ textDecoration: "none" }} to={`/member/import`}>
|
||||||
<PerButton
|
<PerButton
|
||||||
type="default"
|
type="default"
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
import React, { useState, useEffect } from "react";
|
import React, { useState, useEffect } from "react";
|
||||||
import { Button, Tree, Modal, message, Tooltip } from "antd";
|
import { Button, Tree, Modal, message, Tooltip, Spin } from "antd";
|
||||||
// import styles from "./index.module.less";
|
// import styles from "./index.module.less";
|
||||||
import { PlusOutlined, ExclamationCircleFilled } from "@ant-design/icons";
|
import { PlusOutlined, ExclamationCircleFilled } from "@ant-design/icons";
|
||||||
import { resourceCategory } from "../../../api/index";
|
import { resourceCategory } from "../../../api/index";
|
||||||
@ -24,6 +24,7 @@ const ResourceCategoryPage = () => {
|
|||||||
(state: any) => state.loginUser.value.permissions
|
(state: any) => state.loginUser.value.permissions
|
||||||
);
|
);
|
||||||
const [loading, setLoading] = useState<boolean>(true);
|
const [loading, setLoading] = useState<boolean>(true);
|
||||||
|
const [init, setInit] = useState(true);
|
||||||
const [refresh, setRefresh] = useState(false);
|
const [refresh, setRefresh] = useState(false);
|
||||||
const [treeData, setTreeData] = useState<Option[]>([]);
|
const [treeData, setTreeData] = useState<Option[]>([]);
|
||||||
const [selectKey, setSelectKey] = useState<number[]>([]);
|
const [selectKey, setSelectKey] = useState<number[]>([]);
|
||||||
@ -33,6 +34,7 @@ const ResourceCategoryPage = () => {
|
|||||||
const [modal, contextHolder] = Modal.useModal();
|
const [modal, contextHolder] = Modal.useModal();
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
|
setInit(true);
|
||||||
getData();
|
getData();
|
||||||
}, [refresh, permissions]);
|
}, [refresh, permissions]);
|
||||||
|
|
||||||
@ -56,6 +58,7 @@ const ResourceCategoryPage = () => {
|
|||||||
setTreeData(new_arr);
|
setTreeData(new_arr);
|
||||||
}
|
}
|
||||||
setLoading(false);
|
setLoading(false);
|
||||||
|
setInit(false);
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -390,7 +393,12 @@ const ResourceCategoryPage = () => {
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div className="playedu-main-body">
|
<div className="playedu-main-body">
|
||||||
<div style={{ width: 366 }}>
|
{init && (
|
||||||
|
<div className="float-left text-center mt-30">
|
||||||
|
<Spin></Spin>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
<div style={{ display: init ? "none" : "block", width: 366 }}>
|
||||||
{treeData.length > 0 && (
|
{treeData.length > 0 && (
|
||||||
<Tree
|
<Tree
|
||||||
onSelect={onSelect}
|
onSelect={onSelect}
|
||||||
|
@ -12,13 +12,18 @@ import {
|
|||||||
Slider,
|
Slider,
|
||||||
Space,
|
Space,
|
||||||
} from "antd";
|
} from "antd";
|
||||||
// import styles from "./index.module.less";
|
import { appConfig, system } from "../../../api/index";
|
||||||
import { appConfig } from "../../../api/index";
|
|
||||||
import { UploadImageButton } from "../../../compenents";
|
import { UploadImageButton } from "../../../compenents";
|
||||||
|
import { useDispatch } from "react-redux";
|
||||||
import type { TabsProps } from "antd";
|
import type { TabsProps } from "antd";
|
||||||
import type { CheckboxChangeEvent } from "antd/es/checkbox";
|
import type { CheckboxChangeEvent } from "antd/es/checkbox";
|
||||||
|
import {
|
||||||
|
SystemConfigStoreInterface,
|
||||||
|
saveConfigAction,
|
||||||
|
} from "../../../store/system/systemConfigSlice";
|
||||||
|
|
||||||
const SystemConfigPage = () => {
|
const SystemConfigPage = () => {
|
||||||
|
const dispatch = useDispatch();
|
||||||
const [form] = Form.useForm();
|
const [form] = Form.useForm();
|
||||||
const [loading, setLoading] = useState(false);
|
const [loading, setLoading] = useState(false);
|
||||||
const [logo, setLogo] = useState("");
|
const [logo, setLogo] = useState("");
|
||||||
@ -239,6 +244,23 @@ const SystemConfigPage = () => {
|
|||||||
message.success("保存成功!");
|
message.success("保存成功!");
|
||||||
setLoading(false);
|
setLoading(false);
|
||||||
getDetail();
|
getDetail();
|
||||||
|
getSystemConfig();
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
const getSystemConfig = async () => {
|
||||||
|
system.getSystemConfig().then((res: any) => {
|
||||||
|
let data: SystemConfigStoreInterface = {
|
||||||
|
"ldap-enabled": res.data["ldap-enabled"],
|
||||||
|
systemName: res.data["system.name"],
|
||||||
|
systemLogo: res.data["system.logo"],
|
||||||
|
systemApiUrl: res.data["system.api_url"],
|
||||||
|
systemPcUrl: res.data["system.pc_url"],
|
||||||
|
systemH5Url: res.data["system.h5_url"],
|
||||||
|
memberDefaultAvatar: res.data["member.default_avatar"],
|
||||||
|
courseDefaultThumbs: res.data["default.course_thumbs"],
|
||||||
|
};
|
||||||
|
dispatch(saveConfigAction(data));
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import { createSlice } from "@reduxjs/toolkit";
|
import { createSlice } from "@reduxjs/toolkit";
|
||||||
|
|
||||||
type SystemConfigStoreInterface = {
|
type SystemConfigStoreInterface = {
|
||||||
|
"ldap-enabled"?: boolean;
|
||||||
systemApiUrl?: string;
|
systemApiUrl?: string;
|
||||||
systemPcUrl?: string;
|
systemPcUrl?: string;
|
||||||
systemH5Url?: string;
|
systemH5Url?: string;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user