sipeed/picoclaw · error
model %q did not resolve to any provider candidates
Error message
model %q did not resolve to any provider candidates
What it means
After successfully constructing a provider for the requested model, SwitchModel calls resolveModelCandidates(cfg, defaultProvider, value, agent.Fallbacks) to build the fallback candidate chain and gets an empty list. Without candidates the agent has no usable model chain to run on, so the switch is aborted before any agent state (Model/Provider/Candidates) mutates.
Source
Thrown at pkg/agent/agent_command.go:313
}
rt.GetModelInfo = func() (string, string) {
return agent.Model, resolvedCandidateProvider(agent.Candidates, cfg.Agents.Defaults.Provider)
}
rt.SwitchModel = func(value string) (string, error) {
value = strings.TrimSpace(value)
modelCfg, err := resolvedModelConfig(cfg, value, agent.Workspace)
if err != nil {
return "", err
}
nextProvider, _, err := providers.CreateProviderFromConfig(modelCfg)
if err != nil {
return "", fmt.Errorf("failed to initialize model %q: %w", value, err)
}
nextCandidates := resolveModelCandidates(cfg, cfg.Agents.Defaults.Provider, value, agent.Fallbacks)
if len(nextCandidates) == 0 {
return "", fmt.Errorf("model %q did not resolve to any provider candidates", value)
}
oldModel := agent.Model
oldProvider := agent.Provider
agent.Model = value
agent.Provider = nextProvider
agent.Candidates = nextCandidates
agent.ThinkingLevel = parseThinkingLevel(modelCfg.ThinkingLevel)
agent.ThinkingLevelConfigured = isConfiguredThinkingLevel(modelCfg.ThinkingLevel)
if oldProvider != nil && oldProvider != nextProvider {
if stateful, ok := oldProvider.(providers.StatefulProvider); ok {
stateful.Close()
}
}
return oldModel, nil
}
View on GitHub (pinned to 49183d7e8d)
Solutions
- Check agents.defaults.provider in config matches a provider that serves the requested model
- Re-run /model with the fully qualified model identifier used elsewhere in config
- Print/inspect resolvedModelConfig and resolveModelCandidates inputs (config excerpts) to see why the chain is empty
- Fall back to a known-good model name, then re-add the problematic one step by step
Example fix
# before
agents:
defaults:
provider: anthropic
models:
fast:
provider: openai # never reachable as a candidate
# after
agents:
defaults:
provider: openai Defensive patterns
Strategy: validation
Validate before calling
candidates := resolveModelCandidates(cfg, cfg.Agents.Defaults.Provider, value, agent.Fallbacks)
if len(candidates) == 0 {
// chain empty: fix agents.defaults.provider vs model entry before calling SwitchModel
} Type guard
func modelHasCandidates(cfg *config.Config, provider, value string, fallbacks []string) bool {
return len(resolveModelCandidates(cfg, provider, value, fallbacks)) > 0
} Prevention
- Keep agents.defaults.provider aligned with the providers of switchable models
- Lint config: every switchable model must yield >=1 candidate under the default provider
- Prefer fully-qualified model identifiers over aliases
When it happens
Trigger: Config defines the model name but no provider mapping resolves it (e.g. provider defaults disagree with the model entry); fallback chain misconfigured such that filtering removes every candidate; referencing a model alias that exists for provider creation but not in the candidate-resolution rules.
Common situations: Hand-edited config where agents.defaults.provider points at a provider that does not offer the requested model; upgrade changed candidate resolution semantics; duplicate model names across providers with ambiguous resolution; empty fallbacks list plus mismatched default provider.
Related errors
- failed to initialize model %q: %w
- credential: enc:// passphrase required
- credential: enc:// decryption failed (wrong passphrase or SS
- host cannot be empty
- host list contains an empty entry
AI-assisted analysis of sipeed/picoclaw@49183d7e8d (2026-08-15).
Data as JSON: /api/errors/02ae9049ededae16.
Report an issue: GitHub.