Files
AutoZero/llm/provider_test.go
T
Sakurasan d5dac5a6fc feat: AutoZero 通用 Agent 框架(从 AutoGo 五阶段拆分完成)
llm(三协议 Provider)/ session(JSONL 持久化)/ tools(Registry、围栏、
builtin、computer)/ cdp(browser)/ skills / mcp / agent(循环、两级压缩、
编排、审批门控)+ 底座 jsonl/textx/execx/diag/scratch/spill/imagecache。

产品装配代码(config 桥接、schedule 工具、memory/plan/retro/prompt)
留在 AutoGo,宿主接入方式见 MIGRATION.md。
2026-10-26 00:54:46 +08:00

140 lines
4.5 KiB
Go

package llm
import (
"reflect"
"testing"
)
func TestFilterAllowed(t *testing.T) {
models := []string{"glm-4.7", "glm-4.7-air", "glm-4.6", "deepseek-v4-flash", "gpt-5-mini"}
// 空白名单不筛选
if got := FilterAllowed(models, nil); !reflect.DeepEqual(got, models) {
t.Errorf("FilterAllowed(nil) = %v, want unchanged", got)
}
// 前缀通配
if got := FilterAllowed(models, []string{"glm-*"}); !reflect.DeepEqual(got, []string{"glm-4.7", "glm-4.7-air", "glm-4.6"}) {
t.Errorf("FilterAllowed(glm-*) = %v", got)
}
// 精确名大小写不敏感 + 通配混合
if got := FilterAllowed(models, []string{"GLM-4.7", "deepseek-*"}); !reflect.DeepEqual(got, []string{"glm-4.7", "deepseek-v4-flash"}) {
t.Errorf("FilterAllowed(mixed) = %v", got)
}
// 全不匹配
if got := FilterAllowed(models, []string{"claude-*"}); len(got) != 0 {
t.Errorf("FilterAllowed(claude-*) = %v, want empty", got)
}
}
func TestNormalizeAPIFormat(t *testing.T) {
cases := map[string]APIFormat{
"anthropic": FormatAnthropic,
"Anthropic_Messages": FormatAnthropic,
"openai": FormatChatCompletions,
"chat": FormatChatCompletions,
"chat_completions": FormatChatCompletions,
"Responses": FormatResponses,
"": "",
"graphql": "",
}
for in, want := range cases {
if got := NormalizeAPIFormat(in); got != want {
t.Errorf("NormalizeAPIFormat(%q) = %q, want %q", in, got, want)
}
}
}
func TestNewProviderFormats(t *testing.T) {
// 三种格式各自构造出对应 provider
p1, err := NewProvider(ProviderSpec{BaseURL: "https://x.com", APIFormat: FormatAnthropic})
if err != nil || p1 == nil {
t.Errorf("anthropic: %v", err)
}
p2, err := NewProvider(ProviderSpec{BaseURL: "https://x.com/v1", APIFormat: FormatChatCompletions})
if err != nil {
t.Errorf("chat: %v", err)
}
if _, ok := p2.(*OpenAIProvider); !ok {
t.Errorf("chat_completions should yield OpenAIProvider, got %T", p2)
}
p3, err := NewProvider(ProviderSpec{BaseURL: "https://x.com/v1", APIFormat: FormatResponses})
if err != nil {
t.Errorf("responses: %v", err)
}
if _, ok := p3.(*ResponsesProvider); !ok {
t.Errorf("responses should yield ResponsesProvider, got %T", p3)
}
// 未知格式报错
if _, err := NewProvider(ProviderSpec{BaseURL: "https://x.com", APIFormat: "graphql"}); err == nil {
t.Error("unknown format should error")
}
// BaseURL 含 anthropic 时自动推断
p4, _ := NewProvider(ProviderSpec{BaseURL: "https://api.anthropic.com"})
if _, ok := p4.(*AnthropicProvider); !ok {
t.Errorf("anthropic URL should infer AnthropicProvider, got %T", p4)
}
}
// TestMissingRegisteredModels:下架判定——大小写不敏感、通配条目不参与
// 判定(既不标下架也不算存活)、空目录不判定、原文保序去重。
func TestMissingRegisteredModels(t *testing.T) {
fetched := []string{"glm-4.7", "GLM-4.6", "cogview-4", "glm-4.5-air"}
cases := []struct {
name string
registered []string
fetched []string
want []string
}{
{
name: "精确匹配大小写不敏感",
registered: []string{"glm-4.7", "glm-4.6", "dead-model"},
fetched: fetched,
want: []string{"dead-model"},
},
{
name: "通配条目不参与判定",
registered: []string{"glm-*", "kling-*"},
fetched: fetched,
want: nil, // 模式无法对具体目录下结论:跳过,不标下架
},
{
name: "空目录不判定(拉取失败不误标)",
registered: []string{"glm-4.7"},
fetched: nil,
want: nil,
},
{
name: "保序去重、跳过空条目",
registered: []string{"b-dead", "", "a-dead", "B-DEAD"},
fetched: fetched,
want: []string{"b-dead", "a-dead"},
},
{
name: "全部存活返回 nil",
registered: []string{"GLM-4.7", "cogview-4"},
fetched: fetched,
want: nil,
},
}
for _, c := range cases {
got := MissingRegisteredModels(c.registered, c.fetched)
if len(got) != len(c.want) {
t.Errorf("%s: got %v, want %v", c.name, got, c.want)
continue
}
for i := range got {
if got[i] != c.want[i] {
t.Errorf("%s: got[%d]=%q, want %q", c.name, i, got[i], c.want[i])
}
}
}
}
// TestFilterAllowed 与 MissingRegisteredModels 口径一致:同一个匹配函数。
func TestFilterAllowedWildcard(t *testing.T) {
got := FilterAllowed([]string{"glm-4.7", "cogview-4"}, []string{"glm-*"})
if len(got) != 1 || got[0] != "glm-4.7" {
t.Errorf("FilterAllowed = %v, want [glm-4.7]", got)
}
}