Files
LokiStack/frontend/src/api/ai/index.ts
T
opsx c216bdfdd4
CI / Backend (go vet + test) (push) Canceled after 0s
CI / Frontend (lint + build + test) (push) Canceled after 0s
feat(ai): 助手浮窗聚焦日志查询页,携带当前查询结果对话
- 浮球只在 /logs 渲染(产品定位:辅助分析正在查看的查询结果,其它页面不打扰)
- /logs 查询成功后写入 AI 上下文:LogQL、时间范围、结果条数、error 行数、
  最新 20 条样本(去 CRI 包装);对话请求自动携带
- 后端 /ai/chat 接收 context:截断 6000 字 + RedactTextOnly 统一脱敏后并入 system
  (ECHO 假模型实测注入完整);空态文案改为查询导向
2026-11-01 00:31:48 +08:00

98 lines
2.7 KiB
TypeScript

import { http } from '@/api/http'
export interface AIConfig {
enabled: boolean
provider: string
baseUrl: string
/** 后端永远返回掩码(sk-***abcd),保存时留空表示不修改 */
apiKey: string
model: string
temperature: number
maxTokens: number
timeoutSec: number
dailyTokenCap: number
maxScanBytes: number
redactExtra: string[]
}
export interface AIConfigResponse {
config: AIConfig
tokenUsedToday: number
}
export interface AIFinding {
title: string
evidence: string
severity: 'high' | 'medium' | 'low' | string
}
export interface AIAnalysisResult {
summary: string
findings: AIFinding[]
actions: string[]
unknowns: string[]
parseError?: string
}
export interface AISignalBundle {
sourceId: number
sourceName: string
selector: string
from: string
to: string
rangeMinutes: number
totalBytes: number
totalEntries: number
entriesExact: boolean
apps: Array<{ app: string; namespace: string; entries: number; bytes: number; share: string }>
alerts: Array<{ ruleName: string; status: string; count: number; createdAt: string }>
baseline?: { previousBytes: number; currentBytes: number; deltaPercent: number; comparisonNote: string }
snapshotHours: number
warnings: string[]
}
export interface AIRun {
id: number
userId: number
username: string
sourceId: number
sourceName: string
rangeMinutes: number
model: string
question: string
status: string
error: string
conclusion: string
promptPayload: string
promptTokens: number
completionTokens: number
scanBytes: number
durationMs: number
createdAt: string
}
export interface AIAnalyzeResponse {
result: AIAnalysisResult
signals: AISignalBundle
prompt: string
run: AIRun
warnings: string[]
}
export const aiApi = {
getConfig: () => http.get<AIConfigResponse>('/ai/config'),
saveConfig: (data: Partial<AIConfig>) => http.put<{ config: AIConfig }>('/ai/config', data),
testConfig: (data: { baseUrl?: string; model?: string; apiKey?: string }) =>
http.post<{ model: string; latencyMs: number; tokensUsed: number; replyLength: number }>('/ai/config/test', data, { timeout: 45000 }),
analyze: (data: { sourceId: number; start: number; end: number; question?: string; app?: string }) =>
http.post<AIAnalyzeResponse>('/ai/analyze', data, { timeout: 180000 }),
runs: (page: number, pageSize: number) =>
http.get<{ list: AIRun[]; total: number; page: number; pageSize: number }>(
`/ai/runs?page=${page}&pageSize=${pageSize}`,
),
run: (id: number) => http.get<AIRun>(`/ai/runs/${id}`),
chat: (data: { sourceId?: number; history: Array<{ role: 'user' | 'assistant'; content: string }>; page?: string; rangeMinutes?: number; context?: string }) =>
http.post<{ reply: string }>('/ai/chat', data),
}