Merge remote-tracking branch 'origin/dev'

# Conflicts:
#	web/src/components/Login.js
#	web/src/components/user/LayoutHeader.js
This commit is contained in:
dushixiang
2021-03-21 16:48:15 +08:00
116 changed files with 3412 additions and 3011 deletions

View File

@ -33,7 +33,7 @@
}
.layout-header {
height: 48px;
height: 60px;
align-items: center;
padding: 0 16px 0 0;
background: #fff;
@ -45,23 +45,19 @@
padding: 0 12px;
cursor: pointer;
transition: all .3s;
line-height: 48px;
height: 48px;
line-height: 60px;
height: 60px;
}
.layout-header-right-item {
margin: 0 6px;
display: inline;
height: 48px;
}
.layout-header-right-item:hover {
background-color: #eeeeee;
height: 60px;
}
.nickname {
line-height: 48px;
height: 48px;
line-height: 60px;
height: 60px;
width: 125px;
text-align: left;
padding: 0 5px;

View File

@ -1,7 +1,7 @@
import React, {Component} from 'react';
import 'antd/dist/antd.css';
import './App.css';
import {Divider, Layout, Menu} from "antd";
import {Col, Divider, Dropdown, Layout, Menu, Popconfirm, Row, Tooltip} from "antd";
import {Link, Route, Switch} from "react-router-dom";
import Dashboard from "./components/dashboard/Dashboard";
import Asset from "./components/asset/Asset";
@ -21,15 +21,21 @@ import {
DashboardOutlined,
DesktopOutlined,
DisconnectOutlined,
DownOutlined,
GithubOutlined,
IdcardOutlined,
LinkOutlined,
LoginOutlined,
LogoutOutlined,
QuestionCircleOutlined,
SafetyCertificateOutlined,
SettingOutlined,
SolutionOutlined,
TeamOutlined,
UserOutlined,
UserSwitchOutlined
UserSwitchOutlined,
MenuUnfoldOutlined,
MenuFoldOutlined,
} from '@ant-design/icons';
import Info from "./components/user/Info";
import request from "./common/request";
@ -37,18 +43,18 @@ import {message} from "antd/es";
import Setting from "./components/setting/Setting";
import BatchCommand from "./components/command/BatchCommand";
import {isEmpty, NT_PACKAGE} from "./utils/utils";
import {isAdmin} from "./service/permission";
import {getCurrentUser, isAdmin} from "./service/permission";
import UserGroup from "./components/user/UserGroup";
import LoginLog from "./components/devops/LoginLog";
import Term from "./components/access/Term";
import Job from "./components/devops/Job";
import {Header} from "antd/es/layout/layout";
import LayoutHeader from "./components/user/LayoutHeader";
import Security from "./components/devops/Security";
const {Footer, Sider} = Layout;
const {SubMenu} = Menu;
const headerHeight = 60;
class App extends Component {
@ -113,8 +119,54 @@ class App extends Component {
sessionStorage.setItem('openKeys', JSON.stringify(openKeys));
}
confirm = async (e) => {
let result = await request.post('/logout');
if (result['code'] !== 1) {
message.error(result['message']);
} else {
message.success('退出登录成功,即将跳转至登录页面。');
window.location.reload();
}
}
render() {
const menu = (
<Menu>
<Menu.Item>
<Link to={'/info'}>
<SolutionOutlined/>
个人中心
</Link>
</Menu.Item>
<Menu.Item>
<a target='_blank' rel="noreferrer" href='https://github.com/dushixiang/next-terminal'>
<GithubOutlined/>
点个Star
</a>
</Menu.Item>
<Menu.Divider/>
<Menu.Item>
<Popconfirm
key='login-btn-pop'
title="您确定要退出登录吗?"
onConfirm={this.confirm}
okText="确定"
cancelText="取消"
placement="left"
>
<LogoutOutlined/>
退出登录
</Popconfirm>
</Menu.Item>
</Menu>
);
return (
@ -126,7 +178,7 @@ class App extends Component {
<Route path="/">
<Layout className="layout" style={{minHeight: '100vh'}}>
<Sider collapsible collapsed={this.state.collapsed} onCollapse={this.onCollapse}>
<Sider collapsible collapsed={this.state.collapsed} trigger={null}>
<div className="logo">
<img src='logo.svg' alt='logo'/>
{
@ -251,8 +303,38 @@ class App extends Component {
<Layout className="site-layout">
<Header className="site-layout-background"
style={{padding: 0, height: 48, zIndex: 20}}>
<LayoutHeader key='layout-right-header'/>
style={{padding: 0, height: headerHeight, zIndex: 20}}>
<div className='layout-header'>
<Row justify="space-around" align="middle" gutter={24} style={{height: headerHeight}}>
<Col span={4} key={1} style={{height: headerHeight}}>
{React.createElement(this.state.collapsed ? MenuUnfoldOutlined : MenuFoldOutlined, {
className: 'trigger',
onClick: this.onCollapse,
})}
</Col>
<Col span={20} key={2} style={{textAlign: 'right'}}
className={'layout-header-right'}>
<div className={'layout-header-right-item'}>
<Tooltip placement="bottom" title={'使用帮助'}>
<a target='_blank' rel="noreferrer"
href='https://github.com/dushixiang/next-terminal/blob/master/docs/faq.md'>
<QuestionCircleOutlined/>
</a>
</Tooltip>
</div>
<Dropdown overlay={menu}>
<div className='nickname layout-header-right-item'>
{getCurrentUser()['nickname']} &nbsp;<DownOutlined/>
</div>
</Dropdown>
</Col>
</Row>
</div>
</Header>
<Route path="/" exact component={Dashboard}/>

View File

@ -10,7 +10,8 @@ const {Title} = Typography;
class LoginForm extends Component {
formRef = React.createRef()
formRef = React.createRef();
totpInputRef = React.createRef();
state = {
inLogin: false,
@ -44,6 +45,8 @@ class LoginForm extends Component {
loginAccount: params,
totpModalVisible: true
})
this.totpInputRef.current.focus();
return;
}
if (result.code !== 1) {
@ -74,8 +77,9 @@ class LoginForm extends Component {
try {
let result = await request.post('/loginWithTotp', loginAccount);
if (result.code !== 1) {
throw new Error(result.message);
if (result['code'] !== 1) {
message.error(result['message']);
return;
}
// 跳转登录
@ -128,13 +132,14 @@ class LoginForm extends Component {
<Modal title="双因素认证" visible={this.state.totpModalVisible} confirmLoading={this.state.confirmLoading}
maskClosable={false}
centered={true}
okButtonProps={{form:'totp-form', key: 'submit', htmlType: 'submit'}}
onOk={() => {
this.formRef.current
.validateFields()
.then(values => {
this.formRef.current.resetFields();
this.handleOk(values);
// this.formRef.current.resetFields();
})
.catch(info => {
@ -142,10 +147,10 @@ class LoginForm extends Component {
}}
onCancel={this.handleCancel}>
<Form ref={this.formRef}>
<Form id='totp-form' ref={this.formRef}>
<Form.Item name='totp' rules={[{required: true, message: '请输入双因素认证APP中显示的授权码'}]}>
<Input prefix={<OneToOneOutlined/>} placeholder="请输入双因素认证APP中显示的授权码"/>
<Input ref={this.totpInputRef} prefix={<OneToOneOutlined/>} placeholder="请输入双因素认证APP中显示的授权码"/>
</Form.Item>
</Form>
</Modal>

View File

@ -13,7 +13,6 @@ import {
Menu,
Modal,
notification,
PageHeader,
Row,
Select,
Space,
@ -27,7 +26,7 @@ import qs from "qs";
import AssetModal from "./AssetModal";
import request from "../../common/request";
import {message} from "antd/es";
import {getHeaders, isEmpty, itemRender} from "../../utils/utils";
import {getHeaders, isEmpty} from "../../utils/utils";
import dayjs from 'dayjs';
import {
DeleteOutlined,
@ -51,19 +50,6 @@ const confirm = Modal.confirm;
const {Search} = Input;
const {Content} = Layout;
const {Title, Text} = Typography;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
breadcrumbName: '资源管理',
},
{
path: 'assets',
breadcrumbName: '资产管理',
}
];
class Asset extends Component {
@ -660,18 +646,6 @@ class Asset extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="资产管理"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="资产"
>
</PageHeader>
<Content key='page-content' className="site-layout-background page-content">
<div style={{marginBottom: 20}}>
<Row justify="space-around" align="middle" gutter={24}>
@ -906,7 +880,7 @@ class Asset extends Component {
<Button type="primary" onClick={() => {
let csvString= 'name,ssh,127.0.0.1,22,username,password,privateKey,passphrase,description';
let csvString = 'name,ssh,127.0.0.1,22,username,password,privateKey,passphrase,description';
//前置的"\uFEFF"为“零宽不换行空格”,可处理中文乱码问题
const blob = new Blob(["\uFEFF" + csvString], {type: 'text/csv;charset=gb2312;'});
let a = document.createElement('a');

View File

@ -1,27 +1,12 @@
import React, {Component} from 'react';
import {Card, Input, List, PageHeader, Spin} from "antd";
import {Card, Input, List, Spin} from "antd";
import Console from "../access/Console";
import {itemRender} from "../../utils/utils";
import './Command.css'
import request from "../../common/request";
import {message} from "antd/es";
const {Search} = Input;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: '/dynamic-command',
breadcrumbName: '动态指令',
},
{
path: '/batch-command',
breadcrumbName: '批量执行命令',
}
];
class BatchCommand extends Component {
@ -72,18 +57,6 @@ class BatchCommand extends Component {
render() {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="批量执行命令"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="动态指令"
>
</PageHeader>
<Spin spinning={this.state.loading} tip='正在获取指令内容...'>
<div className="page-search">
<Search ref={this.commandRef} placeholder="请输入指令" onSearch={value => {

View File

@ -12,7 +12,6 @@ import {
Layout,
Menu,
Modal,
PageHeader,
Row,
Select,
Space,
@ -33,7 +32,7 @@ import {
SyncOutlined,
UndoOutlined
} from '@ant-design/icons';
import {compare, itemRender} from "../../utils/utils";
import {compare} from "../../utils/utils";
import {hasPermission, isAdmin} from "../../service/permission";
import dayjs from "dayjs";
@ -43,16 +42,6 @@ const {Content} = Layout;
const {Title, Text} = Typography;
const {Search} = Input;
const CheckboxGroup = Checkbox.Group;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'command',
breadcrumbName: '动态指令',
}
];
class DynamicCommand extends Component {
@ -534,18 +523,6 @@ class DynamicCommand extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="动态指令"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="批量动态指令执行"
>
</PageHeader>
<Content className="site-layout-background page-content">
<div style={{marginBottom: 20}}>

View File

@ -10,7 +10,6 @@ import {
Layout,
Menu,
Modal,
PageHeader,
Row,
Select,
Space,
@ -32,7 +31,6 @@ import {
SyncOutlined,
UndoOutlined
} from '@ant-design/icons';
import {itemRender} from "../../utils/utils";
import {hasPermission, isAdmin} from "../../service/permission";
import dayjs from "dayjs";
@ -41,16 +39,6 @@ const confirm = Modal.confirm;
const {Search} = Input;
const {Title, Text} = Typography;
const {Content} = Layout;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'credentials',
breadcrumbName: '授权凭证',
}
];
class Credential extends Component {
@ -483,18 +471,6 @@ class Credential extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="授权凭证"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="访问资产的账户、密钥等"
>
</PageHeader>
<Content className="site-layout-background page-content">
<div style={{marginBottom: 20}}>

View File

@ -1,7 +1,6 @@
import React, {Component} from 'react';
import {Card, Col, PageHeader, Radio, Row, Statistic} from "antd";
import {Card, Col, Radio, Row, Statistic} from "antd";
import {DesktopOutlined, IdcardOutlined, LinkOutlined, UserOutlined} from '@ant-design/icons';
import {itemRender} from '../../utils/utils'
import request from "../../common/request";
import './Dashboard.css'
import {Link} from "react-router-dom";
@ -9,18 +8,6 @@ import {Area} from '@ant-design/charts';
import {isAdmin} from "../../service/permission";
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'dashboard',
breadcrumbName: '仪表盘',
}
];
class Dashboard extends Component {
state = {
@ -79,17 +66,6 @@ class Dashboard extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="dashboard"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="仪表盘"
extra={[]}
>
</PageHeader>
<div className="page-card">

View File

@ -9,7 +9,6 @@ import {
Layout,
Menu,
Modal,
PageHeader,
Row,
Space,
Spin,
@ -30,7 +29,6 @@ import {
SyncOutlined,
UndoOutlined
} from '@ant-design/icons';
import {itemRender} from "../../utils/utils";
import dayjs from "dayjs";
import JobModal from "./JobModal";
@ -40,16 +38,6 @@ const confirm = Modal.confirm;
const {Content} = Layout;
const {Title, Text} = Typography;
const {Search} = Input;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'job',
breadcrumbName: '计划任务',
}
];
class Job extends Component {
@ -441,18 +429,6 @@ class Job extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="计划任务"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="计划任务"
>
</PageHeader>
<Content className="site-layout-background page-content">
<div style={{marginBottom: 20}}>

View File

@ -8,7 +8,6 @@ import {
Layout,
Modal,
notification,
PageHeader,
Row,
Select,
Space,
@ -18,7 +17,7 @@ import {
} from "antd";
import qs from "qs";
import request from "../../common/request";
import {formatDate, isEmpty, itemRender} from "../../utils/utils";
import {formatDate, isEmpty} from "../../utils/utils";
import {message} from "antd/es";
import {DeleteOutlined, ExclamationCircleOutlined, SyncOutlined, UndoOutlined} from "@ant-design/icons";
@ -27,16 +26,6 @@ const confirm = Modal.confirm;
const {Content} = Layout;
const {Search} = Input;
const {Title, Text} = Typography;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'loginLog',
breadcrumbName: '登录日志',
}
];
class LoginLog extends Component {
@ -280,18 +269,6 @@ class LoginLog extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="登录日志"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="只有登录成功的才会保存日志"
>
</PageHeader>
<Content className="site-layout-background page-content">
<div style={{marginBottom: 20}}>
<Row justify="space-around" align="middle" gutter={24}>

View File

@ -1,25 +1,10 @@
import React, {Component} from 'react';
import {
Button,
Col,
Divider,
Input,
Layout,
Modal,
PageHeader,
Row,
Space,
Table,
Tag,
Tooltip,
Typography
} from "antd";
import {Button, Col, Divider, Input, Layout, Modal, Row, Space, Table, Tag, Tooltip, Typography} from "antd";
import qs from "qs";
import request from "../../common/request";
import {message} from "antd/es";
import {DeleteOutlined, ExclamationCircleOutlined, PlusOutlined, SyncOutlined, UndoOutlined} from '@ant-design/icons';
import {itemRender} from "../../utils/utils";
import './Job.css'
import SecurityModal from "./SecurityModal";
@ -27,16 +12,6 @@ const confirm = Modal.confirm;
const {Content} = Layout;
const {Title, Text} = Typography;
const {Search} = Input;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'security',
breadcrumbName: '访问安全',
}
];
class Security extends Component {
@ -296,18 +271,6 @@ class Security extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="访问安全"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="IP访问规则限制"
>
</PageHeader>
<Content className="site-layout-background page-content">
<div style={{marginBottom: 20}}>

View File

@ -7,7 +7,6 @@ import {
Layout,
Modal,
notification,
PageHeader,
Row,
Select,
Space,
@ -18,7 +17,7 @@ import {
} from "antd";
import qs from "qs";
import request from "../../common/request";
import {differTime, itemRender} from "../../utils/utils";
import {differTime} from "../../utils/utils";
import Playback from "./Playback";
import {message} from "antd/es";
import {DeleteOutlined, ExclamationCircleOutlined, SyncOutlined, UndoOutlined} from "@ant-design/icons";
@ -30,16 +29,6 @@ const confirm = Modal.confirm;
const {Content} = Layout;
const {Search} = Input;
const {Title, Text} = Typography;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'offlineSession',
breadcrumbName: '离线会话',
}
];
class OfflineSession extends Component {
@ -365,18 +354,6 @@ class OfflineSession extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="离线会话"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="离线会话管理"
>
</PageHeader>
<Content className="site-layout-background page-content">
<div style={{marginBottom: 20}}>
<Row justify="space-around" align="middle" gutter={24}>

View File

@ -8,7 +8,6 @@ import {
Layout,
Modal,
notification,
PageHeader,
Row,
Select,
Space,
@ -19,7 +18,7 @@ import {
} from "antd";
import qs from "qs";
import request from "../../common/request";
import {differTime, itemRender} from "../../utils/utils";
import {differTime} from "../../utils/utils";
import {message} from "antd/es";
import {PROTOCOL_COLORS} from "../../common/constants";
import {DisconnectOutlined, ExclamationCircleOutlined, SyncOutlined, UndoOutlined} from "@ant-design/icons";
@ -31,16 +30,6 @@ const confirm = Modal.confirm;
const {Content} = Layout;
const {Search} = Input;
const {Title, Text} = Typography;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'onlineSession',
breadcrumbName: '在线会话',
}
];
class OnlineSession extends Component {
@ -335,18 +324,6 @@ class OnlineSession extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="在线会话"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="查询实时在线会话"
>
</PageHeader>
<Content className="site-layout-background page-content">
<div style={{marginBottom: 20}}>

View File

@ -1,6 +1,5 @@
import React, {Component} from 'react';
import {Button, Form, Input, Layout, PageHeader, Select, Switch, Tabs, Tooltip, Typography} from "antd";
import {itemRender} from '../../utils/utils'
import {Button, Form, Input, Layout, Select, Switch, Tabs, Tooltip, Typography} from "antd";
import request from "../../common/request";
import {message} from "antd/es";
import {ExclamationCircleOutlined} from "@ant-design/icons";
@ -10,17 +9,6 @@ const {Option} = Select;
const {TabPane} = Tabs;
const {Title} = Typography;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'setting',
breadcrumbName: '系统设置',
}
];
const formItemLayout = {
labelCol: {span: 12},
wrapperCol: {span: 12},
@ -114,18 +102,6 @@ class Setting extends Component {
render() {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="系统设置"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="系统设置"
>
</PageHeader>
<Content className="site-layout-background page-content">
<Tabs tabPosition={'left'} onChange={this.handleOnTabChange} tabBarStyle={{width: 150}}>

View File

@ -1,6 +1,5 @@
import React, {Component} from 'react';
import {Button, Card, Form, Image, Input, Layout, Modal, PageHeader, Result, Space} from "antd";
import {itemRender} from '../../utils/utils'
import {Button, Card, Form, Image, Input, Layout, Modal, Result, Space} from "antd";
import request from "../../common/request";
import {message} from "antd/es";
import {ExclamationCircleOutlined, ReloadOutlined} from "@ant-design/icons";
@ -8,17 +7,6 @@ import {ExclamationCircleOutlined, ReloadOutlined} from "@ant-design/icons";
const {Content} = Layout;
const {Meta} = Card;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'info',
breadcrumbName: '个人中心',
}
];
const formItemLayout = {
labelCol: {span: 3},
wrapperCol: {span: 6},
@ -121,17 +109,6 @@ class Info extends Component {
render() {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="个人中心"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="个人中心"
/>
<Content className="site-layout-background page-content">
<h1>修改密码</h1>
<Form ref={this.passwordFormRef} name="password" onFinish={this.changePassword}>

View File

@ -1,87 +0,0 @@
import React, {Component} from 'react';
import {Col, Dropdown, Menu, message, Popconfirm, Row, Tooltip} from "antd";
import request from "../../common/request";
import {getCurrentUser} from "../../service/permission";
import {GithubOutlined, LogoutOutlined, QuestionCircleOutlined, SolutionOutlined} from "@ant-design/icons";
import {Link} from "react-router-dom";
class LayoutHeader extends Component {
confirm = async (e) => {
let result = await request.post('/logout');
if (result['code'] !== 1) {
message.error(result['message']);
} else {
message.success('退出登录成功,即将跳转至登录页面。');
window.location.reload();
}
}
render() {
const menu = (
<Menu>
<Menu.Item>
<Link to={'/info'}>
<SolutionOutlined/>
个人中心
</Link>
</Menu.Item>
<Menu.Item>
<a target='_blank' rel="noreferrer" href='https://github.com/dushixiang/next-terminal'>
<GithubOutlined/>
点个Star
</a>
</Menu.Item>
<Menu.Divider/>
<Menu.Item>
<Popconfirm
key='login-btn-pop'
title="您确定要退出登录吗?"
onConfirm={this.confirm}
okText="确定"
cancelText="取消"
placement="left"
>
<LogoutOutlined/>
退出登录
</Popconfirm>
</Menu.Item>
</Menu>
);
return (
<div className='layout-header'>
<Row justify="space-around" align="middle" gutter={24} style={{height: 48}}>
<Col span={4} key={1} style={{height: 48}}> </Col>
<Col span={20} key={2} style={{textAlign: 'right'}} className={'layout-header-right'}>
<div className={'layout-header-right-item'}>
<Tooltip placement="bottom" title={'使用帮助'}>
<a target='_blank' rel="noreferrer" href='https://github.com/dushixiang/next-terminal/blob/master/docs/faq.md'>
<QuestionCircleOutlined/>
</a>
</Tooltip>
</div>
<Dropdown overlay={menu}>
<div className='nickname layout-header-right-item'>{getCurrentUser()['nickname']}</div>
</Dropdown>
</Col>
</Row>
</div>
);
}
}
export default LayoutHeader;

View File

@ -1,5 +1,4 @@
import React, {Component} from 'react';
import {itemRender} from '../../utils/utils'
import {
Badge,
@ -12,7 +11,6 @@ import {
Layout,
Menu,
Modal,
PageHeader,
Row,
Space,
Table,
@ -43,17 +41,6 @@ const {Search} = Input;
const {Title, Text} = Typography;
const {Content} = Layout;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'user',
breadcrumbName: '用户',
}
];
class User extends Component {
inputRefOfNickname = React.createRef();
@ -472,18 +459,6 @@ class User extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="用户管理"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="平台用户管理"
>
</PageHeader>
<Content className="site-layout-background page-content">
<div style={{marginBottom: 20}}>
<Row justify="space-around" align="middle" gutter={24}>

View File

@ -1,7 +1,6 @@
import React, {Component} from 'react';
import {itemRender} from '../../utils/utils'
import {Button, Col, Divider, Input, Layout, Modal, PageHeader, Row, Space, Table, Tooltip, Typography,} from "antd";
import {Button, Col, Divider, Input, Layout, Modal, Row, Space, Table, Tooltip, Typography,} from "antd";
import qs from "qs";
import request from "../../common/request";
import {message} from "antd/es";
@ -15,17 +14,6 @@ const {Search} = Input;
const {Title, Text} = Typography;
const {Content} = Layout;
const routes = [
{
path: '',
breadcrumbName: '首页',
},
{
path: 'user',
breadcrumbName: '用户组',
}
];
class UserGroup extends Component {
inputRefOfName = React.createRef();
@ -334,18 +322,6 @@ class UserGroup extends Component {
return (
<>
<PageHeader
className="site-page-header-ghost-wrapper"
title="用户组管理"
breadcrumb={{
routes: routes,
itemRender: itemRender
}}
subTitle="平台用户管理"
>
</PageHeader>
<Content className="site-layout-background page-content">
<div style={{marginBottom: 20}}>
<Row justify="space-around" align="middle" gutter={24}>