增加在线用户监控

This commit is contained in:
zsvg
2022-06-13 18:04:29 +08:00
parent 2bc7fe2a03
commit 82a928763f
9 changed files with 154 additions and 4 deletions
+1 -1
View File
@@ -2,6 +2,6 @@
ENV = 'development'
# 本地环境接口地址
#VITE_API_URL = 'http://localhost:5000/'
VITE_API_URL = 'http://localhost:5000/'
#VITE_API_URL = 'http://localhost:8088/'
VITE_UI_URL = 'http://localhost:8888/'
+15
View File
@@ -10,6 +10,7 @@
"license": "MIT",
"dependencies": {
"@element-plus/icons-vue": "^1.1.4",
"@svgdotjs/svg.js": "^3.1.2",
"@wangeditor/editor": "^5.0.1",
"axios": "^0.27.2",
"bpmn-js": "^8.1.0",
@@ -1056,6 +1057,15 @@
"node": ">= 8.0.0"
}
},
"node_modules/@svgdotjs/svg.js": {
"version": "3.1.2",
"resolved": "https://registry.npmjs.org/@svgdotjs/svg.js/-/svg.js-3.1.2.tgz",
"integrity": "sha512-0ZCWTiuRjCXT2SUoVDiu+8DLuRQlkxZbO680Y2QkV7jNsULzJajrx6A3MxA/IBQg6UGV5csgPZ8w7U57hZSK+A==",
"funding": {
"type": "github",
"url": "https://github.com/sponsors/Fuzzyma"
}
},
"node_modules/@transloadit/prettier-bytes": {
"version": "0.0.7",
"resolved": "https://registry.npmjs.org/@transloadit/prettier-bytes/-/prettier-bytes-0.0.7.tgz",
@@ -6220,6 +6230,11 @@
"picomatch": "^2.2.2"
}
},
"@svgdotjs/svg.js": {
"version": "3.1.2",
"resolved": "https://registry.npmjs.org/@svgdotjs/svg.js/-/svg.js-3.1.2.tgz",
"integrity": "sha512-0ZCWTiuRjCXT2SUoVDiu+8DLuRQlkxZbO680Y2QkV7jNsULzJajrx6A3MxA/IBQg6UGV5csgPZ8w7U57hZSK+A=="
},
"@transloadit/prettier-bytes": {
"version": "0.0.7",
"resolved": "https://registry.npmjs.org/@transloadit/prettier-bytes/-/prettier-bytes-0.0.7.tgz",
+1
View File
@@ -11,6 +11,7 @@
},
"dependencies": {
"@element-plus/icons-vue": "^1.1.4",
"@svgdotjs/svg.js": "^3.1.2",
"@wangeditor/editor": "^5.0.1",
"axios": "^0.27.2",
"bpmn-js": "^8.1.0",
+10
View File
@@ -91,6 +91,16 @@ const genCode=async (id:string)=>{
});
}
// const genCode=async (id:string)=>{
// await request({
// url: state.url+"/dxf",
// method: 'get',
// params: {id},
// responseType: "blob",
// });
// }
const showRef = ref() as any;
const showCode=async (id:string)=>{
const data= await request({
+85
View File
@@ -0,0 +1,85 @@
<template>
<div>
<el-card class='box-card'>
<template #header>
<el-row>
<el-col :span='14'>
<el-input v-model='state.form.name' placeholder='输入名称回车查询' clearable class='list-search' @keyup.enter='listQuery()' />
<el-button type='primary' @click='listQuery()' :icon='Search' plain>查询</el-button>
</el-col>
<el-col :span='10' style='text-align: right'>
<!-- <el-button type='warning' :icon='Delete' @click='listDelete(state)' plain>删除</el-button>-->
<!-- <el-button type='danger' :icon='Delete' @click='listDeleteAll()' plain>清空</el-button>-->
</el-col>
</el-row>
</template>
<el-table height='400' :cell-style="{padding:'2px'}" :row-style="{height: '36px'}" v-loading='state.loading' :data='state.list'
border stripe @selection-change='listSelect($event,state)'>
<el-table-column type='selection' width='55' align='center' />
<el-table-column label='序号' type='index' width='55' align='center' />
<el-table-column label='用户姓名' width='100' prop='name' />
<el-table-column label='用户账号' prop='usnam' width='100' />
<el-table-column label='登录时间' prop='crtim' width='180'/>
<el-table-column label='登录IP' prop='ip' width='120' />
<el-table-column label='登录地点' prop='addre' width='160' />
<el-table-column label='操作系统' prop='ageos' width='150' />
<el-table-column label='浏览器' prop='agbro' />
</el-table>
<el-pagination
@size-change='pageChange' @current-change='pageChange'
class='mt8' :pager-count='5' :page-sizes='[10, 20, 30]' background
:total='state.total' v-model:current-page='state.form.page' v-model:page-size='state.form.pageSize'
layout='total, sizes, prev, pager, next, jumper'
/>
</el-card>
</div>
</template>
<script lang='ts'>
export default { name: 'MonLogLogin' };
</script>
<script lang='ts' setup>
import { Search } from '@element-plus/icons-vue';
import { onMounted, reactive, ref } from 'vue';
import { listSelect } from '/@/comps/page';
import request from '/@/utils/request';
const drawer = ref();
const state = reactive({
url: '/mon/online/user', loading: true, ids: [], totalList: [] as any,
form: { page: 1, pageSize: 10 }, single: true, multiple: true, list: [], total: 0,
});
onMounted(() => {
listQuery();
});
async function listQuery() {
state.totalList = await request({
url: state.url+"/list",
method: 'get',
params: state.form,
});
state.total = state.totalList.length;
state.loading = false;
state.list = state.totalList.slice(
(state.form.page - 1) * state.form.pageSize,
state.form.pageSize * state.form.pageSize,
);
}
const pageChange = () => {
state.list = state.totalList.slice(
(state.form.page - 1) * state.form.pageSize,
state.form.pageSize * state.form.pageSize,
);
}
</script>
<style scoped>
</style>
+5
View File
@@ -62,6 +62,7 @@
</el-tabs>
</el-form>
</div>
<div id="simpleSquare"></div>
<OrgModal ref='orgModal' @close='closeOrgModal'/>
<Amap ref='amapRef' @close='closeAmap'/>
</el-card>
@@ -77,6 +78,7 @@ import OrgModal from '/@/comps/sys/OrgModal.vue';
import Amap from '/@/comps/ass/amap.vue';
import {FormInstance} from "element-plus";
import request from "/@/utils/request";
import { SVG } from "@svgdotjs/svg.js"
const route = useRoute();
const formRef = ref<FormInstance>();
@@ -95,6 +97,9 @@ const {form} = toRefs(state);
onMounted(async () => {
await editInit({state, route});
await levelsInit();
let shapeModel = SVG().addTo("#simpleSquare").size("100%", "100%");
shapeModel.rect(100, 100).attr({ fill: "#00B1B6" });
//http://t.zoukankan.com/onesea-p-15292991.html
});
+18 -1
View File
@@ -11,7 +11,7 @@
<el-col :span='10' style='text-align: right'>
<el-button type='success' :icon='Plus' @click='tabAdd(state.url)' plain>新增</el-button>
<el-button type='info' :icon='Upload' @click='listImp' plain>导入</el-button>
<el-button type='info' :icon='Download' plain @click='listExp' >导出</el-button>
<el-button type='info' :icon='Download' plain @click='listExp3' >导出</el-button>
<el-button type='danger' :icon='Delete' :disabled='state.multiple' @click='listDelete(state)' plain>删除</el-button>
</el-col>
</el-row>
@@ -85,6 +85,23 @@ const listExp=async ()=>{
});
}
const listExp2=async ()=>{
await request({
url: "/ass/coge/table/download",
method: 'get',
params: state.form,
responseType: "blob",
});
}
const listExp3=async ()=>{
await request({
url: state.url+"/exp3",
method: 'get',
params: state.form,
responseType: "blob",
});
}
const uploadModal = ref();
+15
View File
@@ -358,6 +358,21 @@ export const sysRoutes: Array<RouteRecordRaw> = [
icon: 'ele-DataLine',
},
children: [
{
path: '/mon/online/user',
name: 'MonOnlineUser',
component: () => import('/@/pages/mon/online/user/index.vue'),
meta: {
title: '在线用户',
isLink: '',
isHide: false,
isKeepAlive: true,
isAffix: false,
isIframe: false,
roles: ['admin'],
icon: 'ele-Tickets',
},
},
{
path: '/mon/log/login',
name: 'MonLogLogin',
+4 -2
View File
@@ -86,11 +86,13 @@ service.interceptors.response.use(
});
} else if (error.response.status == 403) {
ElMessage.error('权限不足');
} else if (error.response.status == 500) {
} else if (error.response.status == 404) {
ElMessage.error('接口地址不存在');
} else if (error.response.status == 500) {
ElMessage.error('服务器内部错误');
} else {
if (error.response.data) ElMessage.error(error.response.statusText);
else ElMessage.error('接口路径找不到');
else ElMessage.error('未知错误');
}
return Promise.reject(error);
}