luoyali 1 год назад
Родитель
Сommit
4a27c00189

+ 47 - 0
src/api/system/configure.ts

@@ -0,0 +1,47 @@
+import request from '@/utils/request'
+import { AxiosPromise } from 'axios'
+
+// apiUrl 扩展配置
+const api = {
+	page: '/sys/configure/page',
+	create: '/sys/configure/create',
+	update: '/sys/configure/update',
+	delete: '/sys/configure/delete'
+}
+/**
+ * 扩展配置 - 列表
+ */
+function configurePageApi(data: any): AxiosPromise {
+	return request({
+		url: api.page,
+		method: 'post',
+		data
+	})
+}
+
+/**
+ * 扩展配置 - 新增编辑保存
+ */
+function configureAddOrEditSaveApi(data: any): AxiosPromise {
+	return request({
+		url: data.id ? api.update : api.create,
+		method: 'post',
+		data
+	})
+}
+
+/**
+ * 扩展配置 - 删除
+ */
+function configureDeleteApi(data: any): AxiosPromise {
+	return request({
+		url: api.delete,
+		method: 'post',
+		data
+	})
+}
+export default {
+	configurePageApi,
+	configureAddOrEditSaveApi,
+	configureDeleteApi
+}

+ 3 - 3
src/api/system/post.ts

