mirror of https://github.com/grafana/grafana
Prometheus: Remove all intervalv2 imports and use gtime functions wherever it's possible (#82064)
* Remove all intervalv2 imports and use gtime functions where ever it's possible * Add a comment line * use roundInterval from grafana-plugin-sdk-gopull/81842/head
parent
367790663c
commit
b25ffe2b15
@ -0,0 +1,74 @@ |
||||
// Package intervalv2 partially copied from https://github.com/grafana/grafana/blob/main/pkg/tsdb/intervalv2/intervalv2.go
|
||||
package intervalv2 |
||||
|
||||
import ( |
||||
"time" |
||||
|
||||
"github.com/grafana/grafana-plugin-sdk-go/backend" |
||||
"github.com/grafana/grafana-plugin-sdk-go/backend/gtime" |
||||
) |
||||
|
||||
var ( |
||||
DefaultRes int64 = 1500 |
||||
defaultMinInterval = time.Millisecond * 1 |
||||
) |
||||
|
||||
type Interval struct { |
||||
Text string |
||||
Value time.Duration |
||||
} |
||||
|
||||
type intervalCalculator struct { |
||||
minInterval time.Duration |
||||
} |
||||
|
||||
type Calculator interface { |
||||
Calculate(timerange backend.TimeRange, minInterval time.Duration, maxDataPoints int64) Interval |
||||
CalculateSafeInterval(timerange backend.TimeRange, resolution int64) Interval |
||||
} |
||||
|
||||
type CalculatorOptions struct { |
||||
MinInterval time.Duration |
||||
} |
||||
|
||||
func NewCalculator(opts ...CalculatorOptions) *intervalCalculator { |
||||
calc := &intervalCalculator{} |
||||
|
||||
for _, o := range opts { |
||||
if o.MinInterval == 0 { |
||||
calc.minInterval = defaultMinInterval |
||||
} else { |
||||
calc.minInterval = o.MinInterval |
||||
} |
||||
} |
||||
|
||||
return calc |
||||
} |
||||
|
||||
func (ic *intervalCalculator) Calculate(timerange backend.TimeRange, minInterval time.Duration, maxDataPoints int64) Interval { |
||||
to := timerange.To.UnixNano() |
||||
from := timerange.From.UnixNano() |
||||
resolution := maxDataPoints |
||||
if resolution == 0 { |
||||
resolution = DefaultRes |
||||
} |
||||
|
||||
calculatedInterval := time.Duration((to - from) / resolution) |
||||
|
||||
if calculatedInterval < minInterval { |
||||
return Interval{Text: gtime.FormatInterval(minInterval), Value: minInterval} |
||||
} |
||||
|
||||
rounded := gtime.RoundInterval(calculatedInterval) |
||||
|
||||
return Interval{Text: gtime.FormatInterval(rounded), Value: rounded} |
||||
} |
||||
|
||||
func (ic *intervalCalculator) CalculateSafeInterval(timerange backend.TimeRange, safeRes int64) Interval { |
||||
to := timerange.To.UnixNano() |
||||
from := timerange.From.UnixNano() |
||||
safeInterval := time.Duration((to - from) / safeRes) |
||||
|
||||
rounded := gtime.RoundInterval(safeInterval) |
||||
return Interval{Text: gtime.FormatInterval(rounded), Value: rounded} |
||||
} |
||||
@ -0,0 +1,63 @@ |
||||
package intervalv2 |
||||
|
||||
import ( |
||||
"testing" |
||||
"time" |
||||
|
||||
"github.com/grafana/grafana-plugin-sdk-go/backend" |
||||
"github.com/stretchr/testify/assert" |
||||
) |
||||
|
||||
func TestIntervalCalculator_Calculate(t *testing.T) { |
||||
calculator := NewCalculator(CalculatorOptions{}) |
||||
|
||||
timeNow := time.Now() |
||||
|
||||
testCases := []struct { |
||||
name string |
||||
timeRange backend.TimeRange |
||||
resolution int64 |
||||
expected string |
||||
}{ |
||||
{"from 5m to now and default resolution", backend.TimeRange{From: timeNow, To: timeNow.Add(5 * time.Minute)}, 0, "200ms"}, |
||||
{"from 5m to now and 500 resolution", backend.TimeRange{From: timeNow, To: timeNow.Add(5 * time.Minute)}, 500, "500ms"}, |
||||
{"from 15m to now and default resolution", backend.TimeRange{From: timeNow, To: timeNow.Add(15 * time.Minute)}, 0, "500ms"}, |
||||
{"from 15m to now and 100 resolution", backend.TimeRange{From: timeNow, To: timeNow.Add(15 * time.Minute)}, 100, "10s"}, |
||||
{"from 30m to now and default resolution", backend.TimeRange{From: timeNow, To: timeNow.Add(30 * time.Minute)}, 0, "1s"}, |
||||
{"from 30m to now and 3000 resolution", backend.TimeRange{From: timeNow, To: timeNow.Add(30 * time.Minute)}, 3000, "500ms"}, |
||||
{"from 1h to now and default resolution", backend.TimeRange{From: timeNow, To: timeNow.Add(time.Hour)}, 0, "2s"}, |
||||
{"from 1h to now and 1000 resolution", backend.TimeRange{From: timeNow, To: timeNow.Add(time.Hour)}, 1000, "5s"}, |
||||
} |
||||
|
||||
for _, tc := range testCases { |
||||
t.Run(tc.name, func(t *testing.T) { |
||||
interval := calculator.Calculate(tc.timeRange, time.Millisecond*1, tc.resolution) |
||||
assert.Equal(t, tc.expected, interval.Text) |
||||
}) |
||||
} |
||||
} |
||||
|
||||
func TestIntervalCalculator_CalculateSafeInterval(t *testing.T) { |
||||
calculator := NewCalculator(CalculatorOptions{}) |
||||
|
||||
timeNow := time.Now() |
||||
|
||||
testCases := []struct { |
||||
name string |
||||
timeRange backend.TimeRange |
||||
safeResolution int64 |
||||
expected string |
||||
}{ |
||||
{"from 5m to now", backend.TimeRange{From: timeNow, To: timeNow.Add(5 * time.Minute)}, 11000, "20ms"}, |
||||
{"from 15m to now", backend.TimeRange{From: timeNow, To: timeNow.Add(15 * time.Minute)}, 11000, "100ms"}, |
||||
{"from 30m to now", backend.TimeRange{From: timeNow, To: timeNow.Add(30 * time.Minute)}, 11000, "200ms"}, |
||||
{"from 24h to now", backend.TimeRange{From: timeNow, To: timeNow.Add(1440 * time.Minute)}, 11000, "10s"}, |
||||
} |
||||
|
||||
for _, tc := range testCases { |
||||
t.Run(tc.name, func(t *testing.T) { |
||||
interval := calculator.CalculateSafeInterval(tc.timeRange, tc.safeResolution) |
||||
assert.Equal(t, tc.expected, interval.Text) |
||||
}) |
||||
} |
||||
} |
||||
Loading…
Reference in new issue