Adapters use Unsupportedf instead of silently dropping data they cannot
express. The formatted message is the point: it tells the caller precisely which
part failed, so they can fix it rather than guess.
Reference#
func Unsupportedf(provider, format string, args ...any) error
Parameters
provider— the adapter's name.format,args— afmt-style message naming what could not be represented.
Returns
An *Error with Kind: ErrUnsupported, no status code, and the formatted
message.
Caveats
- It is normally returned before any network call, so it costs nothing.
Retryable()returns false — a provider that structurally cannot express something will not be able to on a second attempt.Client.Modelstreats it specially and does not retry it at all.- Name the specific thing. "unsupported" tells the caller nothing they did not already know from the sentinel.
Usage#
Rejecting a part an adapter cannot render
if img.URL != "" {
// Name the constraint, so the caller knows what to change.
return nil, skyl.Unsupportedf(p.Name(),
"Gemini requires inline image data, not a URL")
}if img.URL != "" {
// Name the constraint, so the caller knows what to change.
return nil, skyl.Unsupportedf(p.Name(),
"Gemini requires inline image data, not a URL")
}Naming a role restriction
if m.Role == skyl.RoleTool {
if _, isText := part.(skyl.Text); isText {
return nil, skyl.Unsupportedf(p.Name(),
"tool messages may only contain tool results")
}
}if m.Role == skyl.RoleTool {
if _, isText := part.(skyl.Text); isText {
return nil, skyl.Unsupportedf(p.Name(),
"tool messages may only contain tool results")
}
}Reporting it to a user
var e *skyl.Error
if errors.As(err, &e) && errors.Is(err, skyl.ErrUnsupported) {
// The message is specific enough to show directly.
return fmt.Errorf("this model (%s) cannot handle that input: %s", e.Provider, e.Message)
}var e *skyl.Error
if errors.As(err, &e) && errors.Is(err, skyl.ErrUnsupported) {
// The message is specific enough to show directly.
return fmt.Errorf("this model (%s) cannot handle that input: %s", e.Provider, e.Message)
}Troubleshooting#
Should my adapter drop the data instead?
No. Silent data loss is the worst failure mode this library has — a dropped image looks exactly like a model that ignored the question, and the caller will spend an afternoon on the prompt before suspecting the transport.
Should I return this for a feature the provider might add later?
Yes. It is the honest answer today, and it costs the caller one line to route
around via ProviderOptions. Pretending support exists is worse.