From 2b4ff620aaa63996c472c4148c682ee8f53f5d1b Mon Sep 17 00:00:00 2001 From: Bjoern Rabenstein Date: Tue, 14 Oct 2014 13:52:39 +0200 Subject: [PATCH] Return a nop iterator for series that have been purged completely. Change-Id: I6e92cac4472486feefdecba8593c17867e8c710d --- storage/local/series.go | 32 +++++++++++++++++++++++++------- storage/local/storage.go | 8 ++++++-- 2 files changed, 31 insertions(+), 9 deletions(-) diff --git a/storage/local/series.go b/storage/local/series.go index 7f18727b7..818f3db52 100644 --- a/storage/local/series.go +++ b/storage/local/series.go @@ -456,13 +456,6 @@ func (s *memorySeries) preloadChunksForRange(from clientmodel.Timestamp, through return s.preloadChunks(pinIndexes, p) } -// memorySeriesIterator implements SeriesIterator. -type memorySeriesIterator struct { - lock, unlock func() - chunkIt chunkIterator - chunks chunks -} - func (s *memorySeries) newIterator(lockFunc, unlockFunc func()) SeriesIterator { chunks := make(chunks, 0, len(s.chunkDescs)) for i, cd := range s.chunkDescs { @@ -504,6 +497,13 @@ func (s *memorySeries) lastTime() clientmodel.Timestamp { return s.head().lastTime() } +// memorySeriesIterator implements SeriesIterator. +type memorySeriesIterator struct { + lock, unlock func() + chunkIt chunkIterator + chunks chunks +} + // GetValueAtTime implements SeriesIterator. func (it *memorySeriesIterator) GetValueAtTime(t clientmodel.Timestamp) metric.Values { it.lock() @@ -628,3 +628,21 @@ func (it *memorySeriesIterator) GetRangeValues(in metric.Interval) metric.Values } return values } + +// nopSeriesIterator implements Series Iterator. It never returns any values. +type nopSeriesIterator struct{} + +// GetValueAtTime implements SeriesIterator. +func (_ nopSeriesIterator) GetValueAtTime(t clientmodel.Timestamp) metric.Values { + return metric.Values{} +} + +// GetBoundaryValues implements SeriesIterator. +func (_ nopSeriesIterator) GetBoundaryValues(in metric.Interval) metric.Values { + return metric.Values{} +} + +// GetRangeValues implements SeriesIterator. +func (_ nopSeriesIterator) GetRangeValues(in metric.Interval) metric.Values { + return metric.Values{} +} diff --git a/storage/local/storage.go b/storage/local/storage.go index a7ce57395..050fd0073 100644 --- a/storage/local/storage.go +++ b/storage/local/storage.go @@ -185,8 +185,12 @@ func (s *memorySeriesStorage) NewIterator(fp clientmodel.Fingerprint) SeriesIter series, ok := s.fingerprintToSeries.get(fp) if !ok { - // TODO: Could this legitimately happen? Series just got purged? - panic("requested iterator for non-existent series") + // Oops, no series for fp found. That happens if, after + // preloading is done, the whole series is identified as old + // enough for purging and hence purged for good. As there is no + // data left to iterate over, return an iterator that will never + // return any values. + return nopSeriesIterator{} } return series.newIterator( func() { s.fpLocker.Lock(fp) },