jaegertracing/jaeger · warning
api_v3 does not expose the backend's search capabilities: %w
Error message
api_v3 does not expose the backend's search capabilities: %w
What it means
traceReader.SearchCapabilities must report what search predicates the underlying storage supports, but api_v3 has no capability-discovery RPC, so the client cannot learn what the remote query service supports. Rather than guess, it returns the zero tracestore.SearchCapabilities wrapped with errors.ErrUnsupported and the message 'api_v3 does not expose the backend's search capabilities'.
Source
Thrown at cmd/jaeger/internal/integration/trace_reader.go:50
var (
_ tracestore.Reader = (*traceReader)(nil)
_ io.Closer = (*traceReader)(nil)
)
// traceReader retrieves trace data from the jaeger-v2 query service through the api_v2.QueryServiceClient.
type traceReader struct {
logger *zap.Logger
clientConn *grpc.ClientConn
client api_v3.QueryServiceClient
}
// SearchCapabilities cannot be answered: api_v3 has no capability discovery, so this
// client has no way to ask the query service what the storage behind it supports
// (RFC 0013 §3.7 proposes the API that would let it). Reporting ErrUnsupported says
// exactly that, where any concrete value would be a guess a caller might trust.
func (*traceReader) SearchCapabilities(context.Context) (tracestore.SearchCapabilities, error) {
return tracestore.SearchCapabilities{}, fmt.Errorf(
"api_v3 does not expose the backend's search capabilities: %w", errors.ErrUnsupported,
)
}
func createTraceReader(logger *zap.Logger, port int) (*traceReader, error) {
logger.Info("Creating the trace reader", zap.Int("port", port))
opts := []grpc.DialOption{
grpc.WithTransportCredentials(insecure.NewCredentials()),
}
cc, err := grpc.NewClient(ports.PortToHostPort(port), opts...)
if err != nil {
return nil, err
}
return &traceReader{
logger: logger,
clientConn: cc,View on GitHub (pinned to 806f444784)
Solutions
- Treat errors.ErrUnsupported as expected for api_v3 and use conservative/default search behavior
- Use a native tracestore Reader (e.g. direct storage backend) instead of the api_v3 remote reader if capabilities matter
- Adopt the capability-discovery API proposed in RFC 0013 §3.7 once available
Example fix
// before
caps, err := reader.SearchCapabilities(ctx)
if err != nil { return err }
// after
caps, err := reader.SearchCapabilities(ctx)
if errors.Is(err, errors.ErrUnsupported) {
caps = tracestore.SearchCapabilities{} // assume minimal support
} else if err != nil { return err } Defensive patterns
Strategy: fallback
Validate before calling
// capability probe caps, err := reader.SearchCapabilities(ctx) supportsMaxDuration := err == nil && caps.MaxDuration
Try / catch
caps, err := reader.SearchCapabilities(ctx)
switch {
case err == nil:
useCaps(caps)
case errors.Is(err, errors.ErrUnsupported): // api_v3 reader
useCaps(tracestore.SearchCapabilities{}) // conservative defaults
default:
return err
} Prevention
- Never assume capability discovery exists for remote api_v3 backends
- Design callers to accept zero-value capabilities meaningfully
- Track RFC 0013 for a real capability API and migrate when available
When it happens
Trigger: Any call to SearchCapabilities on the api_v3-based traceReader (used by e2e integration tests driving jaeger over the wire) — unconditionally returns this error.
Common situations: Test frameworks or code probing search capabilities of a remote jaeger reached through api_v3; capability-adaptive callers that skip unsupported predicates will always take their 'unsupported' path with this backend.
Related errors
- %s and %s are required
- %s must be before %s
- SearchDepth must not be greater than %d
- remote server does not support FindTraceSummaries: %w
- %w: %w
AI-assisted analysis of jaegertracing/jaeger@806f444784 (2026-09-01).
Data as JSON: /api/errors/164c329ebbe978f2.
Report an issue: GitHub.