1. 添加后台管理实现:对项目、设备、人员、传感器的增删改查
2. 集成数据查询功能
This commit is contained in:
parent
40149cb58c
commit
666460a0d9
@ -11,7 +11,9 @@
|
||||
"ant-design-vue": "^1.7.0",
|
||||
"axios": "^0.21.0",
|
||||
"core-js": "^3.6.5",
|
||||
"echarts": "^4.9.0",
|
||||
"ol": "^6.4.3",
|
||||
"v-charts": "^1.19.0",
|
||||
"vue": "^2.6.11",
|
||||
"vue-router": "^3.4.8",
|
||||
"vuex": "^3.5.1"
|
||||
|
@ -2,8 +2,8 @@
|
||||
<a-layout>
|
||||
<a-layout-header style="height: 110px;">
|
||||
<a-row>
|
||||
<a-col :span="12">
|
||||
水质监测平台
|
||||
<a-col :span="12" style="color:white;">
|
||||
<span class="w-title">水质监测平台</span>
|
||||
</a-col>
|
||||
<a-col :span="2" :offset="10">
|
||||
<a-button icon="logout" @click="logout" >登出</a-button>
|
||||
@ -11,34 +11,27 @@
|
||||
</a-row>
|
||||
<a-row>
|
||||
<a-menu v-model="current" mode="horizontal" theme="dark" @click="handleMenuClick">
|
||||
<a-menu-item key="map">
|
||||
<a-menu-item key="map-layout">
|
||||
<icon-font type="wt-iconmap" />主页
|
||||
</a-menu-item>
|
||||
<a-sub-menu>
|
||||
<span slot="title" class="submenu-title-wrapper"
|
||||
><icon-font type="wt-iconsearch" />数据查询</span
|
||||
>
|
||||
<a-menu-item-group title="Item 1">
|
||||
<a-menu-item key="search"> 详细信息 </a-menu-item>
|
||||
<a-menu-item key="setting:2"> Option 2 </a-menu-item>
|
||||
</a-menu-item-group>
|
||||
<a-menu-item-group title="Item 2">
|
||||
<a-menu-item key="setting:3"> Option 3 </a-menu-item>
|
||||
<a-menu-item key="setting:4"> Option 4 </a-menu-item>
|
||||
</a-menu-item-group>
|
||||
<a-menu-item key="detail-search"> <icon-font type="wt-iconxiangxi" />详细数据 </a-menu-item>
|
||||
</a-sub-menu>
|
||||
<a-menu-item key="analysis">
|
||||
<icon-font type="wt-iconmap" />图形分析
|
||||
<icon-font type="wt-iconfenxi" />图形分析
|
||||
</a-menu-item>
|
||||
<a-menu-item key="admin" v-if="isAdmin">
|
||||
<icon-font type="wt-iconmap" />后台管理
|
||||
<icon-font type="wt-iconhoutai" />后台管理
|
||||
</a-menu-item>
|
||||
|
||||
</a-menu>
|
||||
</a-row>
|
||||
</a-layout-header>
|
||||
<a-layout-content>
|
||||
<keep-alive >
|
||||
<keep-alive>
|
||||
<component :is="currentComp"/>
|
||||
</keep-alive>
|
||||
</a-layout-content>
|
||||
@ -49,7 +42,9 @@
|
||||
|
||||
import IconFont from '@/components/icon'
|
||||
import MapLayout from '@/components/map/Index'
|
||||
import Search from '@/components/search/Index'
|
||||
import DetailSearch from '@/components/search/Index'
|
||||
import Analysis from '@/components/analysis/Index'
|
||||
|
||||
import Logs from '@/components/logs/Index'
|
||||
import Admin from '@/components/admin/Index'
|
||||
import { logout } from '@/utils/http'
|
||||
@ -57,13 +52,14 @@ export default {
|
||||
components: {
|
||||
'icon-font':IconFont,
|
||||
'map-layout':MapLayout,
|
||||
'search':Search,
|
||||
'detail-search':DetailSearch,
|
||||
'analysis':Analysis,
|
||||
// 'logs':Logs,
|
||||
'admin':Admin
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
current:['map'],
|
||||
current:['map-layout'],
|
||||
currentComp: 'map-layout'
|
||||
};
|
||||
},
|
||||
@ -95,4 +91,11 @@ export default {
|
||||
.ant-layout-content {
|
||||
height: calc(100vh - 110px);
|
||||
}
|
||||
.w-title{
|
||||
color: white;
|
||||
line-height: 50px;
|
||||
font-size: 24px;
|
||||
font-weight: 600;
|
||||
|
||||
}
|
||||
</style>
|
@ -20,6 +20,10 @@
|
||||
<a-icon type="inbox" />
|
||||
<span>项目</span>
|
||||
</a-menu-item>
|
||||
<a-menu-item key="user-table">
|
||||
<a-icon type="user" />
|
||||
<span>人员</span>
|
||||
</a-menu-item>
|
||||
</a-menu>
|
||||
</a-layout-sider>
|
||||
<a-layout>
|
||||
@ -35,13 +39,14 @@
|
||||
import SensorTable from "./tables/SensorTable";
|
||||
import DeviceTable from './tables/DeviceTable';
|
||||
import ProjectTable from './tables/ProjectTable';
|
||||
|
||||
import UserTable from './tables/UserTable';
|
||||
import { getData, URL_MAP } from "@/utils/http";
|
||||
export default {
|
||||
components: {
|
||||
'sensor-table':SensorTable,
|
||||
'device-table':DeviceTable,
|
||||
'project-table':ProjectTable
|
||||
'project-table':ProjectTable,
|
||||
'user-table':UserTable
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
|
136
src/components/admin/forms/DeviceDetail.vue
Normal file
136
src/components/admin/forms/DeviceDetail.vue
Normal file
@ -0,0 +1,136 @@
|
||||
<template>
|
||||
<div>
|
||||
<a-form-model :model="form">
|
||||
<a-form-model-item label="设备ID">
|
||||
<a-input :disabled="isCreate" v-model="form._id" />
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="设备名称">
|
||||
<a-input v-model="form.device_name" />
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="设备型号">
|
||||
<a-input v-model="form.device_uint" />
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="是否公开">
|
||||
<a-switch v-model="form.isanyone" />
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="传感器">
|
||||
<a-select
|
||||
mode="multiple"
|
||||
v-model="form.sensors"
|
||||
@search="searchSensors"
|
||||
:filter-option="false"
|
||||
:not-found-content="fetching ? undefined : null"
|
||||
>
|
||||
<a-spin v-if="fetching" slot="notFoundContent" size="small" />
|
||||
<a-select-option v-for="u in sensors" :key="u._id">
|
||||
{{ u.name }}
|
||||
</a-select-option>
|
||||
</a-select>
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="所属项目">
|
||||
<a-select
|
||||
show-search
|
||||
v-model="form.project"
|
||||
@search="searchPorjects"
|
||||
:filter-option="false"
|
||||
:not-found-content="fetching ? undefined : null"
|
||||
>
|
||||
<a-spin v-if="fetching" slot="notFoundContent" size="small" />
|
||||
<a-select-option v-for="u in projects" :key="u._id">
|
||||
{{ u.name }}
|
||||
</a-select-option>
|
||||
</a-select>
|
||||
</a-form-model-item>
|
||||
<a-form-model-item :wrapper-col="{ span: 14, offset: 4 }">
|
||||
<a-button type="primary" @click="onSubmit"> 确认 </a-button>
|
||||
<a-button style="margin-left: 10px" @click="$emit('cancle')">
|
||||
关闭
|
||||
</a-button>
|
||||
</a-form-model-item>
|
||||
</a-form-model>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { mergeList } from "@/utils/utils";
|
||||
import { getData, URL_MAP } from "@/utils/http";
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
form: {
|
||||
_id: "",
|
||||
device_name: "",
|
||||
device_uint: "",
|
||||
sensors: [],
|
||||
project:'',
|
||||
state: 0,
|
||||
isanyone: false,
|
||||
position: "",
|
||||
},
|
||||
sensors: [],
|
||||
projects: [],
|
||||
fetching: false,
|
||||
isCreate: true,
|
||||
};
|
||||
},
|
||||
props: {
|
||||
detail: Object,
|
||||
},
|
||||
methods: {
|
||||
onSubmit() {
|
||||
this.$emit("ok", this.form);
|
||||
},
|
||||
async searchPorjects(value) {
|
||||
this.fetching = true;
|
||||
try {
|
||||
let data = await getData(URL_MAP.PROJECT_LIST, {
|
||||
name__icontains: name,
|
||||
});
|
||||
this.projects = mergeList(data.data, this.projects);
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
} finally {
|
||||
this.fetching = false;
|
||||
}
|
||||
},
|
||||
async searchSensors(name) {
|
||||
this.fetching = true;
|
||||
try {
|
||||
let data = await getData(URL_MAP.SENSOR_LIST, {
|
||||
name__icontains: name,
|
||||
});
|
||||
this.sensors = mergeList(data.data, this.sensors);
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
} finally {
|
||||
this.fetching = false;
|
||||
}
|
||||
},
|
||||
},
|
||||
mounted() {
|
||||
for (let key in this.form) {
|
||||
this.form[key] = this.detail[key];
|
||||
}
|
||||
this.isCreate = !!this.form._id
|
||||
if(this.detail.sensors) {
|
||||
this.form.sensors = this.form.sensors.map((v) => v._id);
|
||||
this.sensors = this.detail.sensors
|
||||
}
|
||||
else{
|
||||
this.form.sensors = []
|
||||
this.sensors = []
|
||||
}
|
||||
if(this.detail.project) {
|
||||
this.form.project = this.form.project._id
|
||||
this.projects = [this.detail.project,];
|
||||
}else{
|
||||
this.form.project = null
|
||||
this.projects = []
|
||||
}
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style>
|
||||
</style>
|
118
src/components/admin/forms/ProjectDetail.vue
Normal file
118
src/components/admin/forms/ProjectDetail.vue
Normal file
@ -0,0 +1,118 @@
|
||||
<template>
|
||||
<div>
|
||||
<a-form-model :model="form">
|
||||
<a-form-model-item label="项目名">
|
||||
<a-input v-model="form.name" />
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="管理员">
|
||||
<a-select
|
||||
mode="multiple"
|
||||
v-model="form.managers"
|
||||
@search="searchManagers"
|
||||
:filter-option="false"
|
||||
:not-found-content="fetching ? undefined : null"
|
||||
>
|
||||
<a-spin v-if="fetching" slot="notFoundContent" size="small" />
|
||||
<a-select-option v-for="u in managers" :key="u._id">
|
||||
{{u.name || u.username}}
|
||||
</a-select-option>
|
||||
</a-select>
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="普通用户">
|
||||
<a-select
|
||||
mode="multiple"
|
||||
v-model="form.normals"
|
||||
@search="searchNormals"
|
||||
:filter-option="false"
|
||||
:not-found-content="fetching ? undefined : null"
|
||||
>
|
||||
<a-spin v-if="fetching" slot="notFoundContent" size="small" />
|
||||
<a-select-option v-for="u in normals" :key="u._id">
|
||||
{{u.name || u.username}}
|
||||
</a-select-option>
|
||||
</a-select>
|
||||
</a-form-model-item>
|
||||
<a-form-model-item :wrapper-col="{ span: 14, offset: 4 }">
|
||||
<a-button type="primary" @click="onSubmit">
|
||||
确认
|
||||
</a-button>
|
||||
<a-button style="margin-left: 10px;" @click="$emit('cancle')">
|
||||
关闭
|
||||
</a-button>
|
||||
</a-form-model-item>
|
||||
</a-form-model>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { mergeList } from '@/utils/utils';
|
||||
import { getData, URL_MAP } from '@/utils/http';
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
form: {
|
||||
_id:'',
|
||||
name:'',
|
||||
managers:[],
|
||||
normals:[]
|
||||
},
|
||||
managers: [],
|
||||
normals: [],
|
||||
fetching: false,
|
||||
}
|
||||
},
|
||||
props: {
|
||||
detail:Object
|
||||
},
|
||||
methods: {
|
||||
onSubmit() {
|
||||
this.$emit('ok', this.form)
|
||||
},
|
||||
async searchManagers(value) {
|
||||
this.fetching = true
|
||||
try{
|
||||
let data = await getData(URL_MAP.USER_LIST, {
|
||||
'username__icontains':name,
|
||||
'permission__gte':0x0ff
|
||||
})
|
||||
this.managers = mergeList(data.data, this.managers)
|
||||
}
|
||||
catch(e) {
|
||||
console.log(e)
|
||||
}finally{
|
||||
this.fetching = false
|
||||
}
|
||||
},
|
||||
async searchNormals(name, permission) {
|
||||
this.fetching = true
|
||||
try{
|
||||
let data = await getData(URL_MAP.USER_LIST, {
|
||||
'username__icontains':name,
|
||||
'permission__gte':0x00f
|
||||
})
|
||||
this.normals = mergeList(data.data, this.normals)
|
||||
}
|
||||
catch(e) {
|
||||
console.log(e)
|
||||
}finally{
|
||||
this.fetching = false
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
},
|
||||
mounted() {
|
||||
for(let key in this.form) {
|
||||
this.form[key] = this.detail[key]
|
||||
}
|
||||
this.form.managers = this.form.managers.map(v => v._id)
|
||||
this.form.normals = this.form.normals.map(v => v._id)
|
||||
this.managers = this.detail.managers
|
||||
this.normals = this.detail.normals
|
||||
}
|
||||
};
|
||||
</script>
|
||||
|
||||
<style>
|
||||
</style>
|
57
src/components/admin/forms/SensorDetai.vue
Normal file
57
src/components/admin/forms/SensorDetai.vue
Normal file
@ -0,0 +1,57 @@
|
||||
<template>
|
||||
<div>
|
||||
<a-form-model :model="form">
|
||||
<a-form-model-item label="名称">
|
||||
<a-input v-model="form.name" />
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="参数名">
|
||||
<a-input v-model="form.param_name" />
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="参数key">
|
||||
<a-input v-model="form.param_key" />
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="单位">
|
||||
<a-input v-model="form.uint" />
|
||||
</a-form-model-item>
|
||||
|
||||
<a-form-model-item :wrapper-col="{ span: 14, offset: 4 }">
|
||||
<a-button type="primary" @click="onSubmit"> 确认 </a-button>
|
||||
<a-button style="margin-left: 10px" @click="$emit('cancle')">
|
||||
关闭
|
||||
</a-button>
|
||||
</a-form-model-item>
|
||||
</a-form-model>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
form: {
|
||||
_id: "",
|
||||
name: "",
|
||||
param_name: "",
|
||||
param_key: '',
|
||||
uint:''
|
||||
},
|
||||
};
|
||||
},
|
||||
props: {
|
||||
detail: Object,
|
||||
},
|
||||
methods: {
|
||||
onSubmit() {
|
||||
this.$emit("ok", this.form);
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
for (let key in this.form) {
|
||||
this.form[key] = this.detail[key];
|
||||
}
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style>
|
||||
</style>
|
73
src/components/admin/forms/UserDetail.vue
Normal file
73
src/components/admin/forms/UserDetail.vue
Normal file
@ -0,0 +1,73 @@
|
||||
<template>
|
||||
<div>
|
||||
<a-form-model :model="form">
|
||||
<a-form-model-item label="用户名">
|
||||
<a-input v-model="form.username" />
|
||||
</a-form-model-item>
|
||||
<a-form-model-item label="权限">
|
||||
<a-select
|
||||
v-model="form.permission"
|
||||
>
|
||||
<a-select-option v-for="p in permissionMaps" :key="p.key">
|
||||
{{p.name}}
|
||||
</a-select-option>
|
||||
</a-select>
|
||||
</a-form-model-item>
|
||||
|
||||
<a-form-model-item :wrapper-col="{ span: 14, offset: 4 }">
|
||||
<a-button type="primary" @click="onSubmit"> 确认 </a-button>
|
||||
<a-button style="margin-left: 10px" @click="$emit('cancle')">
|
||||
关闭
|
||||
</a-button>
|
||||
</a-form-model-item>
|
||||
</a-form-model>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
form: {
|
||||
_id: "",
|
||||
username: "",
|
||||
permission: 0x000,
|
||||
},
|
||||
permissionMaps: [
|
||||
{
|
||||
key:0xfff,
|
||||
name: '超级管理员',
|
||||
},
|
||||
{
|
||||
key:0x0ff,
|
||||
name: '项目管理员',
|
||||
},
|
||||
{
|
||||
key:0x00f,
|
||||
name: '普通用户',
|
||||
},
|
||||
{
|
||||
key:0x000,
|
||||
name: '游客',
|
||||
}
|
||||
],
|
||||
};
|
||||
},
|
||||
props: {
|
||||
detail: Object,
|
||||
},
|
||||
methods: {
|
||||
onSubmit() {
|
||||
this.$emit("ok", this.form);
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
for (let key in this.form) {
|
||||
this.form[key] = this.detail[key];
|
||||
}
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style>
|
||||
</style>
|
@ -1,5 +1,8 @@
|
||||
<template>
|
||||
<div>
|
||||
<div style="margin: 20px">
|
||||
<a-row style="margin-bottom: 20px">
|
||||
<a-button type="primary" @click="handleCreate">添加</a-button>
|
||||
</a-row>
|
||||
<a-table
|
||||
:columns="tableCols"
|
||||
:data-source="tableRows"
|
||||
@ -7,107 +10,166 @@
|
||||
:rowKey="idName"
|
||||
@change="handleTableChange"
|
||||
>
|
||||
<span slot="anyone" slot-scope="isanyone">
|
||||
<a-tag v-if="isanyone">
|
||||
是
|
||||
</a-tag>
|
||||
<a-tag v-else>
|
||||
否
|
||||
</a-tag>
|
||||
</span>
|
||||
<span slot="project" slot-scope="project">
|
||||
<a-tag v-if="project !== null">
|
||||
{{ project.name}}
|
||||
</a-tag>
|
||||
</span>
|
||||
<span slot="action" slot-scope="text, record">
|
||||
<a-button size="small" type="link" @click="() => handleDetail(record)" >查看</a-button>
|
||||
<a-divider type="vertical" />
|
||||
<a-button type="danger" size="small" @click="() => handleDelete(record)" >删除</a-button>
|
||||
</span>
|
||||
<span slot="anyone" slot-scope="isanyone">
|
||||
<a-tag v-if="isanyone"> 是 </a-tag>
|
||||
<a-tag v-else> 否 </a-tag>
|
||||
</span>
|
||||
<span slot="project" slot-scope="project">
|
||||
<a-tag v-if="project !== null">
|
||||
{{ project.name }}
|
||||
</a-tag>
|
||||
</span>
|
||||
<span slot="action" slot-scope="text, record">
|
||||
<a-button size="small" type="link" @click="() => handleDetail(record)"
|
||||
>查看</a-button
|
||||
>
|
||||
<a-divider type="vertical" />
|
||||
<a-button type="danger" size="small" @click="() => handleDelete(record)"
|
||||
>删除</a-button
|
||||
>
|
||||
</span>
|
||||
</a-table>
|
||||
<a-modal
|
||||
v-model="visible"
|
||||
:title="isCreate ? '添加设备' : '查看设备'"
|
||||
:destroyOnClose="true"
|
||||
:footer="null"
|
||||
>
|
||||
<device-detail
|
||||
:detail="record"
|
||||
@ok="handleOk"
|
||||
@cancle="visible = false"
|
||||
/>
|
||||
</a-modal>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { getData, URL_MAP } from '@/utils/http'
|
||||
import { deleteJSON, patchJSON, postJSON, getData, URL_MAP } from "@/utils/http";
|
||||
import DeviceDetail from "../forms/DeviceDetail.vue";
|
||||
export default {
|
||||
components: { DeviceDetail },
|
||||
data() {
|
||||
return {
|
||||
tableRows: [],
|
||||
tableCols: [
|
||||
{
|
||||
dataIndex: '_id',
|
||||
key: '_id',
|
||||
title: '设备ID'
|
||||
dataIndex: "_id",
|
||||
key: "_id",
|
||||
title: "设备ID",
|
||||
},
|
||||
{
|
||||
dataIndex: 'device_name',
|
||||
key: 'device_name',
|
||||
title: '设备名称'
|
||||
dataIndex: "device_name",
|
||||
key: "device_name",
|
||||
title: "设备名称",
|
||||
},
|
||||
{
|
||||
dataIndex: 'device_uint',
|
||||
key: 'device_uint',
|
||||
title: '设备型号'
|
||||
dataIndex: "device_uint",
|
||||
key: "device_uint",
|
||||
title: "设备型号",
|
||||
},
|
||||
{
|
||||
dataIndex: 'isanyone',
|
||||
key: 'isanyone',
|
||||
title: '是否公开',
|
||||
scopedSlots: { customRender: 'anyone' },
|
||||
dataIndex: "isanyone",
|
||||
key: "isanyone",
|
||||
title: "是否公开",
|
||||
scopedSlots: { customRender: "anyone" },
|
||||
},
|
||||
{
|
||||
dataIndex: 'project',
|
||||
key: 'project',
|
||||
title: '所属项目',
|
||||
scopedSlots: { customRender: 'project' }
|
||||
dataIndex: "project",
|
||||
key: "project",
|
||||
title: "所属项目",
|
||||
scopedSlots: { customRender: "project" },
|
||||
},
|
||||
{
|
||||
key: 'action',
|
||||
title: '操作',
|
||||
scopedSlots: { customRender: 'action' },
|
||||
}
|
||||
key: "action",
|
||||
title: "操作",
|
||||
scopedSlots: { customRender: "action" },
|
||||
},
|
||||
],
|
||||
pages: {},
|
||||
loading: false,
|
||||
listUrl: URL_MAP.DEVICE_LIST,
|
||||
detailUrl: URL_MAP.DEVICE_DETAIL,
|
||||
idName: '_id'
|
||||
idName: "_id",
|
||||
visible: false,
|
||||
record: {},
|
||||
isCreate: false,
|
||||
};
|
||||
},
|
||||
methods: {
|
||||
handleTableChange(pagination, filters, sorter) {
|
||||
console.log(pagination)
|
||||
console.log(pagination);
|
||||
},
|
||||
async fetch(params) {
|
||||
this.loading = true
|
||||
try{
|
||||
let results = await getData(this.listUrl, params)
|
||||
let data = results.data
|
||||
const pagination = { ...this.pages }
|
||||
pagination.total = data.length
|
||||
this.tableRows = data
|
||||
this.pages = pagination
|
||||
}catch(e)
|
||||
{
|
||||
console.log(e)
|
||||
}finally{
|
||||
this.loading = false
|
||||
this.loading = true;
|
||||
try {
|
||||
let results = await getData(this.listUrl, params);
|
||||
let data = results.data;
|
||||
const pagination = { ...this.pages };
|
||||
pagination.total = data.length;
|
||||
this.tableRows = data;
|
||||
this.pages = pagination;
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
} finally {
|
||||
this.loading = false;
|
||||
}
|
||||
|
||||
},
|
||||
handleDetail(record) {
|
||||
console.log(record)
|
||||
// console.log(record)
|
||||
this.visible = true;
|
||||
this.record = record;
|
||||
},
|
||||
handleDelete(record) {
|
||||
console.log(record)
|
||||
async handleDelete(record) {
|
||||
this.loading = true
|
||||
try{
|
||||
await deleteJSON(URL_MAP.DEVICE_DETAIL, { 'id': record._id })
|
||||
await this.fetch({})
|
||||
}catch(e)
|
||||
{
|
||||
console.log(e)
|
||||
}
|
||||
finally{
|
||||
this.loading = false
|
||||
}
|
||||
},
|
||||
async handleOk(form) {
|
||||
this.visible = false;
|
||||
this.loading = true;
|
||||
try {
|
||||
if (!this.isCreate) {
|
||||
form["id"] = form["_id"];
|
||||
console.log(form)
|
||||
let data = await patchJSON(URL_MAP.DEVICE_DETAIL, form);
|
||||
} else {
|
||||
form["id"] = form["_id"];
|
||||
let data = await postJSON(URL_MAP.DEVICE_LIST, form);
|
||||
}
|
||||
await this.fetch({});
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
} finally {
|
||||
this.isCreate = false;
|
||||
this.loading = false;
|
||||
}
|
||||
},
|
||||
handleCreate() {
|
||||
this.isCreate = true
|
||||
this.visible = true
|
||||
this.record = {
|
||||
'_id':'',
|
||||
'device_name':'',
|
||||
'device_uint':'',
|
||||
'isanyone':false,
|
||||
'state':0,
|
||||
'sensors':[],
|
||||
'project':null
|
||||
}
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.fetch({})
|
||||
}
|
||||
|
||||
this.fetch({});
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
|
@ -1,5 +1,8 @@
|
||||
<template>
|
||||
<div>
|
||||
<div style="margin: 20px">
|
||||
<a-row style="margin-bottom: 20px">
|
||||
<a-button type="primary" @click="handleCreate">添加</a-button>
|
||||
</a-row>
|
||||
<a-table
|
||||
:columns="tableCols"
|
||||
:data-source="tableRows"
|
||||
@ -7,95 +10,155 @@
|
||||
:rowKey="idName"
|
||||
@change="handleTableChange"
|
||||
>
|
||||
|
||||
<span slot="managers" slot-scope="managers">
|
||||
<a-tag v-for="item in managers" :key="item._id">
|
||||
{{ item.name}}
|
||||
</a-tag>
|
||||
</span>
|
||||
<span slot="normals" slot-scope="normals">
|
||||
<a-tag v-for="item in normals" :key="item._id">
|
||||
{{ item.name}}
|
||||
</a-tag>
|
||||
</span>
|
||||
<span slot="action" slot-scope="text, record">
|
||||
<a-button size="small" type="link" @click="() => handleDetail(record)" >查看</a-button>
|
||||
<a-divider type="vertical" />
|
||||
<a-button type="danger" size="small" @click="() => handleDelete(record)" >删除</a-button>
|
||||
</span>
|
||||
<span slot="managers" slot-scope="managers">
|
||||
<a-tag v-for="item in managers" :key="item._id">
|
||||
{{ item.name }}
|
||||
</a-tag>
|
||||
</span>
|
||||
<span slot="normals" slot-scope="normals">
|
||||
<a-tag v-for="item in normals" :key="item._id">
|
||||
{{ item.name }}
|
||||
</a-tag>
|
||||
</span>
|
||||
<span slot="action" slot-scope="text, record">
|
||||
<a-button size="small" type="link" @click="() => handleDetail(record)"
|
||||
>查看</a-button
|
||||
>
|
||||
<a-divider type="vertical" />
|
||||
<a-button type="danger" size="small" @click="() => handleDelete(record)"
|
||||
>删除</a-button
|
||||
>
|
||||
</span>
|
||||
</a-table>
|
||||
<a-modal
|
||||
v-model="visible"
|
||||
:title="isCreate ? '添加项目' : '查看项目'"
|
||||
:destroyOnClose="true"
|
||||
:footer="null"
|
||||
>
|
||||
<project-detail
|
||||
:detail="record"
|
||||
@ok="handleOk"
|
||||
@cancle="visible = false"
|
||||
/>
|
||||
</a-modal>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { getData, URL_MAP } from '@/utils/http'
|
||||
import { deleteJSON, getData, patchJSON, postJSON, URL_MAP } from "@/utils/http";
|
||||
import ProjectDetail from "../forms/ProjectDetail.vue";
|
||||
|
||||
export default {
|
||||
components: {
|
||||
ProjectDetail,
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
tableRows: [],
|
||||
tableCols: [
|
||||
{
|
||||
dataIndex: 'name',
|
||||
key: 'name',
|
||||
title: '名称'
|
||||
dataIndex: "name",
|
||||
key: "name",
|
||||
title: "名称",
|
||||
},
|
||||
{
|
||||
dataIndex: 'managers',
|
||||
key: 'managers',
|
||||
title: '管理员',
|
||||
scopedSlots: { customRender: 'managers' }
|
||||
dataIndex: "managers",
|
||||
key: "managers",
|
||||
title: "管理员",
|
||||
scopedSlots: { customRender: "managers" },
|
||||
},
|
||||
{
|
||||
dataIndex: 'normals',
|
||||
key: 'normals',
|
||||
title: '普通用户',
|
||||
scopedSlots: { customRender: 'normals' }
|
||||
dataIndex: "normals",
|
||||
key: "normals",
|
||||
title: "普通用户",
|
||||
scopedSlots: { customRender: "normals" },
|
||||
},
|
||||
{
|
||||
key: 'action',
|
||||
title: '操作',
|
||||
scopedSlots: { customRender: 'action' },
|
||||
}
|
||||
key: "action",
|
||||
title: "操作",
|
||||
scopedSlots: { customRender: "action" },
|
||||
},
|
||||
],
|
||||
pages: {},
|
||||
loading: false,
|
||||
listUrl: URL_MAP.PROJECT_LIST,
|
||||
detailUrl: URL_MAP.PROJECT_DETAIL,
|
||||
idName: '_id'
|
||||
idName: "_id",
|
||||
visible: false,
|
||||
record: {},
|
||||
isCreate: false,
|
||||
};
|
||||
},
|
||||
methods: {
|
||||
handleTableChange(pagination, filters, sorter) {
|
||||
console.log(pagination)
|
||||
console.log(pagination);
|
||||
},
|
||||
async fetch(params) {
|
||||
this.loading = true;
|
||||
try {
|
||||
let results = await getData(this.listUrl, params);
|
||||
let data = results.data;
|
||||
const pagination = { ...this.pages };
|
||||
pagination.total = data.length;
|
||||
this.tableRows = data;
|
||||
this.pages = pagination;
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
} finally {
|
||||
this.loading = false;
|
||||
}
|
||||
},
|
||||
handleDetail(record) {
|
||||
this.visible = true;
|
||||
this.record = record;
|
||||
},
|
||||
async handleDelete(record) {
|
||||
this.loading = true
|
||||
try{
|
||||
let results = await getData(this.listUrl, params)
|
||||
let data = results.data
|
||||
const pagination = { ...this.pages }
|
||||
pagination.total = data.length
|
||||
this.tableRows = data
|
||||
this.pages = pagination
|
||||
}catch(e)
|
||||
await deleteJSON(URL_MAP.PROJECT_DETAIL, { 'id': record._id })
|
||||
await this.fetch({})
|
||||
}catch(e)
|
||||
{
|
||||
console.log(e)
|
||||
}finally{
|
||||
}
|
||||
finally{
|
||||
this.loading = false
|
||||
}
|
||||
|
||||
},
|
||||
handleDetail(record) {
|
||||
console.log(record)
|
||||
async handleOk(form) {
|
||||
this.visible = false;
|
||||
this.loading = true;
|
||||
try {
|
||||
if (!this.isCreate) {
|
||||
form["id"] = form["_id"];
|
||||
let data = await patchJSON(URL_MAP.PROJECT_DETAIL, form);
|
||||
} else {
|
||||
form["_id"] = undefined;
|
||||
let data = await postJSON(URL_MAP.PROJECT_LIST, form);
|
||||
}
|
||||
await this.fetch({});
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
} finally {
|
||||
this.isCreate = false;
|
||||
this.loading = false;
|
||||
}
|
||||
},
|
||||
handleCreate() {
|
||||
this.isCreate = true;
|
||||
this.visible = true
|
||||
this.record = {
|
||||
name: null,
|
||||
managers: [],
|
||||
normals: [],
|
||||
};
|
||||
},
|
||||
handleDelete(record) {
|
||||
console.log(record)
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.fetch({})
|
||||
}
|
||||
|
||||
this.fetch({});
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
|
@ -1,5 +1,8 @@
|
||||
<template>
|
||||
<div>
|
||||
<div style="margin: 20px">
|
||||
<a-row style="margin-bottom: 20px">
|
||||
<a-button type="primary" @click="handleCreate">添加</a-button>
|
||||
</a-row>
|
||||
<a-table
|
||||
:columns="tableCols"
|
||||
:data-source="tableRows"
|
||||
@ -13,12 +16,27 @@
|
||||
<a-button type="danger" size="small" @click="() => handleDelete(record)" >删除</a-button>
|
||||
</span>
|
||||
</a-table>
|
||||
<a-modal
|
||||
v-model="visible"
|
||||
:title="isCreate ? '添加设备' : '查看设备'"
|
||||
:destroyOnClose="true"
|
||||
:footer="null"
|
||||
>
|
||||
<sensor-detai
|
||||
:detail="record"
|
||||
@ok="handleOk"
|
||||
@cancle="visible = false"
|
||||
/>
|
||||
</a-modal>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { getData, URL_MAP } from '@/utils/http'
|
||||
import { deleteJSON, patchJSON, postJSON, getData, URL_MAP } from '@/utils/http'
|
||||
import SensorDetai from '../forms/SensorDetai.vue';
|
||||
|
||||
export default {
|
||||
components: { SensorDetai },
|
||||
data() {
|
||||
return {
|
||||
tableRows: [],
|
||||
@ -38,6 +56,11 @@ export default {
|
||||
key: 'param_key',
|
||||
title: '参数key'
|
||||
},
|
||||
{
|
||||
dataIndex: 'uint',
|
||||
key: 'uint',
|
||||
title: '单位'
|
||||
},
|
||||
{
|
||||
key: 'action',
|
||||
title: '操作',
|
||||
@ -48,7 +71,10 @@ export default {
|
||||
loading: false,
|
||||
listUrl: URL_MAP.SENSOR_LIST,
|
||||
detailUrl: URL_MAP.SENSOR_DETAIL,
|
||||
idName: '_id'
|
||||
idName: '_id',
|
||||
visible: false,
|
||||
record: {},
|
||||
isCreate: false,
|
||||
};
|
||||
},
|
||||
methods: {
|
||||
@ -73,10 +99,53 @@ export default {
|
||||
|
||||
},
|
||||
handleDetail(record) {
|
||||
console.log(record)
|
||||
// console.log(record)
|
||||
this.visible = true;
|
||||
this.record = record;
|
||||
},
|
||||
handleDelete(record) {
|
||||
console.log(record)
|
||||
async handleDelete(record) {
|
||||
this.loading = true
|
||||
try{
|
||||
await deleteJSON(URL_MAP.SENSOR_DETAIL, { 'id': record._id })
|
||||
await this.fetch({})
|
||||
}catch(e)
|
||||
{
|
||||
console.log(e)
|
||||
}
|
||||
finally{
|
||||
this.loading = false
|
||||
}
|
||||
},
|
||||
async handleOk(form) {
|
||||
this.visible = false;
|
||||
this.loading = true;
|
||||
try {
|
||||
if (!this.isCreate) {
|
||||
form["id"] = form["_id"];
|
||||
let data = await patchJSON(URL_MAP.SENSOR_DETAIL, form);
|
||||
} else {
|
||||
form["id"] = undefined;
|
||||
form['_id'] = undefined;
|
||||
let data = await postJSON(URL_MAP.SENSOR_LIST, form);
|
||||
}
|
||||
await this.fetch({});
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
} finally {
|
||||
this.isCreate = false;
|
||||
this.loading = false;
|
||||
}
|
||||
},
|
||||
handleCreate() {
|
||||
this.isCreate = true
|
||||
this.visible = true
|
||||
this.record = {
|
||||
'_id':'',
|
||||
'param_name':'',
|
||||
'param_key':'',
|
||||
'name':'',
|
||||
'uint':''
|
||||
}
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
|
157
src/components/admin/tables/UserTable.vue
Normal file
157
src/components/admin/tables/UserTable.vue
Normal file
@ -0,0 +1,157 @@
|
||||
<template>
|
||||
<div style="margin: 20px">
|
||||
<a-row style="margin-bottom: 20px">
|
||||
<a-button type="primary" @click="handleCreate">添加</a-button>
|
||||
</a-row>
|
||||
<a-table
|
||||
:columns="tableCols"
|
||||
:data-source="tableRows"
|
||||
:loading="loading"
|
||||
:rowKey="idName"
|
||||
@change="handleTableChange"
|
||||
>
|
||||
<span slot="permission" slot-scope="permission">
|
||||
<a-tag >
|
||||
{{ permissionMap[permission] }}
|
||||
</a-tag>
|
||||
</span>
|
||||
<span slot="action" slot-scope="text, record">
|
||||
<a-button size="small" type="link" @click="() => handleDetail(record)" >查看</a-button>
|
||||
<a-divider type="vertical" />
|
||||
<a-button type="danger" size="small" @click="() => handleDelete(record)" >删除</a-button>
|
||||
</span>
|
||||
</a-table>
|
||||
<a-modal
|
||||
v-model="visible"
|
||||
:title="isCreate ? '添加用户' : '添加用户'"
|
||||
:destroyOnClose="true"
|
||||
:footer="null"
|
||||
>
|
||||
<user-detail
|
||||
:detail="record"
|
||||
@ok="handleOk"
|
||||
@cancle="visible = false"
|
||||
/>
|
||||
</a-modal>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { deleteJSON, getData, patchJSON, postJSON, URL_MAP } from '@/utils/http'
|
||||
import UserDetail from '../forms/UserDetail.vue';
|
||||
export default {
|
||||
components: { UserDetail },
|
||||
data() {
|
||||
return {
|
||||
tableRows: [],
|
||||
tableCols: [
|
||||
{
|
||||
dataIndex: 'username',
|
||||
key: 'username',
|
||||
title: '用户名'
|
||||
},
|
||||
{
|
||||
dataIndex: 'permission',
|
||||
key: 'permission',
|
||||
title: '用户权限',
|
||||
scopedSlots: { customRender: 'permission' },
|
||||
},
|
||||
{
|
||||
key: 'action',
|
||||
title: '操作',
|
||||
scopedSlots: { customRender: 'action' },
|
||||
}
|
||||
],
|
||||
permissionMap: {
|
||||
0xfff:'超级管理员',
|
||||
0x0ff:'项目管理员',
|
||||
0x00f:'普通用户',
|
||||
0x000:'游客'
|
||||
},
|
||||
pages: {},
|
||||
loading: false,
|
||||
listUrl: URL_MAP.USER_LIST,
|
||||
detailUrl: URL_MAP.DEVICE_DETAIL,
|
||||
idName: '_id',
|
||||
visible: false,
|
||||
record: {},
|
||||
isCreate: false,
|
||||
};
|
||||
},
|
||||
methods: {
|
||||
handleTableChange(pagination, filters, sorter) {
|
||||
console.log(pagination)
|
||||
},
|
||||
async fetch(params) {
|
||||
this.loading = true
|
||||
try{
|
||||
let results = await getData(this.listUrl, params)
|
||||
let data = results.data
|
||||
const pagination = { ...this.pages }
|
||||
pagination.total = data.length
|
||||
this.tableRows = data
|
||||
this.pages = pagination
|
||||
}catch(e)
|
||||
{
|
||||
console.log(e)
|
||||
}finally{
|
||||
this.loading = false
|
||||
}
|
||||
|
||||
},
|
||||
handleDetail(record) {
|
||||
this.visible = true;
|
||||
this.record = record;
|
||||
},
|
||||
async handleDelete(record) {
|
||||
this.loading = true
|
||||
try{
|
||||
await deleteJSON(URL_MAP.USER_DETAIL, { 'id': record._id })
|
||||
await this.fetch({})
|
||||
}catch(e)
|
||||
{
|
||||
console.log(e)
|
||||
}
|
||||
finally{
|
||||
this.loading = false
|
||||
}
|
||||
|
||||
},
|
||||
async handleOk(form) {
|
||||
this.visible = false;
|
||||
this.loading = true;
|
||||
try {
|
||||
if (!this.isCreate) {
|
||||
form["id"] = form["_id"];
|
||||
let data = await patchJSON(URL_MAP.USER_DETAIL, form);
|
||||
} else {
|
||||
form["_id"] = undefined;
|
||||
let data = await postJSON(URL_MAP.USER_LIST, form);
|
||||
}
|
||||
await this.fetch({});
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
} finally {
|
||||
this.isCreate = false;
|
||||
this.loading = false;
|
||||
}
|
||||
},
|
||||
handleCreate() {
|
||||
this.isCreate = true;
|
||||
this.visible = true
|
||||
this.record = {
|
||||
_id:'',
|
||||
username: '',
|
||||
permission: 0x000
|
||||
};
|
||||
},
|
||||
},
|
||||
mounted() {
|
||||
this.fetch({})
|
||||
}
|
||||
|
||||
};
|
||||
</script>
|
||||
|
||||
<style>
|
||||
</style>
|
@ -1,7 +1,7 @@
|
||||
import { Icon } from 'ant-design-vue';
|
||||
|
||||
const IconFont = Icon.createFromIconfontCN({
|
||||
scriptUrl: '//at.alicdn.com/t/font_2205869_701srfkqc5.js', // generated by iconfont.cn
|
||||
scriptUrl: '//at.alicdn.com/t/font_2205869_ablhiuxmevf.js', // generated by iconfont.cn
|
||||
});
|
||||
|
||||
export default IconFont
|
@ -1,18 +1,142 @@
|
||||
<template>
|
||||
<div>
|
||||
<a-layout>
|
||||
<a-layout-sider>Sider</a-layout-sider>
|
||||
<a-layout-content>Content</a-layout-content>
|
||||
</a-layout>
|
||||
<a-row>
|
||||
<a-col :span="12">
|
||||
<a-range-picker
|
||||
separator="至"
|
||||
:placeholder="['开始日期', '结束日期']"
|
||||
:defaultValue="datetimeRange"
|
||||
@change="dateRangeChange"
|
||||
></a-range-picker>
|
||||
</a-col>
|
||||
<a-col :span="12">
|
||||
<a-select
|
||||
v-model="device"
|
||||
placeholder="请选择"
|
||||
@change="onDeviceChange"
|
||||
|
||||
>
|
||||
<a-select-option
|
||||
v-for="item in deviceList"
|
||||
:key="item._id"
|
||||
|
||||
:value="item._id"
|
||||
> {{item.device_name}} </a-select-option>
|
||||
</a-select>
|
||||
</a-col>
|
||||
</a-row>
|
||||
<a-spin :spinning="loading">
|
||||
<a-row>
|
||||
<SZJCChart :dataRow="waterData" :labelMap="labelMap"></SZJCChart>
|
||||
</a-row>
|
||||
</a-spin>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import SZJCChart from "./SZJCChart";
|
||||
import { getData, URL_MAP } from "@/utils/http";
|
||||
import Moment from 'moment'
|
||||
import { processWater } from '@/utils/water'
|
||||
export default {
|
||||
components: {
|
||||
SZJCChart,
|
||||
},
|
||||
data() {
|
||||
return {
|
||||
datetimeRange: [Moment('2020-10-01'), Moment('2020-12-31')],
|
||||
update: false,
|
||||
device: "",
|
||||
deviceList: [],
|
||||
deviceInstance: {},
|
||||
labelMap: {},
|
||||
waterData: [],
|
||||
loading: false,
|
||||
};
|
||||
},
|
||||
watch: {
|
||||
device: function (old, newVal) {
|
||||
for (let i = 0; i < this.deviceList.length; i++) {
|
||||
if (this.deviceList[i]._id === newVal) {
|
||||
this.deviceInstance = this.deviceList[i];
|
||||
break;
|
||||
}
|
||||
}
|
||||
},
|
||||
},
|
||||
methods: {
|
||||
async initSeting() {
|
||||
let sensors = (await getData(URL_MAP.SENSOR_LIST)).data
|
||||
const labelMap = {}
|
||||
sensors.forEach(s => labelMap[s.param_key] = s.param_name)
|
||||
this.labelMap = labelMap
|
||||
},
|
||||
|
||||
}
|
||||
async initDevice() {
|
||||
const device_ = (await getData(URL_MAP.DEVICE_LIST)).data;
|
||||
try {
|
||||
const device = device_.filter((item) => item.state == 1);
|
||||
this.deviceList = device;
|
||||
device.forEach((item) => {
|
||||
Object.keys(this.labelMap).forEach((k) => {
|
||||
if (item[k + "_factor"] === undefined) {
|
||||
item[k + "_factor"] = 1;
|
||||
}
|
||||
});
|
||||
});
|
||||
this.device = device[0]._id
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
}
|
||||
},
|
||||
|
||||
async getData() {
|
||||
this.loading = true
|
||||
try {
|
||||
const params = {
|
||||
'data__collect_time__gte':this.datetimeRange[0].toDate().getTime(),
|
||||
'data__collect_time__lte':this.datetimeRange[1].toDate().getTime(),
|
||||
'device_id':this.device
|
||||
}
|
||||
let data = await getData(URL_MAP.WATER_LIST, params)
|
||||
// console.log(data)
|
||||
this.waterData = processWater(data.data, Object.keys(this.labelMap))
|
||||
// console.log(this.waterData)
|
||||
} catch (e) {
|
||||
console.log(e);
|
||||
this.waterData = [];
|
||||
}
|
||||
finally{
|
||||
this.loading = false
|
||||
}
|
||||
},
|
||||
|
||||
onDeviceChange(value) {
|
||||
this.device = value
|
||||
this.getData();
|
||||
},
|
||||
|
||||
dateRangeChange(dates, dateStrings) {
|
||||
this.datetimeRange = dates;
|
||||
console.log(this.datetimeRange)
|
||||
this.getData();
|
||||
},
|
||||
},
|
||||
|
||||
async mounted() {
|
||||
await this.initSeting();
|
||||
await this.initDevice();
|
||||
this.getData();
|
||||
},
|
||||
};
|
||||
</script>
|
||||
|
||||
<style>
|
||||
|
||||
.el-header,
|
||||
.el-footer {
|
||||
background-color: #b3c0d1;
|
||||
color: #333;
|
||||
text-align: center;
|
||||
line-height: 60px;
|
||||
}
|
||||
</style>
|
112
src/components/search/SZJCChart.vue
Normal file
112
src/components/search/SZJCChart.vue
Normal file
@ -0,0 +1,112 @@
|
||||
<template>
|
||||
<div>
|
||||
<div v-if="hasData">
|
||||
<a-row :gutter="12">
|
||||
<a-col :span="12">
|
||||
<ve-histogram :data="chartData" :settings="chartSetting[0]" :extend="chartExtend"></ve-histogram>
|
||||
</a-col>
|
||||
<a-col :span="12">
|
||||
<ve-histogram :data="chartData" :settings="chartSetting[1]" :extend="chartExtend"></ve-histogram>
|
||||
</a-col>
|
||||
</a-row>
|
||||
<a-row :gutter="12">
|
||||
<a-col :span="12">
|
||||
<ve-histogram :data="chartData" :settings="chartSetting[2]" :extend="chartExtend"></ve-histogram>
|
||||
</a-col>
|
||||
<a-col :span="12">
|
||||
<ve-histogram :data="chartData" :settings="chartSetting[3]" :extend="chartExtend"></ve-histogram>
|
||||
</a-col>
|
||||
</a-row>
|
||||
</div>
|
||||
<div v-else style="text-align: center;margin-top: 100px">
|
||||
无数据!
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
// const echarts = require('echarts');
|
||||
// import Model from './Model'
|
||||
|
||||
export default {
|
||||
// name: "BasicChart",
|
||||
data() {
|
||||
return {
|
||||
chartData: [],
|
||||
chartSetting: [],
|
||||
chartExtend:{
|
||||
// xAxis:{ type: 'time' }
|
||||
}
|
||||
};
|
||||
},
|
||||
|
||||
props: {
|
||||
dataRow: { type: Array, default: () => [] },
|
||||
labelMap: { type: Object, default: () => {} }
|
||||
},
|
||||
|
||||
watch: {
|
||||
dataRow() {
|
||||
this.init()
|
||||
}
|
||||
},
|
||||
|
||||
computed: {
|
||||
hasData() {
|
||||
if(!!this.dataRow && this.dataRow.length > 0){
|
||||
return true
|
||||
}
|
||||
return false
|
||||
}
|
||||
},
|
||||
|
||||
methods: {
|
||||
setData() {
|
||||
if (this.dataRow.length === 0) {
|
||||
return;
|
||||
}
|
||||
this.dataRow.forEach(item => {
|
||||
item.time = new Date(item.time).toLocaleString();
|
||||
});
|
||||
|
||||
const cols = Object.keys(this.dataRow[0]);
|
||||
|
||||
this.chartData = {
|
||||
columns: cols,
|
||||
rows: this.dataRow
|
||||
};
|
||||
},
|
||||
|
||||
setSeting() {
|
||||
this.chartSetting = [];
|
||||
for (let key in this.labelMap) {
|
||||
this.chartSetting.push({
|
||||
labelMap: this.labelMap,
|
||||
metrics: [key],
|
||||
dimension: ["time"]
|
||||
});
|
||||
}
|
||||
},
|
||||
|
||||
init() {
|
||||
this.setData();
|
||||
this.setSeting();
|
||||
}
|
||||
},
|
||||
|
||||
async mounted() {
|
||||
this.init();
|
||||
}
|
||||
};
|
||||
</script>
|
||||
|
||||
<style>
|
||||
#setting {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#chart {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
</style>
|
@ -3,10 +3,11 @@ import App from './App.vue'
|
||||
import store from './utils/store'
|
||||
import router from './utils/router'
|
||||
import Antd from 'ant-design-vue';
|
||||
import VCharts from 'v-charts'
|
||||
import 'ant-design-vue/dist/antd.css';
|
||||
|
||||
Vue.use(Antd)
|
||||
|
||||
Vue.use(VCharts)
|
||||
Vue.config.productionTip = false
|
||||
Vue.prototype.$store = store
|
||||
|
||||
|
@ -14,6 +14,9 @@ export const URL_MAP = {
|
||||
PROJECT_DETAIL: 'project/detail/',
|
||||
SENSOR_LIST: 'sensor/',
|
||||
SENSOR_DETAIL: 'sensor/detail/',
|
||||
WATER_LIST: 'v1/api/water_detail/',
|
||||
USER_LIST: 'user/',
|
||||
USER_DETAIL: 'user/detail/'
|
||||
|
||||
}
|
||||
|
||||
@ -45,7 +48,46 @@ export async function logout()
|
||||
}
|
||||
|
||||
export async function getData(url, json) {
|
||||
let response = await instance.get(url, json)
|
||||
let response = await instance.get(url, {
|
||||
params: json
|
||||
})
|
||||
|
||||
let data = await response.data
|
||||
return data
|
||||
}
|
||||
|
||||
export async function postJSON(url, json) {
|
||||
const headerJSON = {
|
||||
"Content-Type": "application/json"
|
||||
};
|
||||
let response = await instance.post(url, JSON.stringify(json), { headers: headerJSON })
|
||||
let data = await response.data
|
||||
return data
|
||||
}
|
||||
|
||||
export async function putJSON(url, json) {
|
||||
const headerJSON = {
|
||||
"Content-Type": "application/json"
|
||||
};
|
||||
let response = await instance.put(url, JSON.stringify(json), { headers: headerJSON })
|
||||
let data = await response.data
|
||||
return data
|
||||
}
|
||||
|
||||
export async function patchJSON(url, json) {
|
||||
const headerJSON = {
|
||||
"Content-Type": "application/json"
|
||||
};
|
||||
let response = await instance.patch(url, JSON.stringify(json), { headers: headerJSON })
|
||||
let data = await response.data
|
||||
return data
|
||||
}
|
||||
|
||||
export async function deleteJSON(url, json) {
|
||||
const headerJSON = {
|
||||
"Content-Type": "application/json"
|
||||
};
|
||||
let response = await instance.delete(url, { data:json })
|
||||
let data = await response.data
|
||||
return data
|
||||
}
|
@ -1,15 +1,14 @@
|
||||
import { getData } from './http'
|
||||
|
||||
function processDevice(store)
|
||||
{
|
||||
const { deviceList, projectList, sensorList } = store.state
|
||||
|
||||
let deviceIdName = {}
|
||||
let projectIdName = {}
|
||||
let sensorIdName = {}
|
||||
|
||||
deviceList.forEach(d => deviceIdName[d._id] = d.device_name)
|
||||
projectList.forEach(p => projectIdName[p._id.$oid] = p.name)
|
||||
sensorList.forEach(s => sensorIdName[s._id.$oid] = s.name)
|
||||
|
||||
export function mergeList(a1=[], a2=[], key='_id') {
|
||||
let a = []
|
||||
let u = []
|
||||
a1.forEach(uu => {
|
||||
a.push(uu)
|
||||
u.push(uu[key])
|
||||
})
|
||||
a2.forEach(uu => {
|
||||
if(!u.includes(uu[key])) {
|
||||
a.push(uu)
|
||||
}
|
||||
})
|
||||
return a
|
||||
}
|
27
src/utils/water.js
Normal file
27
src/utils/water.js
Normal file
@ -0,0 +1,27 @@
|
||||
export function processWater(water, label){
|
||||
|
||||
const waters = []
|
||||
|
||||
water.forEach( w => {
|
||||
let n = {}
|
||||
label.forEach( key => {
|
||||
if(!!w.data) {
|
||||
n[key] = w.data[key]
|
||||
}
|
||||
|
||||
} )
|
||||
n['time'] = new Date(w.data.collect_time)
|
||||
waters.push(n)
|
||||
} )
|
||||
return waters
|
||||
}
|
||||
|
||||
export function processTimeData(dataArr=[], start=new Date(), end=new Date(), step=1) {
|
||||
const data_re = []
|
||||
for(let i=start.getTime(); i<=end.getTime(); i+=step)
|
||||
{
|
||||
data_re.push({
|
||||
|
||||
})
|
||||
}
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user