feat(系统配置): 实现全局配置管理功能

- 新增ConfigContext提供全局配置状态管理
- 重构系统设置页面,移除语言和深色模式选项
- 优化备份功能,支持自定义备份路径
- 应用主题颜色动态更新功能
- 添加配置变更自动重载机制
This commit is contained in:
zhang1106
2026-01-21 10:40:30 +08:00
parent 2af47ee162
commit dfd3d67ca0
5 changed files with 1596 additions and 58 deletions
+57 -20
View File
@@ -2,6 +2,7 @@ import React, { useState, useEffect } from 'react';
import { Tabs, Form, Input, Switch, Select, Button, Card, Space, message, Modal, Table, Tag, Progress, Divider, Descriptions, Alert } from 'antd';
import { SettingOutlined, GlobalOutlined, BgColorsOutlined, DatabaseOutlined, InfoCircleOutlined, CloudUploadOutlined, DeleteOutlined, ReloadOutlined, DownloadOutlined, SyncOutlined, CheckCircleOutlined, ExclamationCircleOutlined } from '@ant-design/icons';
import axios from 'axios';
import { useConfig } from '../context/ConfigContext';
const { Option } = Select;
const { TabPane } = Tabs;
@@ -15,6 +16,7 @@ const SystemSettings = () => {
const [backupLoading, setBackupLoading] = useState(false);
const [systemInfo, setSystemInfo] = useState(null);
const [form] = Form.useForm();
const { reloadConfig } = useConfig();
useEffect(() => {
fetchSettings();
@@ -74,6 +76,8 @@ const SystemSettings = () => {
await axios.put('/api/system-settings', { settings: updates });
message.success('设置保存成功');
fetchSettings();
// 重新加载全局配置,使更改立即生效
await reloadConfig();
} catch (error) {
message.error('保存设置失败');
} finally {
@@ -151,6 +155,8 @@ const SystemSettings = () => {
await axios.post(`/api/system-settings/reset/${key}`);
message.success('重置成功');
fetchSettings();
// 重新加载全局配置,使更改立即生效
await reloadConfig();
} catch (error) {
message.error('重置失败');
}
@@ -237,10 +243,29 @@ const SystemSettings = () => {
{ value: 'DD/MM/YYYY', label: '01/01/2024' },
{ value: 'MM/DD/YYYY', label: '01/01/2024' }
],
language: [
{ value: 'zh-CN', label: '简体中文' },
{ value: 'zh-TW', label: '繁體中文' },
{ value: 'en-US', label: 'English' }
primary_color: [
{ value: '#667eea', label: '蓝色 (#667eea)' },
{ value: '#764ba2', label: '紫色 (#764ba2)' },
{ value: '#f093fb', label: '粉色 (#f093fb)' },
{ value: '#4facfe', label: '浅蓝色 (#4facfe)' },
{ value: '#43e97b', label: '绿色 (#43e97b)' },
{ value: '#fa709a', label: '红色 (#fa709a)' },
{ value: '#fee140', label: '黄色 (#fee140)' },
{ value: '#00b4db', label: '青色 (#00b4db)' },
{ value: '#0083b0', label: '深蓝色 (#0083b0)' },
{ value: '#fcb045', label: '橙色 (#fcb045)' }
],
secondary_color: [
{ value: '#764ba2', label: '紫色 (#764ba2)' },
{ value: '#667eea', label: '蓝色 (#667eea)' },
{ value: '#4facfe', label: '浅蓝色 (#4facfe)' },
{ value: '#43e97b', label: '绿色 (#43e97b)' },
{ value: '#fa709a', label: '红色 (#fa709a)' },
{ value: '#fee140', label: '黄色 (#fee140)' },
{ value: '#00b4db', label: '青色 (#00b4db)' },
{ value: '#0083b0', label: '深蓝色 (#0083b0)' },
{ value: '#fcb045', label: '橙色 (#fcb045)' },
{ value: '#f093fb', label: '粉色 (#f093fb)' }
],
table_row_height: [
{ value: 'small', label: '紧凑 (Small)' },
@@ -273,11 +298,18 @@ const SystemSettings = () => {
};
const renderGeneralSettings = () => {
const generalKeys = ['site_name', 'site_logo', 'timezone', 'date_format', 'language', 'session_timeout', 'max_login_attempts', 'maintenance_mode'];
const generalKeys = ['site_name', 'site_logo', 'timezone', 'date_format', 'session_timeout', 'max_login_attempts', 'maintenance_mode'];
return (
<Card title="全局配置" bordered={false}>
<Form form={form} layout="vertical" onFinish={handleSaveSettings}>
{generalKeys.map(key => settings[key] && renderFormItem(key, settings[key]))}
{generalKeys.map(key => {
// 确保时区和日期格式使用select类型
const settingData = { ...settings[key] };
if (key === 'timezone' || key === 'date_format') {
settingData.type = 'select';
}
return renderFormItem(key, settingData);
})}
<Form.Item>
<Space>
<Button type="primary" htmlType="submit" loading={saving}>保存设置</Button>
@@ -290,18 +322,25 @@ const SystemSettings = () => {
};
const renderAppearanceSettings = () => {
const appearanceKeys = ['primary_color', 'secondary_color', 'dark_mode', 'compact_mode', 'sidebar_collapsed', 'table_row_height', 'animation_enabled'];
const appearanceKeys = ['primary_color', 'secondary_color', 'compact_mode', 'sidebar_collapsed', 'table_row_height', 'animation_enabled'];
return (
<Card title="外观设置" bordered={false}>
<Form form={form} layout="vertical" onFinish={handleSaveSettings}>
<Alert
message="主题颜色"
description="修改主题颜色后需要刷新页面才能生效。深色模式可以减少眼睛疲劳。"
description="修改主题颜色后需要刷新页面才能生效。"
type="info"
showIcon
style={{ marginBottom: 16 }}
/>
{appearanceKeys.map(key => settings[key] && renderFormItem(key, settings[key]))}
{appearanceKeys.map(key => {
// 确保主题颜色使用select类型
const settingData = { ...settings[key] };
if (key === 'primary_color' || key === 'secondary_color') {
settingData.type = 'select';
}
return renderFormItem(key, settingData);
})}
<Form.Item>
<Space>
<Button type="primary" htmlType="submit" loading={saving}>保存设置</Button>
@@ -314,14 +353,6 @@ const SystemSettings = () => {
};
const renderBackupSettings = () => {
const backupInfo = settings.backup_retention ? {
auto_backup_enabled: settings.auto_backup_enabled,
backup_interval: settings.backup_interval,
backup_retention: settings.backup_retention,
last_backup_time: settings.last_backup_time,
backup_count: settings.backup_count
} : null;
const backupColumns = [
{
title: '文件名',
@@ -357,13 +388,19 @@ const SystemSettings = () => {
}
];
// 备份设置键列表
const backupKeys = ['auto_backup_enabled', 'backup_interval', 'backup_retention', 'backup_path', 'last_backup_time', 'backup_count'];
return (
<div>
<Card title="自动备份设置" bordered={false} style={{ marginBottom: 16 }}>
<Form form={form} layout="vertical" onFinish={handleSaveSettings}>
{backupInfo && Object.entries(backupInfo).map(([key, data]) => (
data && typeof data === 'object' ? renderFormItem(key, data) : null
))}
{backupKeys.map(key => {
if (settings[key]) {
return renderFormItem(key, settings[key]);
}
return null;
})}
<Form.Item>
<Space>
<Button type="primary" htmlType="submit" loading={saving}>保存设置</Button>