@@ -9,7 +9,7 @@ const api = {
 	delete: '/sys/post/delete'
 }
 /**
- * 用户管理 - 列表
+ * 岗位管理 - 列表
  */
 function postPageApi(data: any): AxiosPromise {
 	return request({
@@ -20,7 +20,7 @@ function postPageApi(data: any): AxiosPromise {
 }
 
 /**
- * 用户管理 - 新增编辑保存
+ * 岗位管理 - 新增编辑保存
  */
 function postAddOrEditSaveApi(data: any): AxiosPromise {
 	return request({
@@ -31,7 +31,7 @@ function postAddOrEditSaveApi(data: any): AxiosPromise {
 }
 
 /**
- * 用户管理 - 删除
+ * 岗位管理 - 删除
  */
 function postDeleteApi(data: any): AxiosPromise {
 	return request({

+ 4 - 4
src/api/system/region.ts

@@ -1,7 +1,7 @@
 import request from '@/utils/request'
 import { AxiosPromise } from 'axios'
 
-// apiUrl 部门管理
+// apiUrl 行政区域
 const api = {
 	page: '/sys/region/list-tree',
 	create: '/sys/region/create',
@@ -9,7 +9,7 @@ const api = {
 	delete: '/sys/region/delete'
 }
 /**
- * 部门管理 - 列表
+ * 行政区域 - 列表
  */
 function regionPageApi(data: any): AxiosPromise {
 	return request({
@@ -20,7 +20,7 @@ function regionPageApi(data: any): AxiosPromise {
 }
 
 /**
- * 部门管理 - 新增编辑保存
+ * 行政区域 - 新增编辑保存
  */
 function regionAddOrEditSaveApi(data: any): AxiosPromise {
 	return request({
@@ -31,7 +31,7 @@ function regionAddOrEditSaveApi(data: any): AxiosPromise {
 }
 
 /**
- * 部门管理 - 删除
+ * 行政区域 - 删除
  */
 function regionDeleteApi(data: any): AxiosPromise {
 	return request({

+ 6 - 0
src/router/index.ts

@@ -187,6 +187,12 @@ export const constantRoutes: Array<AppRouteRecordRaw> = [
 				component: () => import('@/views/setting/region/index.vue'),
 				name: 'region',
 				meta: { title: '行政区域', icon: '' }
+			},
+			{
+				path: 'configure',
+				component: () => import('@/views/setting/configure/index.vue'),
+				name: 'configure',
+				meta: { title: '扩展配置', icon: '' }
 			}
 		]
 	},

+ 331 - 0
src/views/configure/index.vue

@@ -0,0 +1,331 @@
+<template>
+	<div class="pageWrap">
+		<div class="content-warp flex-column-page-wrap">
+			<!-- 公用搜索组件 -->
+			<LeSearchForm ref="searchForm" v-model:searchData="searchData" :forms="forms" :loading="tableOpts.options.loading"> </LeSearchForm>
+
+			<!--  LeTable 组件使用  -->
+			<LeTable
+				ref="tableRef"
+				v-model:searchParams="tableOpts.searchParams"
+				v-bind="tableOpts"
+				v-model:curRow="tableOpts.curRow"
+				v-model:checked-options="checkedColumns"
+				:columns="activeColumns"
+			>
+				<template #toolLeft>
+					<el-button type="primary" @click="addHandler">
+						<el-icon class="btn-icon">
+							<Plus />
+						</el-icon>
+					</el-button>
+					<el-button type="danger" :disabled="curSelectionRows.length === 0" @click="batch_del">
+						<el-icon class="btn-icon">
+							<Delete />
+						</el-icon>
+					</el-button>
+				</template>
+
+				<template #statusSlot="scope">
+					<status-indicator v-if="scope.row.status === 1" pulse type="success"></status-indicator>
+					<status-indicator v-else pulse type="danger"></status-indicator>
+				</template>
+
+				<template #actionSlot="scope">
+					<el-tooltip content="编辑" placement="bottom" effect="light">
+						<el-icon class="ibt0" @click="table_edit(scope.row)">
+							<Edit />
+						</el-icon>
+					</el-tooltip>
+					<el-divider direction="vertical"></el-divider>
+					<el-popconfirm title="确定删除吗?" @confirm="table_del(scope.row)">
+						<template #reference>
+							<el-icon class="ibt0">
+								<Delete />
+							</el-icon>
+						</template>
+					</el-popconfirm>
+				</template>
+			</LeTable>
+		</div>
+
+		<LeFormConfigDialog
+			v-if="visible"
+			ref="dialogUserRef"
+			v-model="visible"
+			:title="`${isCreate ? '新增' : '编辑'}应用`"
+			width="600px"
+			:form-data="activeData"
+			:form-options="formOptions"
+			@submit="submitHandler"
+		/>
+	</div>
+</template>
+<script lang="tsx" setup>
+import app from '@/api/system/app'
+import { computed, nextTick, ref, watch } from 'vue'
+import { ElMessage, ElTree } from 'element-plus'
+import { useTablePage } from '@/hooks/useTablePage'
+import { Plus, Delete } from '@element-plus/icons-vue'
+import StatusIndicator from '@/components/StatusIndicator'
+
+const visible = ref(false) // 弹窗显示隐藏
+const isCreate = ref(true)
+const activeData = ref({})
+const formsDialog = [
+	{
+		prop: 'identification',
+		label: '标识',
+		itemType: 'input',
+		rules: [{ required: true, message: '请输入标识', trigger: 'blur' }]
+	},
+	{
+		prop: 'name',
+		label: '名称',
+		itemType: 'input',
+		rules: [{ required: true, message: '请输入应用别名', trigger: 'blur' }]
+	},
+	{
+		prop: 'secretKey',
+		label: '密钥',
+		itemType: 'input',
+		rules: [{ required: true, message: '请输入应用别名', trigger: 'blur' }]
+	},
+	{
+		prop: 'expire',
+		label: '授权至',
+		itemType: 'datePicker',
+		valueFormat: 'YYYY-MM-DD',
+		rules: [{ required: true, message: '请输入授权结束日期', trigger: 'blur' }]
+	},
+
+	{
+		prop: 'status',
+		label: '状态',
+		itemType: 'switch',
+		activeText: '是',
+		inactiveText: '否'
+	},
+	{
+		prop: 'sort',
+		label: '排序',
+		itemType: 'inputNumber',
+		rules: [{ required: true, message: '请输入排序', trigger: 'blur' }]
+	}
+]
+// 新增的表单 和 编辑的表单
+const formOptions = computed(() => {
+	return {
+		forms: formsDialog,
+		labelWidth: 120,
+		span: 30,
+		showResetBtn: true,
+		formConfig: {
+			submitLoading: false
+		}
+	}
+})
+const groupFilterText = ref('')
+const treeRef = ref<InstanceType<typeof ElTree>>()
+
+// 表格搜索条件
+const forms = ref([
+	{
+		prop: 'keyword',
+		label: '标识:',
+		itemType: 'input',
+		placeholder: '请输入标识'
+	}
+])
+
+// table列表数据请求
+const queryList = async () => {
+	const { options, searchParams } = tableOpts
+	options.loading = true
+	try {
+		const { records: list, total } = await app.appPageApi(searchParams)
+		tableOpts.total = total
+		tableOpts.list = list
+	} catch {
+		console.log('获取列表数据失败')
+		tableOpts.total = 0
+		tableOpts.list = []
+		options.loading = false // 更改加载中的 loading值
+	} finally {
+		options.loading = false
+	}
+}
+
+// table 参数
+const columns = [
+	{
+		prop: 'identification',
+		label: '标识',
+		minWidth: 80
+	},
+	{
+		prop: 'status',
+		label: '状态',
+		minWidth: 50,
+		slots: {
+			default: 'statusSlot'
+		}
+	},
+	{
+		prop: 'name',
+		label: '名称',
+		minWidth: 100
+	},
+	{
+		prop: 'secretKey',
+		label: '密钥',
+		minWidth: 100
+	},
+	{
+		prop: 'sort',
+		label: '排序',
+		minWidth: 80
+	},
+	{
+		prop: 'updateBy',
+		label: '修改人',
+		minWidth: 100
+	},
+	{
+		prop: 'updateTime',
+		label: '修改时间',
+		minWidth: 126
+	},
+	{
+		prop: 'createBy',
+		label: '创建人',
+		minWidth: 100
+	},
+	{
+		prop: 'createTime',
+		label: '创建时间',
+		minWidth: 126
+	},
+	{
+		prop: 'action',
+		label: '操作',
+		width: 100,
+		fixed: 'right',
+		slots: {
+			default: 'actionSlot'
+		}
+	}
+]
+
+const { searchData, tableOpts, checkedColumns, activeColumns, curSelectionRows, updateParams } = useTablePage(
+	{
+		options: {
+			showIndex: false
+		},
+		// 需要展示的列
+		columns,
+		// 控制列配置
+		columnsConfig: {
+			columns
+		}
+	},
+	{
+		queryList,
+		fetchImmediate: false
+	}
+)
+
+// 删除
+const deleteItem = async ids => {
+	try {
+		await app.appDeleteApi(ids)
+		updateParams()
+	} catch (e) {
+		console.log('删除失败')
+		ElMessage.error(`删除失败~`)
+	}
+}
+
+// 单个删除
+const table_del = row => {
+	deleteItem([row.id])
+}
+
+//批量删除
+const batch_del = () => {
+	const ids = curSelectionRows.value.map(item => item.id) // 多选数据
+	deleteItem(ids)
+}
+
+const table_edit = async row => {
+	isCreate.value = false
+	activeData.value = { ...row, status: row.status ? true : false }
+	visible.value = true
+}
+
+// 弹窗事件
+const submitHandler = async params => {
+	formOptions.value.formConfig.submitLoading = true
+	try {
+		params.status = params.status ? 1 : 0
+		params.expire = params.expire + ' 00:00:00'
+		params.id = activeData.value.id ? activeData.value.id : null
+		await app.appAddOrEditSaveApi(params)
+		ElMessage.success(`${isCreate.value ? '新增' : '修改'}成功~`)
+		visible.value = false
+		updateParams()
+		formOptions.value.formConfig.submitLoading = false
+	} catch (e) {
+		console.log(e)
+		formOptions.value.formConfig.submitLoading = false
+	}
+}
+
+const addHandler = () => {
+	isCreate.value = true
+	activeData.value = {}
+	visible.value = true
+}
+
+nextTick(() => {
+	queryList()
+})
+
+watch(groupFilterText, val => {
+	treeRef.value!.filter(val)
+})
+</script>
+<style scoped lang="scss">
+.pageWrap {
+	flex: 1;
+	display: flex;
+	height: 100%;
+	//background: #fff;
+}
+.content-warp {
+	flex: 1;
+	//width: calc(100% - 250px);
+	width: calc(100% - 210px);
+}
+// 单独自己写的
+/*:deep(.box-card) {
+	height: 100%;
+	.el-card__body {
+		padding: 0;
+	}
+}*/
+
+// 应用的树结构样式
+:deep(.menu-tree) {
+	.el-tree-node__content {
+		height: 36px;
+	}
+	.el-tree-node__content .el-tree-node__label .icon {
+		margin-right: 5px;
+	}
+}
+
+.nopadding {
+	padding: 0px;
+}
+</style>

+ 319 - 0
src/views/setting/configure/index.vue

@@ -0,0 +1,319 @@
+<template>
+	<div class="pageWrap">
+		<div class="content-warp flex-column-page-wrap">
+			<!-- 公用搜索组件 -->
+			<LeSearchForm ref="searchForm" v-model:searchData="searchData" :forms="forms" :loading="tableOpts.options.loading"> </LeSearchForm>
+
+			<!--  LeTable 组件使用  -->
+			<LeTable
+				ref="tableRef"
+				v-model:searchParams="tableOpts.searchParams"
+				v-bind="tableOpts"
+				v-model:curRow="tableOpts.curRow"
+				v-model:checked-options="checkedColumns"
+				:columns="activeColumns"
+			>
+				<template #toolLeft>
+					<el-button type="primary" @click="addHandler">
+						<el-icon class="btn-icon">
+							<Plus />
+						</el-icon>
+					</el-button>
+					<el-button type="danger" :disabled="curSelectionRows.length === 0" @click="batch_del">
+						<el-icon class="btn-icon">
+							<Delete />
+						</el-icon>
+					</el-button>
+				</template>
+
+				<template #statusSlot="scope">
+					<status-indicator v-if="scope.row.status === 1" pulse type="success"></status-indicator>
+					<status-indicator v-else pulse type="danger"></status-indicator>
+				</template>
+
+				<template #actionSlot="scope">
+					<el-tooltip content="编辑" placement="bottom" effect="light">
+						<el-icon class="ibt0" @click="table_edit(scope.row)">
+							<Edit />
+						</el-icon>
+					</el-tooltip>
+					<el-divider direction="vertical"></el-divider>
+					<el-popconfirm title="确定删除吗?" @confirm="table_del(scope.row)">
+						<template #reference>
+							<el-icon class="ibt0">
+								<Delete />
+							</el-icon>
+						</template>
+					</el-popconfirm>
+				</template>
+			</LeTable>
+		</div>
+
+		<LeFormConfigDialog
+			v-if="visible"
+			ref="dialogUserRef"
+			v-model="visible"
+			:title="`${isCreate ? '新增' : '编辑'}扩展配置`"
+			width="600px"
+			:form-data="activeData"
+			:form-options="formOptions"
+			@submit="submitHandler"
+		/>
+	</div>
+</template>
+<script lang="tsx" setup>
+import configure from '@/api/system/configure'
+import { computed, nextTick, ref, watch } from 'vue'
+import { ElMessage, ElTree } from 'element-plus'
+import { useTablePage } from '@/hooks/useTablePage'
+import { Plus, Delete } from '@element-plus/icons-vue'
+import StatusIndicator from '@/components/StatusIndicator'
+
+const visible = ref(false) // 弹窗显示隐藏
+const isCreate = ref(true)
+const activeData = ref({})
+const formsDialog = [
+	{
+		prop: 'category',
+		label: '分类',
+		itemType: 'input',
+		rules: [{ required: true, message: '请输入分类', trigger: 'blur' }]
+	},
+	{
+		prop: 'title',
+		label: '标题',
+		itemType: 'input',
+		rules: [{ required: true, message: '请输入标题', trigger: 'blur' }]
+	},
+	{
+		prop: 'key',
+		label: '关键字',
+		itemType: 'input',
+		rules: [{ required: true, message: '请输入关键字', trigger: 'blur' }]
+	},
+	{
+		prop: 'content',
+		label: '内容',
+		itemType: 'input',
+		rules: [{ required: true, message: '请输入内容', trigger: 'blur' }]
+	},
+	{
+		prop: 'sort',
+		label: '排序',
+		itemType: 'inputNumber'
+	}
+]
+// 新增的表单 和 编辑的表单
+const formOptions = computed(() => {
+	return {
+		forms: formsDialog,
+		labelWidth: 120,
+		span: 30,
+		showResetBtn: true,
+		formConfig: {
+			submitLoading: false
+		}
+	}
+})
+const groupFilterText = ref('')
+const treeRef = ref<InstanceType<typeof ElTree>>()
+
+// 表格搜索条件
+const forms = ref([
+	{
+		prop: 'keyword',
+		label: '标题:',
+		itemType: 'input',
+		placeholder: '请输入标题'
+	}
+])
+
+// table列表数据请求
+const queryList = async () => {
+	const { options, searchParams } = tableOpts
+	options.loading = true
+	try {
+		const { records: list, total } = await configure.configurePageApi(searchParams)
+		tableOpts.total = total
+		tableOpts.list = list
+	} catch {
+		console.log('获取列表数据失败')
+		tableOpts.total = 0
+		tableOpts.list = []
+		options.loading = false // 更改加载中的 loading值
+	} finally {
+		options.loading = false
+	}
+}
+
+// table 参数
+const columns = [
+	{
+		prop: 'title',
+		label: '标题',
+		minWidth: 250
+	},
+	{
+		prop: 'key',
+		label: '关键字',
+		minWidth: 150
+	},
+	{
+		prop: 'content',
+		label: '内容',
+		minWidth: 100,
+		showOverflowTooltip: true
+	},
+	{
+		prop: 'category',
+		label: '分类',
+		minWidth: 150
+	},
+	{
+		prop: 'sort',
+		label: '排序',
+		minWidth: 80
+	},
+	{
+		prop: 'updateBy',
+		label: '修改人',
+		minWidth: 100
+	},
+	{
+		prop: 'updateTime',
+		label: '修改时间',
+		minWidth: 126
+	},
+	{
+		prop: 'createBy',
+		label: '创建人',
+		minWidth: 100
+	},
+	{
+		prop: 'createTime',
+		label: '创建时间',
+		minWidth: 126
+	},
+	{
+		prop: 'action',
+		label: '操作',
+		width: 100,
+		fixed: 'right',
+		slots: {
+			default: 'actionSlot'
+		}
+	}
+]
+
+const { searchData, tableOpts, checkedColumns, activeColumns, curSelectionRows, updateParams } = useTablePage(
+	{
+		options: {
+			showIndex: false
+		},
+		// 需要展示的列
+		columns,
+		// 控制列配置
+		columnsConfig: {
+			columns
+		}
+	},
+	{
+		queryList,
+		fetchImmediate: false
+	}
+)
+
+// 删除
+const deleteItem = async ids => {
+	try {
+		await configure.configureDeleteApi(ids)
+		updateParams()
+	} catch (e) {
+		console.log('删除失败')
+		ElMessage.error(`删除失败~`)
+	}
+}
+
+// 单个删除
+const table_del = row => {
+	deleteItem([row.id])
+}
+
+//批量删除
+const batch_del = () => {
+	const ids = curSelectionRows.value.map(item => item.id) // 多选数据
+	deleteItem(ids)
+}
+
+const table_edit = async row => {
+	isCreate.value = false
+	activeData.value = { ...row, status: row.status ? true : false }
+	visible.value = true
+}
+
+// 弹窗事件
+const submitHandler = async params => {
+	formOptions.value.formConfig.submitLoading = true
+	try {
+		params.status = params.status ? 1 : 0
+		params.expire = params.expire + ' 00:00:00'
+		params.id = activeData.value.id ? activeData.value.id : null
+		await configure.configureAddOrEditSaveApi(params)
+		ElMessage.success(`${isCreate.value ? '新增' : '修改'}成功~`)
+		visible.value = false
+		updateParams()
+		formOptions.value.formConfig.submitLoading = false
+	} catch (e) {
+		console.log(e)
+		formOptions.value.formConfig.submitLoading = false
+	}
+}
+
+const addHandler = () => {
+	isCreate.value = true
+	activeData.value = {}
+	visible.value = true
+}
+
+nextTick(() => {
+	queryList()
+})
+
+watch(groupFilterText, val => {
+	treeRef.value!.filter(val)
+})
+</script>
+<style scoped lang="scss">
+.pageWrap {
+	flex: 1;
+	display: flex;
+	height: 100%;
+	//background: #fff;
+}
+.content-warp {
+	flex: 1;
+	//width: calc(100% - 250px);
+	width: calc(100% - 210px);
+}
+// 单独自己写的
+/*:deep(.box-card) {
+	height: 100%;
+	.el-card__body {
+		padding: 0;
+	}
+}*/
+
+// 应用的树结构样式
+:deep(.menu-tree) {
+	.el-tree-node__content {
+		height: 36px;
+	}
+	.el-tree-node__content .el-tree-node__label .icon {
+		margin-right: 5px;
+	}
+}
+
+.nopadding {
+	padding: 0px;
+}
+</style>