mirror of
https://github.com/Twigpine/zero.git
synced 2026-11-10 05:01:28 -10:00
* feat: use Exa as default search provider Amp-Thread-ID: https://ampcode.com/threads/T-01a01522-a5f1-7139-8a55-5e417cba2751 Co-authored-by: Amp <[email protected]> * fix(config): carry a legacy default's disable across the Exa migration A user who ran `zero mcp disable firecrawl` chose not to open that outbound connection. Renaming the built-in default to exa re-opened it under the new name on upgrade, and because the replacement looked like an untouched default the startup warning stayed quiet too. Carry an explicit user-level disable of a retired default onto its successor, but only when the user never declared the successor themselves — an explicit exa entry wins either way. The carried-over disable is recorded as a user-level decision, so the lower-trust project layer cannot lift it while `zero mcp enable exa` still can. Regression coverage: the legacy-disabled upgrade path, the explicit-exa override, a configured-but-enabled legacy entry, the CLI re-enable, the project-layer re-enable attempt, and the resulting startup behavior (NormalizeConfig must not hand back an exa server to connect to). Co-Authored-By: Claude Opus 5 (1M context) <[email protected]> * fix(config): keep a retired default's transport for partial user entries A user who added an API key to the firecrawl default wrote only the header — the seeded default supplied the http type and URL. Once the default stops being seeded that entry resolves with no type, url, or command, and NormalizeConfig rejects it, taking down startup for every other server too rather than just that one. Record what Zero used to ship for a retired default and re-seed it under the user's own fields. Only for an entry that named no transport of its own: an entry with a self-hosted url or a stdio command is a complete definition the user owns, and grafting the retired http default onto a command produces a server that is rejected outright. Regression coverage at both ResolveMCP and NormalizeConfig for the header-only entry and its failure path, the self-hosted stdio entry that must be left alone, and a disabled retired entry keeping a usable transport so a later re-enable resolves. Co-Authored-By: Claude Opus 5 (1M context) <[email protected]> --------- Co-authored-by: Amp <[email protected]> Co-authored-by: Claude Opus 5 (1M context) <[email protected]>
47 lines
1.5 KiB
Go
47 lines
1.5 KiB
Go
package cli
|
|
|
|
import (
|
|
"bytes"
|
|
"encoding/json"
|
|
"path/filepath"
|
|
"testing"
|
|
|
|
"github.com/Gitlawb/zero/internal/config"
|
|
)
|
|
|
|
// `zero mcp disable exa` must work even though exa is a built-in
|
|
// default that is not written to the user's config file until overridden.
|
|
func TestRunMCPDisableSeededExaDefault(t *testing.T) {
|
|
configPath := filepath.Join(t.TempDir(), "zero", "config.json")
|
|
// A config with no Exa entry — the default lives in code, not the file.
|
|
writeMCPCommandRawConfig(t, configPath, `{"activeProvider":"fast"}`)
|
|
|
|
var out, errBuf bytes.Buffer
|
|
code := runWithDeps([]string{"mcp", "disable", "exa", "--json"}, &out, &errBuf, appDeps{
|
|
userConfigPath: func() (string, error) { return configPath, nil },
|
|
})
|
|
if code != exitSuccess {
|
|
t.Fatalf("disable exit=%d stderr=%s", code, errBuf.String())
|
|
}
|
|
var payload struct {
|
|
ServerName string `json:"serverName"`
|
|
Disabled bool `json:"disabled"`
|
|
Changed bool `json:"changed"`
|
|
}
|
|
if err := json.Unmarshal(out.Bytes(), &payload); err != nil {
|
|
t.Fatalf("decode disable JSON: %v\n%s", err, out.String())
|
|
}
|
|
if payload.ServerName != "exa" || !payload.Disabled || !payload.Changed {
|
|
t.Fatalf("disable payload = %#v, want exa disabled+changed", payload)
|
|
}
|
|
|
|
// End-to-end: resolving that config now turns the default off.
|
|
cfg, err := config.ResolveMCP(config.ResolveOptions{UserConfigPath: configPath})
|
|
if err != nil {
|
|
t.Fatalf("ResolveMCP: %v", err)
|
|
}
|
|
if !cfg.Servers["exa"].Disabled {
|
|
t.Fatal("expected `mcp disable exa` to turn the seeded default off in the resolved config")
|
|
}
|
|
}
|