| 572 | } |
| 573 | |
| 574 | func (b *blockBaseSeriesSet) Next() bool { |
| 575 | for b.p.Next() { |
| 576 | if err := b.index.Series(b.p.At(), &b.builder, &b.bufChks); err != nil { |
| 577 | // Postings may be stale. Skip if no underlying series exists. |
| 578 | if errors.Is(err, storage.ErrNotFound) { |
| 579 | continue |
| 580 | } |
| 581 | b.err = fmt.Errorf("get series %d: %w", b.p.At(), err) |
| 582 | return false |
| 583 | } |
| 584 | |
| 585 | if len(b.bufChks) == 0 { |
| 586 | continue |
| 587 | } |
| 588 | |
| 589 | intervals, err := b.tombstones.Get(b.p.At()) |
| 590 | if err != nil { |
| 591 | b.err = fmt.Errorf("get tombstones: %w", err) |
| 592 | return false |
| 593 | } |
| 594 | |
| 595 | // NOTE: |
| 596 | // * block time range is half-open: [meta.MinTime, meta.MaxTime). |
| 597 | // * chunks are both closed: [chk.MinTime, chk.MaxTime]. |
| 598 | // * requested time ranges are closed: [req.Start, req.End]. |
| 599 | |
| 600 | var trimFront, trimBack bool |
| 601 | |
| 602 | // Copy chunks as iterables are reusable. |
| 603 | // Count those in range to size allocation (roughly - ignoring tombstones). |
| 604 | nChks := 0 |
| 605 | for _, chk := range b.bufChks { |
| 606 | if chk.MaxTime >= b.mint && chk.MinTime <= b.maxt { |
| 607 | nChks++ |
| 608 | } |
| 609 | } |
| 610 | chks := make([]chunks.Meta, 0, nChks) |
| 611 | |
| 612 | // Prefilter chunks and pick those which are not entirely deleted or totally outside of the requested range. |
| 613 | for _, chk := range b.bufChks { |
| 614 | if chk.MaxTime < b.mint { |
| 615 | continue |
| 616 | } |
| 617 | if chk.MinTime > b.maxt { |
| 618 | continue |
| 619 | } |
| 620 | if (tombstones.Interval{Mint: chk.MinTime, Maxt: chk.MaxTime}.IsSubrange(intervals)) { |
| 621 | continue |
| 622 | } |
| 623 | chks = append(chks, chk) |
| 624 | |
| 625 | // If still not entirely deleted, check if trim is needed based on requested time range. |
| 626 | if !b.disableTrimming { |
| 627 | if chk.MinTime < b.mint { |
| 628 | trimFront = true |
| 629 | } |
| 630 | if chk.MaxTime > b.maxt { |
| 631 | trimBack = true |