diff --git a/head.go b/head.go index 8f5beb4fb6..1d0f688395 100644 --- a/head.go +++ b/head.go @@ -833,24 +833,17 @@ func (h *headIndexReader) SortedPostings(p Postings) Postings { if err := p.Err(); err != nil { return errPostings{err: errors.Wrap(err, "expand postings")} } - var err error sort.Slice(ep, func(i, j int) bool { - if err != nil { - return false - } a := h.head.series.getByID(ep[i]) b := h.head.series.getByID(ep[j]) if a == nil || b == nil { - err = errors.Errorf("series not found") + level.Debug(h.head.logger).Log("msg", "looked up series not found") return false } return labels.Compare(a.lset, b.lset) < 0 }) - if err != nil { - return errPostings{err: err} - } return newListPostings(ep) } diff --git a/index.go b/index.go index 89f7764331..c0680aa338 100644 --- a/index.go +++ b/index.go @@ -525,6 +525,8 @@ type IndexReader interface { // Postings returns the postings list iterator for the label pair. // The Postings here contain the offsets to the series inside the index. + // Found IDs are not strictly required to point to a valid Series, e.g. during + // background garbage collections. Postings(name, value string) (Postings, error) // SortedPostings returns a postings list that is reordered to be sorted @@ -533,6 +535,7 @@ type IndexReader interface { // Series populates the given labels and chunk metas for the series identified // by the reference. + // Returns ErrNotFound if the ref does not resolve to a known series. Series(ref uint64, lset *labels.Labels, chks *[]ChunkMeta) error // LabelIndices returns the label pairs for which indices exist. diff --git a/querier.go b/querier.go index 808a1057aa..12e05e79df 100644 --- a/querier.go +++ b/querier.go @@ -450,6 +450,10 @@ Outer: for s.p.Next() { ref := s.p.At() if err := s.index.Series(ref, &lset, &chunks); err != nil { + // Postings may be stale. Skip if no underlying series exists. + if errors.Cause(err) == ErrNotFound { + continue + } s.err = err return false } diff --git a/querier_test.go b/querier_test.go index e46f3b9475..b6f95bf7ce 100644 --- a/querier_test.go +++ b/querier_test.go @@ -702,9 +702,8 @@ func TestBaseChunkSeries(t *testing.T) { ref: 108, }, }, - postings: []uint64{12, 10, 108}, - - expIdxs: []int{0, 1, 3}, + postings: []uint64{12, 13, 10, 108}, // 13 doesn't exist and should just be skipped over. + expIdxs: []int{0, 1, 3}, }, { series: []refdSeries{ @@ -718,12 +717,11 @@ func TestBaseChunkSeries(t *testing.T) { { lset: labels.New([]labels.Label{{"b", "c"}}...), chunks: []ChunkMeta{{Ref: 8282}}, - ref: 1, + ref: 3, }, }, postings: []uint64{}, - - expIdxs: []int{}, + expIdxs: []int{}, }, }