feat(llm): 支持 OpenAI Responses API 格式的 LLM 配置

依赖升级到 norma v0.3.1(新增 FormatOpenAIResponses + reasoning_content 回传
修复)。每个 LLM profile 现在可选第三种格式 openai-responses,打
POST /v1/responses,与 Chat Completions / Anthropic 并列。

- agent.Config:ConfigFrom / FromEnv / Provider() 支持 openai-responses
  (BaseURL 归一化去 /responses 尾巴,默认 model gpt-5)
- server:saveLLMConfig 放开二元 format 归一;模型列表端点复用 OpenAI
  /models(Responses 模型列表仍在 /v1/models)
- db: llm_profiles 的 format CHECK 约束加入 openai-responses,并幂等迁移
  (DROP + ADD CONSTRAINT)补旧库
- web: 格式下拉新增「OpenAI (Responses API)」,类型与回显同步

流式/非流式两条路都走新 adapter;输出、token 统计、操作统计、LLM 录制
四条链路复用中性层,无需改动。
This commit is contained in:
Autumn-27 committed 2026-08-25 11:39:24 -04:00
1 parent 587ba422b4
commit 12541a6dec
9 files changed
+71 -16

No files matched your search

+7 -4
View File
@@ -296,7 +296,7 @@ function ProfileSheet({
}) {
const isNew = !profile;
const [name, setName] = React.useState("");
const [format, setFormat] = React.useState<"anthropic" | "openai">("anthropic");
const [format, setFormat] = React.useState<"anthropic" | "openai" | "openai-responses">("anthropic");
const [model, setModel] = React.useState("");
const [baseUrl, setBaseUrl] = React.useState("");
const [proxy, setProxy] = React.useState("");
@@ -321,7 +321,9 @@ function ProfileSheet({
React.useEffect(() => {
if (!open) return;
setName(profile?.name ?? "");
setFormat(profile?.format === "openai" ? "openai" : "anthropic");
setFormat(
profile?.format === "openai" || profile?.format === "openai-responses" ? profile.format : "anthropic",
);
setModel(profile?.model ?? "");
setBaseUrl(profile?.base_url ?? "");
setProxy(profile?.proxy ?? "");
@@ -448,13 +450,14 @@ function ProfileSheet({
</div>
<div className="grid gap-2">
<Label>格式</Label>
<Select value={format} onValueChange={(v) => setFormat(v as "anthropic" | "openai")}>
<Select value={format} onValueChange={(v) => setFormat(v as "anthropic" | "openai" | "openai-responses")}>
<SelectTrigger>
<SelectValue placeholder="选择格式" />
</SelectTrigger>
<SelectContent>
<SelectItem value="anthropic">Anthropic</SelectItem>
<SelectItem value="openai">OpenAI</SelectItem>
<SelectItem value="openai">OpenAI (Chat Completions)</SelectItem>
<SelectItem value="openai-responses">OpenAI (Responses API)</SelectItem>
</SelectContent>
</Select>
</div>
+1 -1
View File
@@ -782,7 +782,7 @@ export interface Settings {
export interface LLMProfile {
id: string;
name: string;
format: "openai" | "anthropic";
format: "openai" | "anthropic" | "openai-responses";
base_url?: string;
proxy?: string;
model: string;