将routes_sys.ts拆分为5个独立的路由文件
This commit is contained in:
296
server/routes_system_settings.ts
Normal file
296
server/routes_system_settings.ts
Normal file
@@ -0,0 +1,296 @@
|
||||
import { Hono } from "hono";
|
||||
import debug from "debug";
|
||||
import type {
|
||||
SystemSetting,
|
||||
SystemSettingGroupData,
|
||||
} from "../client/share/types.ts";
|
||||
|
||||
import type { Variables, WithAuth } from "./app.tsx";
|
||||
|
||||
const log = {
|
||||
api: debug("api:sys"),
|
||||
};
|
||||
|
||||
// 创建系统设置路由
|
||||
export function createSystemSettingsRoutes(withAuth: WithAuth) {
|
||||
const settingsRoutes = new Hono<{ Variables: Variables }>();
|
||||
|
||||
// 获取所有系统设置(按分组)
|
||||
settingsRoutes.get('/', withAuth, async (c) => {
|
||||
try {
|
||||
const apiClient = c.get('apiClient');
|
||||
const settings = await apiClient.database
|
||||
.table('system_settings')
|
||||
.select('*');
|
||||
|
||||
// 按分组整理数据
|
||||
const groupedSettings = settings.reduce((acc: SystemSettingGroupData[], setting) => {
|
||||
const groupIndex = acc.findIndex((g: SystemSettingGroupData) => g.name === setting.group);
|
||||
if (groupIndex === -1) {
|
||||
acc.push({
|
||||
name: setting.group,
|
||||
description: `${setting.group}组设置`,
|
||||
settings: [{
|
||||
id: setting.id,
|
||||
key: setting.key,
|
||||
value: setting.value,
|
||||
description: setting.description,
|
||||
group: setting.group
|
||||
}]
|
||||
});
|
||||
} else {
|
||||
acc[groupIndex].settings.push({
|
||||
id: setting.id,
|
||||
key: setting.key,
|
||||
value: setting.value,
|
||||
description: setting.description,
|
||||
group: setting.group
|
||||
});
|
||||
}
|
||||
return acc;
|
||||
}, []);
|
||||
|
||||
return c.json({
|
||||
message: '获取系统设置成功',
|
||||
data: groupedSettings
|
||||
});
|
||||
} catch (error) {
|
||||
log.api('获取系统设置失败:', error);
|
||||
return c.json({ error: '获取系统设置失败' }, 500);
|
||||
}
|
||||
});
|
||||
|
||||
// 获取指定分组的系统设置
|
||||
settingsRoutes.get('/group/:group', withAuth, async (c) => {
|
||||
try {
|
||||
const apiClient = c.get('apiClient');
|
||||
const group = c.req.param('group');
|
||||
|
||||
const settings = await apiClient.database
|
||||
.table('system_settings')
|
||||
.where('group', group)
|
||||
.select('*');
|
||||
|
||||
return c.json({
|
||||
message: '获取分组设置成功',
|
||||
data: settings
|
||||
});
|
||||
} catch (error) {
|
||||
log.api('获取分组设置失败:', error);
|
||||
return c.json({ error: '获取分组设置失败' }, 500);
|
||||
}
|
||||
});
|
||||
|
||||
// 更新系统设置
|
||||
settingsRoutes.put('/:key', withAuth, async (c) => {
|
||||
try {
|
||||
const apiClient = c.get('apiClient');
|
||||
const key = c.req.param('key');
|
||||
const settingData = await c.req.json();
|
||||
|
||||
// 验证设置是否存在
|
||||
const existingSetting = await apiClient.database
|
||||
.table('system_settings')
|
||||
.where('key', key)
|
||||
.first();
|
||||
|
||||
if (!existingSetting) {
|
||||
return c.json({ error: '设置项不存在' }, 404);
|
||||
}
|
||||
|
||||
// 更新设置
|
||||
await apiClient.database
|
||||
.table('system_settings')
|
||||
.where('key', key)
|
||||
.update({
|
||||
value: settingData.value,
|
||||
updated_at: apiClient.database.fn.now()
|
||||
});
|
||||
|
||||
// 获取更新后的设置
|
||||
const updatedSetting = await apiClient.database
|
||||
.table('system_settings')
|
||||
.where('key', key)
|
||||
.first();
|
||||
|
||||
return c.json({
|
||||
message: '系统设置已更新',
|
||||
data: updatedSetting
|
||||
});
|
||||
} catch (error) {
|
||||
log.api('更新系统设置失败:', error);
|
||||
return c.json({ error: '更新系统设置失败' }, 500);
|
||||
}
|
||||
});
|
||||
|
||||
// 批量更新系统设置
|
||||
settingsRoutes.put('/', withAuth, async (c) => {
|
||||
try {
|
||||
const apiClient = c.get('apiClient');
|
||||
const settingsData = await c.req.json();
|
||||
|
||||
// 验证数据格式
|
||||
if (!Array.isArray(settingsData)) {
|
||||
return c.json({ error: '无效的请求数据格式,应为数组' }, 400);
|
||||
}
|
||||
|
||||
const trxProvider = apiClient.database.transactionProvider();
|
||||
const trx = await trxProvider();
|
||||
|
||||
for (const setting of settingsData) {
|
||||
if (!setting.key) continue;
|
||||
|
||||
// 验证设置是否存在
|
||||
const existingSetting = await trx.table('system_settings')
|
||||
.where('key', setting.key)
|
||||
.first();
|
||||
|
||||
if (!existingSetting) {
|
||||
throw new Error(`设置项 ${setting.key} 不存在`);
|
||||
}
|
||||
|
||||
// 更新设置
|
||||
await trx.table('system_settings')
|
||||
.where('key', setting.key)
|
||||
.update({
|
||||
value: setting.value,
|
||||
updated_at: trx.fn.now()
|
||||
});
|
||||
}
|
||||
|
||||
await trx.commit();
|
||||
|
||||
// 获取所有更新后的设置
|
||||
const updatedSettings = await apiClient.database
|
||||
.table('system_settings')
|
||||
.whereIn('key', settingsData.map(s => s.key))
|
||||
.select('*');
|
||||
|
||||
return c.json({
|
||||
message: '系统设置已批量更新',
|
||||
data: updatedSettings
|
||||
});
|
||||
} catch (error) {
|
||||
log.api('批量更新系统设置失败:', error);
|
||||
return c.json({ error: '批量更新系统设置失败' }, 500);
|
||||
}
|
||||
});
|
||||
|
||||
// 重置系统设置
|
||||
settingsRoutes.post('/reset', withAuth, async (c) => {
|
||||
try {
|
||||
const apiClient = c.get('apiClient');
|
||||
|
||||
// 重置为迁移文件中定义的初始值
|
||||
const trxProvider = apiClient.database.transactionProvider();
|
||||
const trx = await trxProvider();
|
||||
|
||||
// 清空现有设置
|
||||
await trx.table('system_settings').delete();
|
||||
|
||||
// 插入默认设置
|
||||
await trx.table('system_settings').insert([
|
||||
// 基础设置组
|
||||
{
|
||||
key: 'SITE_NAME',
|
||||
value: '应用管理系统',
|
||||
description: '站点名称',
|
||||
group: 'basic',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
},
|
||||
{
|
||||
key: 'SITE_DESCRIPTION',
|
||||
value: '一个强大的应用管理系统',
|
||||
description: '站点描述',
|
||||
group: 'basic',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
},
|
||||
{
|
||||
key: 'SITE_KEYWORDS',
|
||||
value: '应用管理,系统管理,后台管理',
|
||||
description: '站点关键词',
|
||||
group: 'basic',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
},
|
||||
// 功能设置组
|
||||
{
|
||||
key: 'ENABLE_REGISTER',
|
||||
value: 'true',
|
||||
description: '是否开启注册',
|
||||
group: 'feature',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
},
|
||||
{
|
||||
key: 'ENABLE_CAPTCHA',
|
||||
value: 'true',
|
||||
description: '是否开启验证码',
|
||||
group: 'feature',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
},
|
||||
{
|
||||
key: 'LOGIN_ATTEMPTS',
|
||||
value: '5',
|
||||
description: '登录尝试次数',
|
||||
group: 'feature',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
},
|
||||
// 上传设置组
|
||||
{
|
||||
key: 'UPLOAD_MAX_SIZE',
|
||||
value: '10',
|
||||
description: '最大上传大小(MB)',
|
||||
group: 'upload',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
},
|
||||
{
|
||||
key: 'ALLOWED_FILE_TYPES',
|
||||
value: 'jpg,jpeg,png,gif,doc,docx,xls,xlsx,pdf',
|
||||
description: '允许的文件类型',
|
||||
group: 'upload',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
},
|
||||
// 通知设置组
|
||||
{
|
||||
key: 'NOTIFY_ON_LOGIN',
|
||||
value: 'true',
|
||||
description: '登录通知',
|
||||
group: 'notify',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
},
|
||||
{
|
||||
key: 'NOTIFY_ON_ERROR',
|
||||
value: 'true',
|
||||
description: '错误通知',
|
||||
group: 'notify',
|
||||
created_at: apiClient.database.fn.now(),
|
||||
updated_at: apiClient.database.fn.now()
|
||||
}
|
||||
]);
|
||||
|
||||
await trx.commit();
|
||||
|
||||
const resetSettings = await apiClient.database
|
||||
.table('system_settings')
|
||||
.select('*');
|
||||
|
||||
return c.json({
|
||||
message: '系统设置已重置',
|
||||
data: resetSettings
|
||||
});
|
||||
} catch (error) {
|
||||
log.api('重置系统设置失败:', error);
|
||||
return c.json({ error: '重置系统设置失败' }, 500);
|
||||
}
|
||||
});
|
||||
|
||||
return settingsRoutes;
|
||||
}
|
||||
Reference in New Issue
Block a user