feat:管理后台系统设置页面 + 小程序登录页条件渲染
This commit is contained in:
@@ -0,0 +1,18 @@
|
||||
import request from '@/utils/request'
|
||||
|
||||
// 获取所有可见配置列表
|
||||
export function getSystemConfigList() {
|
||||
return request({
|
||||
url: '/admin/systemConfig/list',
|
||||
method: 'get'
|
||||
})
|
||||
}
|
||||
|
||||
// 批量更新配置
|
||||
export function updateSystemConfig(data: { configKey: string; configValue: string }[]) {
|
||||
return request({
|
||||
url: '/admin/systemConfig/update',
|
||||
method: 'put',
|
||||
data
|
||||
})
|
||||
}
|
||||
@@ -27,6 +27,11 @@ export const menuConfig: MenuItem[] = [
|
||||
title: '用户管理',
|
||||
icon: 'UserFilled'
|
||||
},
|
||||
{
|
||||
path: '/system',
|
||||
title: '系统设置',
|
||||
icon: 'Setting'
|
||||
},
|
||||
{
|
||||
path: '/aiconfig',
|
||||
title: 'AI配置管理',
|
||||
|
||||
@@ -55,6 +55,20 @@ const routes: RouteRecordRaw[] = [
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
path: '/system',
|
||||
component: Layout,
|
||||
redirect: '/system/settings',
|
||||
meta: { title: '系统设置', icon: 'Setting' },
|
||||
children: [
|
||||
{
|
||||
path: 'settings',
|
||||
name: 'SystemSettings',
|
||||
component: () => import('@/views/system/SystemSettings.vue'),
|
||||
meta: { title: '基础设置' }
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
path: '/aiconfig',
|
||||
component: Layout,
|
||||
|
||||
@@ -0,0 +1,183 @@
|
||||
<template>
|
||||
<div class="system-settings">
|
||||
<div class="page-header">
|
||||
<h2>基础设置</h2>
|
||||
<el-button type="primary" :loading="saving" @click="handleSave">保存</el-button>
|
||||
</div>
|
||||
|
||||
<el-card v-if="loading" v-loading="true" class="loading-card" />
|
||||
|
||||
<div v-else class="config-groups">
|
||||
<el-card v-for="(items, group) in groupedConfigs" :key="group" class="config-group">
|
||||
<template #header>
|
||||
<span class="group-title">{{ groupLabels[group] || group }}</span>
|
||||
</template>
|
||||
|
||||
<div v-for="item in items" :key="item.configKey" class="config-item">
|
||||
<div class="config-label">
|
||||
<span class="config-name">{{ item.configName }}</span>
|
||||
<span class="config-desc">{{ item.description }}</span>
|
||||
</div>
|
||||
<div class="config-control">
|
||||
<el-switch
|
||||
v-if="item.valueType === 'boolean'"
|
||||
v-model="editValues[item.configKey]"
|
||||
:active-value="'true'"
|
||||
:inactive-value="'false'"
|
||||
/>
|
||||
<el-input
|
||||
v-else-if="item.valueType === 'string'"
|
||||
v-model="editValues[item.configKey]"
|
||||
style="width: 300px"
|
||||
/>
|
||||
<el-input-number
|
||||
v-else-if="item.valueType === 'number'"
|
||||
v-model="editValues[item.configKey]"
|
||||
style="width: 200px"
|
||||
/>
|
||||
<span v-else>{{ editValues[item.configKey] }}</span>
|
||||
</div>
|
||||
</div>
|
||||
</el-card>
|
||||
|
||||
<el-empty v-if="Object.keys(groupedConfigs).length === 0" description="暂无配置项" />
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script setup lang="ts">
|
||||
import { ref, computed, onMounted } from 'vue'
|
||||
import { ElMessage } from 'element-plus'
|
||||
import { getSystemConfigList, updateSystemConfig } from '@/api/systemConfig'
|
||||
|
||||
interface ConfigItem {
|
||||
configKey: string
|
||||
configValue: string
|
||||
valueType: string
|
||||
configGroup: string
|
||||
configName: string
|
||||
description: string
|
||||
sortOrder: number
|
||||
}
|
||||
|
||||
const loading = ref(false)
|
||||
const saving = ref(false)
|
||||
const configs = ref<ConfigItem[]>([])
|
||||
const editValues = ref<Record<string, string | boolean>>({})
|
||||
|
||||
const groupLabels: Record<string, string> = {
|
||||
system: '系统配置',
|
||||
login: '登录设置',
|
||||
notification: '通知设置'
|
||||
}
|
||||
|
||||
const groupedConfigs = computed(() => {
|
||||
const groups: Record<string, ConfigItem[]> = {}
|
||||
for (const item of configs.value) {
|
||||
if (!groups[item.configGroup]) {
|
||||
groups[item.configGroup] = []
|
||||
}
|
||||
groups[item.configGroup].push(item)
|
||||
}
|
||||
return groups
|
||||
})
|
||||
|
||||
const fetchConfigs = async () => {
|
||||
loading.value = true
|
||||
try {
|
||||
const res = await getSystemConfigList()
|
||||
configs.value = res.data || []
|
||||
// 初始化编辑值
|
||||
const values: Record<string, string | boolean> = {}
|
||||
for (const item of configs.value) {
|
||||
values[item.configKey] = item.configValue
|
||||
}
|
||||
editValues.value = values
|
||||
} catch (error) {
|
||||
ElMessage.error('获取配置列表失败')
|
||||
} finally {
|
||||
loading.value = false
|
||||
}
|
||||
}
|
||||
|
||||
const handleSave = async () => {
|
||||
saving.value = true
|
||||
try {
|
||||
const updates = configs.value.map(item => ({
|
||||
configKey: item.configKey,
|
||||
configValue: String(editValues.value[item.configKey])
|
||||
}))
|
||||
await updateSystemConfig(updates)
|
||||
ElMessage.success('保存成功')
|
||||
await fetchConfigs()
|
||||
} catch (error) {
|
||||
ElMessage.error('保存失败')
|
||||
} finally {
|
||||
saving.value = false
|
||||
}
|
||||
}
|
||||
|
||||
onMounted(() => {
|
||||
fetchConfigs()
|
||||
})
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
.system-settings {
|
||||
padding: 20px;
|
||||
}
|
||||
|
||||
.page-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.page-header h2 {
|
||||
margin: 0;
|
||||
font-size: 20px;
|
||||
}
|
||||
|
||||
.loading-card {
|
||||
height: 200px;
|
||||
}
|
||||
|
||||
.config-group {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.group-title {
|
||||
font-weight: 600;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.config-item {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
padding: 16px 0;
|
||||
border-bottom: 1px solid var(--el-border-color-lighter);
|
||||
}
|
||||
|
||||
.config-item:last-child {
|
||||
border-bottom: none;
|
||||
}
|
||||
|
||||
.config-label {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 4px;
|
||||
}
|
||||
|
||||
.config-name {
|
||||
font-size: 14px;
|
||||
font-weight: 500;
|
||||
color: var(--el-text-color-primary);
|
||||
}
|
||||
|
||||
.config-desc {
|
||||
font-size: 12px;
|
||||
color: var(--el-text-color-secondary);
|
||||
}
|
||||
</style>
|
||||
Reference in New Issue
Block a user