This commit is contained in:
2025-12-09 13:40:41 +08:00
parent 9127df2600
commit 5b83f7a6d1
9 changed files with 442 additions and 113 deletions

4
src/ai/ai.ts Normal file
View File

@@ -0,0 +1,4 @@
import { App } from '@kevisual/app/src/app.ts';
import { storage } from '../module/query.ts';
export const app = new App({ token: storage.getItem('token') || '' });

6
src/ai/index.ts Normal file
View File

@@ -0,0 +1,6 @@
import { app } from './ai.ts'
import './routes/cmd-run.ts'
export {
app
}

54
src/ai/routes/cmd-run.ts Normal file
View File

@@ -0,0 +1,54 @@
import { app } from '../ai.ts';
import { execSync } from 'node:child_process'
const promptTemplate = `# CMD 结果判断器
分析上一条 CMD 命令的执行结果,判断是否需要执行下一条命令。
- 若结果中隐含或明确指示需继续执行 → 返回:\`{"cmd": "推断出的下一条命令", "type": "cmd"}\`
- 若无后续操作 → 返回:\`{"type": "none"}\`
1. 仅输出合法 JSON无任何额外文本。
2. \`cmd\` 必须从执行结果中合理推断得出,非预设或猜测。
3. 禁止解释、注释、换行或格式错误。`
app.router.route({
path: 'cmd-run',
description: '执行 CMD 命令并判断下一步操作, 参数是 cmd 字符串',
}).define(async (ctx) => {
const cmd = ctx.query.cmd || '';
if (!cmd) {
ctx.throw(400, 'cmd is required');
}
let result = '';
ctx.state.steps = ctx.state?.steps || [];
try {
result = execSync(cmd, { encoding: 'utf-8' });
ctx.state.steps.push({ cmd, result });
} catch (error: any) {
result = error.message || '';
ctx.state.steps.push({ cmd, result, error: true });
ctx.body = {
steps: ctx.state.steps,
}
return;
}
const prompt = `${promptTemplate}\n上一条命令:\n${cmd}\n执行结果:\n${result}\n`;
const response = await app.ai.question(prompt);
const msg = app.ai.utils.extractJsonFromMarkdown(app.ai.responseText);
try {
const { cmd, type } = msg;
if (type === 'cmd' && cmd) {
await app.router.call({ path: 'cmd-run', payload: { cmd } }, { state: ctx.state });
} else {
ctx.state.steps.push({ type: 'none' });
}
} catch (error) {
result = '执行错误,无法解析返回结果为合法 JSON' + app.ai.responseText
ctx.state.steps.push({ cmd, result, parseError: true });
}
ctx.body = {
steps: ctx.state.steps,
}
}).addTo(app.router);