فهرست منبع

增加菜单管理模块,调整api结构

chenwen 2 سال پیش
والد
کامیت
1023c26c0a

+ 15 - 8
src/api/header.js

@@ -1,13 +1,15 @@
 import request from '../utils/request';
 
-export const fetchData = () => {
-    return request({
-        url: '/auth/loadMyMenus',
-        method: 'post'
-    });
-};
+const api={}
 
-export const processMenus=(menus)=>{
+api.fetchData=()=>{
+	return request({
+	    url: '/auth/loadMyMenus',
+	    method: 'post'
+	});
+}
+
+api.processMenus=(menus)=>{
 	let map={};
 	menus.forEach(menu=>{
 		map[menu.menuId]=menu
@@ -19,11 +21,16 @@ export const processMenus=(menus)=>{
 		if(pMenu){
 			pMenu.subMenus=pMenu.subMenus||[]
 			pMenu.subMenus.push(menu)
+			menu['fatherMenuName']=pMenu.menuName
 		}
 		else{
+			menu['fatherMenuName']=''
 			pMenuList.push(menu)
 		}
 	})
 	
 	return pMenuList
-}
+}
+
+export  default api
+

+ 9 - 2
src/api/login.js

@@ -1,9 +1,16 @@
 import request from '../utils/request';
 
-export const checkLogin = loginForm => {
+
+const api={}
+
+
+api.checkLogin = loginForm => {
     return request({
         url: '/login/check',
         method: 'post',
         params: loginForm
     });
-};
+};
+
+
+export  default api

+ 27 - 0
src/api/menu.js

@@ -0,0 +1,27 @@
+import request from '../utils/request';
+
+export default {
+	saveMenu : (data) => {
+	    return request({
+	        url: '/menu/update',
+	        method: 'post',
+			params:  data
+	    });
+	},
+	
+	addMenu : (data) => {
+	    return request({
+	        url: '/menu/add',
+	        method: 'post',
+			params:  data
+	    });
+	},
+	
+	delMenu : (data) => {
+	    return request({
+	        url: '/menu/delete',
+	        method: 'post',
+			params:  data
+	    });
+	}
+}

+ 9 - 3
src/api/sidetree.js

@@ -1,6 +1,9 @@
 import request from '../utils/request';
 
-export const fetchData = query => {
+const api={}
+
+
+api.fetchData = query => {
     return request({
         url: './test/wells.json',
         method: 'get',
@@ -8,10 +11,13 @@ export const fetchData = query => {
     });
 };
 
-export const fetchCustomData = query => {
+api.fetchCustomData = query => {
     return request({
         url: './test/customWells.json',
         method: 'get',
         params: query
     });
-};
+};
+
+
+export  default api

+ 7 - 4
src/components/Header.vue

@@ -55,7 +55,7 @@
 	import { storeToRefs } from 'pinia'
 	import { useHomeStore } from "../store/home.js"
 	import { useRouter } from "vue-router"
-	import { fetchData,processMenus } from "../api/header.js"
+	import headerAPI from "../api/header.js"
 	import navmenuItem from "./NavmenuItem.vue"
 	
 	const store=useHomeStore()
@@ -65,10 +65,10 @@
 	const menus = ref([])
 	
 	const getData = () => {
-	    fetchData().then( resp => {
+	    headerAPI.fetchData().then( resp => {
 			console.log(resp)
 			if(resp.code===0){
-				menus.value=processMenus(resp.data||[])
+				menus.value=headerAPI.processMenus(resp.data||[])
 				store.currentMenu=menus.value[0]
 			}
 			else{
@@ -111,7 +111,10 @@
 	
 	const menuClickHandle = (item) =>{
 		//console.log(item)
-		store.currentMenu=item
+		if(item.menuLink){
+			store.currentMenu=item
+		}
+		
 	}
 	
 </script>

+ 1 - 1
src/components/NavmenuItem.vue

@@ -6,7 +6,7 @@
 		{{ item?.menuName }}
 	</el-menu-item>
 	
-	<el-sub-menu :index="item ? item.menuId : ''" v-else>
+	<el-sub-menu :index="item ? item.menuId : ''"    v-else>
 		<template #title>
 			<el-icon v-if="item.menuIcon">
 				<component :is="item.menuIcon"></component>

+ 3 - 3
src/components/Sidetree.vue

@@ -47,7 +47,7 @@
 	import {ref} from 'vue'
 	import {storeToRefs} from 'pinia'
 	import {useHomeStore} from "../store/home.js"
-	import { fetchData,fetchCustomData } from "../api/sidetree.js"
+	import sidetreeAPI from "../api/sidetree.js"
 
 
 	const store = useHomeStore()
@@ -70,14 +70,14 @@
 	const customWells = ref([])
 	
 	const getData = () => {
-	    fetchData({}).then((res) => {
+	    sidetreeAPI.fetchData({}).then((res) => {
 	        sysWells.value=res
 	    });
 	};
 	getData();
 	
 	const getCustomData = () => {
-	    fetchCustomData({}).then((res) => {
+	    sidetreeAPI.fetchCustomData({}).then((res) => {
 	        customWells.value=res
 	    });
 	};

+ 4 - 4
src/pages/Login.vue

@@ -8,7 +8,7 @@
 	        <div class="ms-title">智能油田生产决策平台</div>
 	        <el-form :model="loginForm" :rules="rules" ref="login" label-width="0px" class="ms-content">
 	            <el-form-item prop="loginId">
-	                <el-input v-model="loginForm.loginId" placeholder="用户名" input-style="height:40px" tabindex="1">
+	                <el-input v-model="loginForm.loginId" placeholder="用户名" input-style="height:40px" tabindex="1"  autofocus>
 	                    <template #prepend>
 	                       <el-button icon="User"></el-button>
 						</template>
@@ -32,11 +32,11 @@
 </template>
 
 <script setup>
-import { ref, reactive } from "vue";
+import { ref, reactive,onMounted} from "vue";
 
 import { useRouter } from "vue-router";
 import { ElMessage } from "element-plus";
-import { checkLogin } from "../api/login.js"
+import loginAPI from "../api/login.js"
 import app from "../utils/app.js"
 import md5 from '../utils/md5.js'
 
@@ -60,7 +60,7 @@ import md5 from '../utils/md5.js'
 					let {loginId,pwd}=loginForm
 					pwd=md5(pwd)
 					//console.log(pwd+","+loginForm.pwd)
-					checkLogin({loginId,pwd}).then(resp=>{
+					loginAPI.checkLogin({loginId,pwd}).then(resp=>{
 						console.log(resp)
 						isLoading.value=false
 						if(resp.code===0){

+ 241 - 0
src/pages/auth/Menu.vue

@@ -0,0 +1,241 @@
+<template>
+	<div class="page-container">
+		<div class="page-side">
+			<el-scrollbar style="height:100%;padding:5px;box-sizing: border-box;">
+				<el-tree :data="menus" :props="defaultProps" :highlight-current="true" class="tree"  @node-click="nodeClickHandle">
+					   
+				</el-tree>
+				
+			</el-scrollbar>
+		</div>
+		<div class="page-split"></div>
+		<div class="page-main">
+			<el-form :model="formModel" ref="formcomp"  label-position="right" label-width="auto" :inline="false" :rules="rules" :inline-message="true">
+			    <el-form-item label="上级菜单">
+					<el-tree-select v-model="formModel.fatherMenuId" :data="menus" :props="defaultProps" :render-after-expand="false" check-strictly  class="edit-form-item"/>
+			        <!-- <el-input v-model="formModel.fatherMenuName" autocomplete="off"  class="edit-form-item" :readonly="true"/> -->
+					<el-button type="primary" plain size="default" @click="clearSuperHandle">清除</el-button>
+					<span class="footnote">(为0或空表示顶级){{formModel.fatherMenuId}}</span>
+			    </el-form-item>
+				
+			     
+				
+				  
+				<el-form-item label="菜单名" prop="menuName">
+				    <el-input v-model="formModel.menuName"  autocomplete="off" placeholder="请输入菜单名" class="edit-form-item" clearable/>
+				</el-form-item>
+				
+				<el-form-item label="链接地址">
+				    <el-input v-model="formModel.menuLink"  autocomplete="off" placeholder="请输入链接地址" class="edit-form-item" clearable/>
+				</el-form-item>
+				
+				<el-form-item label="图标">
+				    <el-input v-model="formModel.menuIcon"  autocomplete="off" placeholder="请输入图标名" class="edit-form-item" clearable/>
+				</el-form-item>
+				  
+				<el-form-item label="显示序号">
+				    <el-input-number v-model="formModel.displayNum" :min="1" :max="10000"/>
+				</el-form-item>
+				  
+	
+				<el-form-item label=" ">
+					<el-button type="primary" @click="saveSubmit">保存</el-button>
+					<el-button type="success" @click="addSubmit">新增</el-button>
+					<el-button @click="delSubmit">删除</el-button>
+				</el-form-item>
+			</el-form>
+		</div>
+	</div>
+</template>
+
+<script setup>
+	import {ref,reactive,toRefs,toRaw } from 'vue'
+	import headerAPI from "../../api/header.js"
+	import navmenuItem from "../../components/NavmenuItem.vue"
+	import {ElMessageBox,ElMessage} from 'element-plus'
+	import  menuAPI from "../../api/menu.js"
+	
+	const formModel = reactive({
+	  fatherMenuName:null,
+	  fatherMenuId:'',
+	  menuId: '',
+	  menuName:'',
+	  menuLink:'',
+	  menuIcon:null,
+	  displayNum:1
+	  
+	})
+	
+	const formcomp = ref(null);
+	
+	const rules =reactive({
+		menuName:[
+			{required:true,message:'菜单名还未填写',trigger:'blur'},
+			{ min: 2, max: 20, message: '菜单名长度应该为3-20', trigger: 'blur' }
+			]
+	})
+	
+	
+	
+	const defaultProps = {
+		children: 'subMenus',
+		label: 'menuName',
+		value:'menuId'           //兼容treeSelect
+	}
+	
+	const menus = ref([])
+	
+	const getData = () => {
+	    headerAPI.fetchData().then( resp => {
+			//console.log(resp)
+			if(resp.code===0){
+				menus.value=headerAPI.processMenus(resp.data||[])
+			}
+			else{
+				console.log(resp.msg)
+			}
+	        
+			
+	    });
+	};
+	getData();
+	
+	const nodeClickHandle = (item) =>{
+		console.log(item)
+		
+		let {fatherMenuName,fatherMenuId,menuId,menuName,menuLink,menuIcon,displayNum}=item
+		fatherMenuId=fatherMenuId=='0'?null:fatherMenuId
+		Object.assign(formModel,{fatherMenuName,fatherMenuId,menuId,menuName,menuLink,menuIcon,displayNum})
+		
+	}
+	
+	const clearForm=()=>{
+		let [fatherMenuName,fatherMenuId,menuId,menuName,menuLink,menuIcon,displayNum]=[null,null,null,null,null,null,1]
+		Object.assign(formModel,{fatherMenuName,fatherMenuId,menuId,menuName,menuLink,menuIcon,displayNum})
+	}
+	
+	const clearSuperHandle=()=>{
+		formModel.fatherMenuName=''
+		formModel.fatherMenuId='0'
+	}
+	
+	
+	
+	const saveSubmit=()=>{
+		formcomp.value.validate((valid) => {
+			if(!valid){
+				ElMessage.error("请按要求填写数据");
+				return
+			}
+			menuAPI.saveMenu(toRaw(formModel)).then(resp=>{
+				if(resp.code!=0){
+					ElMessage.error(resp.msg)
+					return
+				}
+				ElMessage.success('操作成功')
+				getData();
+				
+			}).catch(err=>{
+				ElMessage.error(err||'操作失败')
+			})
+		})
+	}
+	
+	const addSubmit=()=>{
+		formcomp.value.validate((valid) => {
+			if(!valid){
+				ElMessage.error("请按要求填写数据");
+				return
+			}
+			menuAPI.addMenu(toRaw(formModel)).then(resp=>{
+				if(resp.code!=0){
+					ElMessage.error(resp.msg)
+					return
+				}
+				ElMessage.success('操作成功')
+				clearForm()
+				getData();
+				
+			}).catch(err=>{
+				ElMessage.error(err||'操作失败')
+			})
+		})
+	}
+	
+	
+	const delSubmit=()=>{
+		if(!formModel.menuId){
+			ElMessage.error("请先选择一个菜单,再继续");
+			return;
+		}
+		ElMessageBox.confirm(
+			'确定要删除吗?',
+			'操作确认',
+			{
+				confirmButtonText:'确定',
+				cancelButtonText:'取消',
+				type: 'warning'
+			}
+		).then(()=>{
+			menuAPI.delMenu({menuId:formModel.menuId}).then(resp=>{
+				if(resp.code!=0){
+					ElMessage.error(resp.msg)
+					return
+				}
+				ElMessage.success('操作成功')
+				clearForm()
+				getData();
+				
+			}).catch(err=>{
+				ElMessage.error(err||'操作失败')
+			})
+			
+		}).catch(()=>{
+			console.log('cancel del')
+		})
+	}
+	
+</script>
+
+<style scoped>
+	.page-container{
+		padding: 5px 10px;
+		box-sizing: border-box;
+		height: 100%;
+		display: flex;
+		flex-flow: row nowrap;
+	}
+	.page-side{
+		width:240px;
+		height: 100%;
+	}
+	.page-split{
+		width:5px;
+		height: 100%;
+		background-color: #f2f2f2;
+	}
+	.page-main{
+		flex:1;
+		padding:0 50px;
+	}
+	
+	.el-form--inline.el-form--label-top{
+		justify-content: space-between;
+	}
+	.edit-form-item{
+		width:350px;
+	}
+	.footnote{
+		font-size:12px;
+		color:#999;
+	}
+	
+	.page-side:deep(.el-menu){
+		border-right: none;
+	}
+	
+	.tree {
+		/* background-color: #324157;
+		color: #c2c2d2; */
+	}
+</style>

+ 0 - 0
src/pages/sys/ParamMgr.vue → src/pages/base/ParamMgr.vue