feat: harden ai agent admin workflow experience

This commit is contained in:
2026-06-22 04:50:11 +08:00
parent ae29c24529
commit 4ec846a702
385 changed files with 61461 additions and 5886 deletions
@@ -64,6 +64,16 @@ export interface ParamDefinition {
default?: any;
}
/**
* 列表后处理配置(排序 + 条数限制)
*/
export interface ListConfig {
sort_field?: string;
sort_order?: 'asc' | 'desc';
/** 0 表示不额外限制(仍受系统最大 1000 条约束) */
limit?: number;
}
/**
* 树形配置
*/
@@ -131,12 +141,17 @@ export interface DataSource {
// SQL 配置
sql_content?: string;
db_connection?: string;
/** SQL 执行目标库/catalog */
db_database?: string;
/** SQL 执行目标模式/schema */
db_schema?: string;
// 静态数据
static_data?: any[];
// 参数定义
params?: ParamDefinition[];
// 结果处理
result_type?: ResultType;
list_config?: ListConfig;
tree_config?: TreeConfig;
field_mapping?: Record<string, string>;
chart_config?: ChartConfig;
@@ -195,12 +210,17 @@ export interface DataSourceInput {
// SQL 配置
sql_content?: string;
db_connection?: string;
/** SQL 执行目标库/catalog */
db_database?: string;
/** SQL 执行目标模式/schema */
db_schema?: string;
// 静态数据
static_data?: any[];
// 参数定义
params?: ParamDefinition[];
// 结果处理
result_type?: ResultType;
list_config?: ListConfig;
tree_config?: TreeConfig;
field_mapping?: Record<string, string>;
chart_config?: ChartConfig;
@@ -268,6 +288,10 @@ export interface TestRequest {
// SQL 配置
sql_content?: string;
db_connection?: string;
/** SQL 执行目标库/catalog */
db_database?: string;
/** SQL 执行目标模式/schema */
db_schema?: string;
// 静态数据
static_data?: any[];
// 参数
@@ -275,6 +299,7 @@ export interface TestRequest {
params?: Record<string, any>;
// 结果处理
result_type?: ResultType;
list_config?: ListConfig;
tree_config?: TreeConfig;
field_mapping?: Record<string, string>;
chart_config?: ChartConfig;
+14 -8
View File
@@ -1,16 +1,22 @@
export * from './announcement';
export * from '../online-dev/form-data-api';
export * from '../online-dev/form-manager';
// 注意: login-log 模块请直接导入以避免 PaginatedResponse 类型冲突
// import { getLoginLogListApi, ... } from '#/api/core/login-log';
// 注意: ai-platform 模块请直接导入以避免类型冲突
// import { ... } from '#/api/core/ai-platform';
export * from '../online-dev/screen-design';
export * from './application';
export * from './auth';
export * from './data-source';
export * from './database-connection';
export * from './database-manager';
export * from './dept';
export * from './dict';
export * from './file';
export * from './field-permission';
export * from './menu';
export * from './message';
export * from './oauth';
export * from './permission';
export * from './post';
export * from './role';
export * from './resource-scope';
export * from './server-health';
export * from './ui-config';
export * from './scheduler';
export * from './server-monitor';
export * from './user';
export * from './websocket';
@@ -10,7 +10,6 @@ export interface LoginLog {
user_id?: string;
username: string;
status: number;
login_type?: string;
failure_reason?: number;
failure_message?: string;
login_ip: string;
@@ -34,7 +33,6 @@ export interface LoginLogListParams {
username?: string;
user_id?: string;
status?: number;
login_type?: string;
failure_reason?: number;
login_ip?: string;
device_type?: string;
+5
View File
@@ -110,14 +110,19 @@ export interface MenuStats {
/**
* 获取用户所有菜单(路由树)
* @param applicationCode 应用编码,用于过滤应用专属菜单
* @param devMode 开发模式:true只返回系统菜单,false只返回应用菜单
*/
export async function getAllMenusApi(
applicationCode?: string,
devMode?: boolean,
) {
const params: Record<string, any> = {};
if (applicationCode) {
params.application_code = applicationCode;
}
if (devMode !== undefined) {
params.devMode = devMode;
}
return requestClient.get<RouteRecordStringComponent[]>(
'/api/core/menu/route/tree',
{ params },
+6 -7
View File
@@ -29,7 +29,6 @@ export interface PostCreateInput {
status?: boolean;
description?: string;
dept_id?: string;
sort?: number;
}
export interface PostUpdateInput extends Partial<PostCreateInput> {}
@@ -121,7 +120,7 @@ export async function deletePostApi(postId: string) {
*/
export async function batchDeletePostApi(data: PostBatchDeleteInput) {
return requestClient.post<{ count: number }>(
'/api/core/post/batch/delete',
'/api/core/post/batch_delete',
data,
);
}
@@ -133,7 +132,7 @@ export async function batchUpdatePostStatusApi(
data: PostBatchUpdateStatusInput,
) {
return requestClient.post<{ count: number }>(
'/api/core/post/batch/status',
'/api/core/post/batch_update_status',
data,
);
}
@@ -142,7 +141,7 @@ export async function batchUpdatePostStatusApi(
* 根据部门ID获取岗位列表
*/
export async function getPostsByDeptApi(deptId: string) {
return requestClient.get<Post[]>(`/api/core/post/by/dept/${deptId}`);
return requestClient.get<Post[]>(`/api/core/post/by_dept/${deptId}`);
}
/**
@@ -195,7 +194,7 @@ export async function getPostStatsApi() {
* 导出岗位数据
*/
export async function exportPostApi(params?: PostListParams) {
return requestClient.get<Blob>('/api/core/post/export/excel', {
return requestClient.get<Blob>('/api/core/post/export', {
params,
responseType: 'blob',
});
@@ -208,7 +207,7 @@ export async function importPostApi(file: File) {
const formData = new FormData();
formData.append('file', file);
return requestClient.post<{ error_count: number; success_count: number }>(
'/api/core/post/import/excel',
'/api/core/post/import',
formData,
{
headers: {
@@ -222,7 +221,7 @@ export async function importPostApi(file: File) {
* 获取简单岗位列表(用于选择器)
*/
export async function getSimplePostListApi() {
return requestClient.get<Post[]>('/api/core/post/all');
return requestClient.get<Post[]>('/api/core/post/simple');
}
/**
@@ -1,5 +1,10 @@
import { requestClient } from '#/api/request';
/**
* 服务器监控相关类型定义
*/
// 基础信息
export interface BasicInfo {
hostname: string;
ip_address: string;
@@ -14,6 +19,7 @@ export interface BasicInfo {
version: string;
}
// CPU信息
export interface CpuInfo {
physical_cores: number;
total_cores: number;
@@ -26,6 +32,7 @@ export interface CpuInfo {
cpu_stats: Record<string, any>;
}
// 内存信息
export interface MemoryVirtual {
total: number;
available: number;
@@ -53,6 +60,7 @@ export interface MemoryInfo {
swap: MemorySwap;
}
// 磁盘信息
export interface DiskPartition {
device: string;
mountpoint: string;
@@ -73,6 +81,7 @@ export interface DiskInfo {
total_write_time?: number;
}
// 网络信息
export interface NetworkTotal {
bytes_sent: number;
bytes_recv: number;
@@ -127,6 +136,7 @@ export interface NetworkInfo {
connections: NetworkConnection[];
}
// 进程信息
export interface Process {
pid: number;
name: string;
@@ -143,6 +153,7 @@ export interface ProcessInfo {
sleeping_processes: number;
}
// 系统负载
export interface SystemLoad {
load_1min: number;
load_5min: number;
@@ -150,6 +161,7 @@ export interface SystemLoad {
cpu_count: number;
}
// 启动时间
export interface BootTime {
boot_time: string;
uptime_seconds: number;
@@ -159,6 +171,7 @@ export interface BootTime {
uptime_minutes: number;
}
// 用户信息
export interface UserInfo {
name: string;
terminal?: string;
@@ -167,12 +180,14 @@ export interface UserInfo {
pid?: number;
}
// 电池信息
export interface BatteryInfo {
percent: number;
power_plugged: boolean;
seconds_left?: number;
}
// 实时统计
export interface RealtimeStats {
cpu_percent: number;
memory_percent: number;
@@ -202,6 +217,7 @@ export interface RealtimeStats {
timestamp: string;
}
// 服务器监控完整响应
export interface ServerMonitorResponse {
basic_info: BasicInfo;
cpu_info: CpuInfo;
@@ -215,62 +231,105 @@ export interface ServerMonitorResponse {
timestamp: string;
}
/**
* API调用函数
*/
/**
* 获取服务器完整监控信息
*/
export async function getServerOverviewApi() {
return requestClient.get<ServerMonitorResponse>(
'/api/core/server_monitor/overview',
);
}
/**
* 获取实时统计信息
*/
export async function getRealtimeStatsApi() {
return requestClient.get<RealtimeStats>('/api/core/server_monitor/realtime');
}
/**
* 获取基础系统信息
*/
export async function getBasicInfoApi() {
return requestClient.get<BasicInfo>('/api/core/server_monitor/basic_info');
}
/**
* 获取CPU信息
*/
export async function getCpuInfoApi() {
return requestClient.get<CpuInfo>('/api/core/server_monitor/cpu_info');
}
/**
* 获取内存信息
*/
export async function getMemoryInfoApi() {
return requestClient.get<MemoryInfo>('/api/core/server_monitor/memory_info');
}
/**
* 获取磁盘信息
*/
export async function getDiskInfoApi() {
return requestClient.get<DiskInfo>('/api/core/server_monitor/disk_info');
}
/**
* 获取网络信息
*/
export async function getNetworkInfoApi() {
return requestClient.get<NetworkInfo>(
'/api/core/server_monitor/network_info',
);
}
/**
* 获取进程信息
*/
export async function getProcessInfoApi() {
return requestClient.get<ProcessInfo>(
'/api/core/server_monitor/process_info',
);
}
/**
* 获取系统负载信息
*/
export async function getSystemLoadApi() {
return requestClient.get<SystemLoad>('/api/core/server_monitor/system_load');
}
/**
* 获取系统启动时间信息
*/
export async function getBootTimeApi() {
return requestClient.get<BootTime>('/api/core/server_monitor/boot_time');
}
/**
* 获取用户信息
*/
export async function getUsersInfoApi() {
return requestClient.get<UserInfo[]>('/api/core/server_monitor/users_info');
}
/**
* 获取温度信息
*/
export async function getTemperatureInfoApi() {
return requestClient.get<Record<string, any>>(
'/api/core/server_monitor/temperature_info',
);
}
/**
* 获取电池信息
*/
export async function getBatteryInfoApi() {
return requestClient.get<BatteryInfo>(
'/api/core/server_monitor/battery_info',
+1 -1
View File
@@ -71,7 +71,7 @@ export function mergePreferencesConfig(
current: PreferencesConfig,
updates: PreferencesConfig,
): PreferencesConfig {
return merge({}, current, updates) as PreferencesConfig;
return merge({}, updates, current) as PreferencesConfig;
}
// ============ 前端偏好配置API ============
+253 -18
View File
@@ -39,6 +39,46 @@ export namespace WebSocketApi {
heartbeatInterval?: number;
}
/** 监控数据类型 */
export interface MonitorMessage {
type:
| 'get_overview'
| 'get_realtime'
| 'set_interval'
| 'start_monitor'
| 'stop_monitor'
| 'test_connection';
interval?: number;
timestamp?: string;
}
/** 服务器监控数据 */
export interface ServerMonitorData {
basic_info?: any;
cpu_info?: any;
memory_info?: any;
disk_info?: any;
network_info?: any;
process_info?: any;
system_load?: any;
boot_time?: any;
users_info?: any;
timestamp?: string;
}
/** Redis监控数据 */
export interface RedisMonitorData {
connection_id?: string;
connection_name?: string;
status?: string;
info?: any;
memory?: any;
stats?: any;
keyspace?: any[];
clients?: any[];
slow_log?: any[];
timestamp?: string;
}
}
/**
@@ -359,26 +399,34 @@ export class WebSocketManager {
/**
* 创建WebSocket连接
*/
function buildWebSocketUrl(endpoint: string): string {
const apiUrl = import.meta.env.VITE_GLOB_API_URL || '';
const currentProtocol = location.protocol === 'https:' ? 'wss:' : 'ws:';
let wsOrigin = `${currentProtocol}//${location.host}`;
let apiPath = apiUrl;
if (/^https?:\/\//i.test(apiUrl)) {
const parsed = new URL(apiUrl);
wsOrigin = `${parsed.protocol === 'https:' ? 'wss:' : 'ws:'}//${parsed.host}`;
apiPath = parsed.pathname;
}
const basePath = apiPath
.replace(/\/$/, '')
.replace(/\/(?:basic-api|api)$/i, '');
const normalizedBase = basePath && basePath !== '/' ? basePath : '';
const normalizedEndpoint = endpoint.startsWith('/') ? endpoint : `/${endpoint}`;
return `${wsOrigin}${normalizedBase}${normalizedEndpoint}`;
}
export function createWebSocket(
endpoint: string,
callbacks?: WebSocketApi.WebSocketCallbacks,
): WebSocketManager {
// 构建WebSocket URL
let wsUrl: string;
if (import.meta.env.DEV) {
// 开发环境:直接连接到后端服务器
const wsProtocol = location.protocol === 'https:' ? 'wss:' : 'ws:';
wsUrl = `${wsProtocol}//localhost:8000${endpoint}`;
} else {
// 生产环境:使用当前域名
const wsProtocol = location.protocol === 'https:' ? 'wss:' : 'ws:';
const wsHost = location.host;
wsUrl = `${wsProtocol}//${wsHost}${endpoint}`;
}
const config: WebSocketApi.WebSocketConfig = {
url: wsUrl,
url: buildWebSocketUrl(endpoint),
reconnect: true,
maxReconnectAttempts: 5,
reconnectInterval: 3000,
@@ -390,7 +438,7 @@ export function createWebSocket(
}
/**
* Create test WebSocket connection
* 创建测试WebSocket连接
*/
export function createTestWebSocket(
callbacks?: WebSocketApi.WebSocketCallbacks,
@@ -399,7 +447,7 @@ export function createTestWebSocket(
}
/**
* Create notification WebSocket connection
* 创建通知WebSocket连接
*/
export function createNotificationWebSocket(
callbacks?: WebSocketApi.WebSocketCallbacks,
@@ -408,10 +456,197 @@ export function createNotificationWebSocket(
}
/**
* Create chat WebSocket connection
* 创建服务器监控WebSocket连接
*/
export function createServerMonitorWebSocket(
callbacks?: WebSocketApi.WebSocketCallbacks,
): WebSocketManager {
return createWebSocket('/ws/server-monitor/', callbacks);
}
/**
* 创建Redis监控WebSocket连接
*/
export function createRedisMonitorWebSocket(
callbacks?: WebSocketApi.WebSocketCallbacks,
): WebSocketManager {
return createWebSocket('/ws/redis-monitor/', callbacks);
}
/**
* 创建数据库监控WebSocket连接
*/
export function createDatabaseMonitorWebSocket(
callbacks?: WebSocketApi.WebSocketCallbacks,
): WebSocketManager {
return createWebSocket('/ws/database-monitor/', callbacks);
}
/**
* 监控WebSocket管理器类
*/
export class MonitorWebSocketManager extends WebSocketManager {
/**
* 获取概览信息
*/
getOverview(): boolean {
return this.send({
type: 'get_overview',
timestamp: new Date().toISOString(),
});
}
/**
* 获取实时统计
*/
getRealtime(): boolean {
return this.send({
type: 'get_realtime',
timestamp: new Date().toISOString(),
});
}
/**
* 开始监控
*/
startMonitoring(): boolean {
return this.send({
type: 'start_monitor',
timestamp: new Date().toISOString(),
});
}
/**
* 停止监控
*/
stopMonitoring(): boolean {
return this.send({
type: 'stop_monitor',
timestamp: new Date().toISOString(),
});
}
/**
* 测试连接(适用于Redis监控)
*/
testConnection(): boolean {
return this.send({
type: 'test_connection',
timestamp: new Date().toISOString(),
});
}
}
/**
* 创建服务器监控WebSocket管理器
*/
export function createServerMonitorManager(
callbacks?: WebSocketApi.WebSocketCallbacks,
): MonitorWebSocketManager {
const wsManager = createServerMonitorWebSocket(callbacks);
// 创建增强版管理器
return Object.setPrototypeOf(wsManager, MonitorWebSocketManager.prototype);
}
/**
* 创建Redis监控WebSocket管理器
*/
export function createRedisMonitorManager(
callbacks?: WebSocketApi.WebSocketCallbacks,
): MonitorWebSocketManager {
const wsManager = createRedisMonitorWebSocket(callbacks);
// 创建增强版管理器
return Object.setPrototypeOf(wsManager, MonitorWebSocketManager.prototype);
}
/**
* 数据库监控WebSocket管理器类
*/
export class DatabaseMonitorWebSocketManager extends WebSocketManager {
/**
* 获取数据库配置列表
*/
getConfigs(): boolean {
return this.send({
type: 'get_configs',
timestamp: new Date().toISOString(),
});
}
/**
* 获取概览信息
*/
getOverview(dbName: string): boolean {
return this.send({
type: 'get_overview',
db_name: dbName,
timestamp: new Date().toISOString(),
});
}
/**
* 获取实时统计
*/
getRealtime(dbName: string): boolean {
return this.send({
type: 'get_realtime',
db_name: dbName,
timestamp: new Date().toISOString(),
});
}
/**
* 开始监控
*/
startMonitoring(dbName: string): boolean {
return this.send({
type: 'start_monitor',
db_name: dbName,
timestamp: new Date().toISOString(),
});
}
/**
* 停止监控
*/
stopMonitoring(): boolean {
return this.send({
type: 'stop_monitor',
timestamp: new Date().toISOString(),
});
}
/**
* 测试连接
*/
testConnection(dbName: string): boolean {
return this.send({
type: 'test_connection',
db_name: dbName,
timestamp: new Date().toISOString(),
});
}
}
/**
* 创建聊天WebSocket连接
*/
export function createChatWebSocket(
callbacks?: WebSocketApi.WebSocketCallbacks,
): WebSocketManager {
return createWebSocket('/ws/chat/', callbacks);
}
/**
* 创建数据库监控WebSocket管理器
*/
export function createDatabaseMonitorManager(
callbacks?: WebSocketApi.WebSocketCallbacks,
): DatabaseMonitorWebSocketManager {
const wsManager = createDatabaseMonitorWebSocket(callbacks);
// 创建增强版管理器
return Object.setPrototypeOf(
wsManager,
DatabaseMonitorWebSocketManager.prototype,
);
}