{"record":{"id":"2740b4866acb50e9","repo":"thanos-io/thanos","slug":"failed-to-convert-matchers-2740b4","errorCode":null,"errorMessage":"failed to convert matchers","messagePattern":"failed to convert matchers","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"cmd/thanos/sidecar.go","lineNumber":371,"sourceCode":"\t\t\tinfo.WithStatusInfoFunc(),\n\t\t)\n\n\t\tstatusSrv := status.NewServer(\n\t\t\tcomponent.Sidecar.String(),\n\t\t\tstatus.WithTSDBStatisticsGetter(\n\t\t\t\tstatus.TSDBStatisticsGetterFunc(func(limit int, matchers []storepb.LabelMatcher) (map[string]tsdb.Stats, error) {\n\t\t\t\t\tif !httpProbe.IsReady() {\n\t\t\t\t\t\treturn nil, errors.New(\"not ready\")\n\t\t\t\t\t}\n\n\t\t\t\t\tctx, cancel := context.WithTimeout(context.Background(), conf.prometheus.getConfigTimeout)\n\t\t\t\t\tdefer cancel()\n\n\t\t\t\t\t// Check if external labels match the provided matchers.\n\t\t\t\t\textLabels := m.Labels()\n\t\t\t\t\tpromMatchers, err := storepb.MatchersToPromMatchers(matchers...)\n\t\t\t\t\tif err != nil {\n\t\t\t\t\t\treturn nil, errors.Wrap(err, \"failed to convert matchers\")\n\t\t\t\t\t}\n\t\t\t\t\tfor _, matcher := range promMatchers {\n\t\t\t\t\t\tif !matcher.Matches(extLabels.Get(matcher.Name)) {\n\t\t\t\t\t\t\t// External labels don't match, return empty result.\n\t\t\t\t\t\t\treturn nil, nil\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tstatsEntry, err := c.TSDBStatusInGRPC(ctx, conf.prometheus.url, limit)\n\t\t\t\t\tif err != nil {\n\t\t\t\t\t\treturn nil, errors.Wrap(err, \"failed to get tsdb status from prometheus\")\n\t\t\t\t\t}\n\n\t\t\t\t\treturn map[string]tsdb.Stats{\n\t\t\t\t\t\t\"\": statsEntry.ToTSDBStats(limit),\n\t\t\t\t\t}, nil\n\t\t\t\t}),\n\t\t\t),","sourceCodeStart":353,"sourceCodeEnd":389,"githubUrl":"https://github.com/thanos-io/thanos/blob/35b8b991177def87ed52dcf10f9b6d87f07282c8/cmd/thanos/sidecar.go#L353-L389","documentation":"While serving TSDB statistics, the sidecar converts protobuf store matchers to Prometheus matchers via storepb.MatchersToPromMatchers. If any matcher has an invalid type or value, conversion fails and the RPC returns 'failed to convert matchers' wrapped with the underlying reason.","triggerScenarios":"errors.Wrap inside TSDBStatisticsGetterFunc: storepb.MatchersToPromMatchers(matchers...) errors because a LabelMatcher uses an unknown MatchType or an invalid regex value sent by the client.","commonSituations":"Custom tooling crafting LabelMatcher protos with a zero-value MatchType; clients built against a newer protobuf enum than the sidecar understands; malformed regex strings passed through UIs.","solutions":["Fix the client to send valid MatchType values (EQ, NEQ, RE, NRE) in each LabelMatcher","Validate regex matchers client-side before sending (regexp.Compile)","Align protobuf/store API versions between client and sidecar","Check the wrapped inner error in logs to identify the exact offending matcher"],"exampleFix":"// before\nmatcher := &storepb.LabelMatcher{Name: \"job\", Value: \"node\"}   // MatchType unset\n// after\nmatcher := &storepb.LabelMatcher{Type: storepb.LabelMatcher_EQ, Name: \"job\", Value: \"node\"}","handlingStrategy":"type-guard","validationCode":"for _, m := range matchers {\n    if m.Type < storepb.LabelMatcher_EQ || m.Type > storepb.LabelMatcher_NRE {\n        return fmt.Errorf(\"invalid matcher type %v for label %s\", m.Type, m.Name)\n    }\n    if m.Type == storepb.LabelMatcher_RE || m.Type == storepb.LabelMatcher_NRE {\n        if _, err := regexp.Compile(m.Value); err != nil {\n            return fmt.Errorf(\"invalid regex %q: %v\", m.Value, err)\n        }\n    }\n}","typeGuard":"func validMatcher(m *storepb.LabelMatcher) bool {\n    switch m.Type {\n    case storepb.LabelMatcher_EQ, storepb.LabelMatcher_NEQ,\n        storepb.LabelMatcher_RE, storepb.LabelMatcher_NRE:\n        if m.Type == storepb.LabelMatcher_RE || m.Type == storepb.LabelMatcher_NRE {\n            _, err := regexp.Compile(m.Value)\n            return err == nil\n        }\n        return true\n    }\n    return false\n}","tryCatchPattern":"promMatchers, err := storepb.MatchersToPromMatchers(matchers...)\nif err != nil {\n    return nil, status.Errorf(codes.InvalidArgument, \"bad matcher: %v\", err)\n}","preventionTips":["Always set the MatchType field explicitly when building LabelMatcher protos","Compile-validate regex values before sending","Keep client and server thanos/protobuf versions aligned","Log the offending matcher (name, type, value) when conversion fails"],"tags":["grpc","matchers","protobuf","validation"],"backgroundTag":"invalid-argument-value","analyzedSha":"35b8b991177def87ed52dcf10f9b6d87f07282c8","analyzedAt":"2026-09-07T01:49:59.689Z","contentChangedAt":"2026-09-07T01:49:59.689Z","schemaVersion":2},"datasetVersion":"2026-09-15T23:17:13.987Z"}