Skip to content

Commit 3ee8c20

Browse files
committed
增加LLMMock功能,列表回复还存在一些bug,基础功能正常。
1 parent 55a932d commit 3ee8c20

6 files changed

Lines changed: 578 additions & 3 deletions

File tree

bun.lock

Lines changed: 55 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -209,7 +209,8 @@
209209
"wrap-ansi": "^10.0.0",
210210
"xss": "^1.0.15",
211211
"yaml": "^2.8.3",
212-
"zod": "^4.3.6"
212+
"zod": "^4.3.6",
213+
"llm-mock-server": "^1.0.9"
213214
},
214215
"optionalDependencies": {
215216
"doubaoime-asr": "^0.1.0"

scripts/dev.ts

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ const defines = {
2020
// (12MB) from accumulating during long-running sessions.
2121
// dev 模式使用 development 模式
2222
'process.env.NODE_ENV': JSON.stringify('production'),
23+
'process.env.MOCK_SERVER': JSON.stringify('true'),
2324
}
2425

2526
const defineArgs = Object.entries(defines).flatMap(([k, v]) => [
@@ -44,6 +45,21 @@ const inspectArgs = process.env.BUN_INSPECT
4445
? ['--inspect-wait=' + process.env.BUN_INSPECT]
4546
: []
4647

48+
const userArgs = process.argv.slice(2)
49+
if (defines['process.env.MOCK_SERVER'] === JSON.stringify('true')) {
50+
// 启动日志
51+
// 包装层日志打到 stderr,避免污染 CLI 的 stdout(管道模式)
52+
console.error('[dev] launching CLI')
53+
console.error('[dev] entry:', cliPath)
54+
console.error('[dev] version:', defines['MACRO.VERSION'] ?? '(unknown)')
55+
console.error('[dev] features:', allFeatures.length, 'enabled')
56+
if (inspectArgs.length > 0) {
57+
console.error('[dev] inspect:', process.env.BUN_INSPECT)
58+
}
59+
if (userArgs.length > 0) {
60+
console.error('[dev] args:', userArgs.join(' '))
61+
}
62+
}
4763
const result = Bun.spawnSync(
4864
[
4965
'bun',
@@ -52,7 +68,7 @@ const result = Bun.spawnSync(
5268
...defineArgs,
5369
...featureArgs,
5470
cliPath,
55-
...process.argv.slice(2),
71+
...userArgs,
5672
],
5773
{ stdio: ['inherit', 'inherit', 'inherit'], cwd: projectRoot },
5874
)

src/entrypoints/cli.tsx

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -377,6 +377,14 @@ async function main(): Promise<void> {
377377
await cliMain();
378378
profileCheckpoint('cli_after_main_complete');
379379
}
380-
380+
if (process.env.MOCK_SERVER === 'true') {
381+
import('../mock/mockServer.js')
382+
.then(({ runMock }) => {
383+
runMock();
384+
})
385+
.catch(err => {
386+
console.error('Failed to load mock server:', err);
387+
});
388+
}
381389
// eslint-disable-next-line custom-rules/no-top-level-side-effects
382390
await main();

src/mock/crypto.ts

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
import { createHash } from 'crypto'
2+
3+
// 递归排序对象键(保证序列化结果稳定)
4+
function sortObjectKeys(obj: any): any {
5+
if (obj === null || typeof obj !== 'object') return obj
6+
if (Array.isArray(obj)) return obj.map(sortObjectKeys)
7+
const sorted: any = {}
8+
Object.keys(obj)
9+
.sort()
10+
.forEach(key => {
11+
sorted[key] = sortObjectKeys(obj[key])
12+
})
13+
return sorted
14+
}
15+
16+
// 提取 Anthropic 请求中影响响应的关键字段
17+
function extractAnthropicKeyFields(body: any): any {
18+
// 可根据需求增删字段
19+
return {
20+
model: body.model,
21+
messages: body.messages, // 整个消息数组
22+
system: body.system,
23+
tools: body.tools,
24+
temperature: body.temperature,
25+
max_tokens: body.max_tokens,
26+
top_p: body.top_p,
27+
stop_sequences: body.stop_sequences,
28+
// 注意:stream 通常不影响内容,可以排除
29+
// metadata 中的 user_id 等也可以排除,或保留一部分
30+
}
31+
}
32+
33+
// 生成请求指纹(缓存键)
34+
export function getRequestFingerprint(reqBody: any): string {
35+
const keyFields = extractAnthropicKeyFields(reqBody)
36+
const sorted = sortObjectKeys(keyFields)
37+
const jsonStr = JSON.stringify(sorted)
38+
// 使用 SHA-256 作为键(可选,也可以直接用 jsonStr)
39+
return createHash('sha256').update(jsonStr).digest('hex')
40+
}

0 commit comments

Comments
 (0)