app/vmselect/promql: adjust calculations for rate and increase for the first value

These calculations should trigger alerts on `/api/v1/query` for counters starting from values greater than 0.
This commit is contained in:
Aliaksandr Valialkin 2019-12-24 19:39:22 +02:00
parent 9a2554691c
commit e24ee43109
2 changed files with 22 additions and 32 deletions

View File

@ -116,13 +116,11 @@ type rollupFuncArg struct {
currTimestamp int64 currTimestamp int64
idx int idx int
step int64 step int64
window int64
// Real previous value even if it is located too far from the current window. // Real previous value even if it is located too far from the current window.
// It matches prevValue if prevValue is not nan. // It matches prevValue if prevValue is not nan.
realPrevValue float64 realPrevValue float64
// Global scrape interval across all the data points in [Start...End] time range.
scrapeInterval int64
} }
func (rfa *rollupFuncArg) reset() { func (rfa *rollupFuncArg) reset() {
@ -133,8 +131,8 @@ func (rfa *rollupFuncArg) reset() {
rfa.currTimestamp = 0 rfa.currTimestamp = 0
rfa.idx = 0 rfa.idx = 0
rfa.step = 0 rfa.step = 0
rfa.window = 0
rfa.realPrevValue = nan rfa.realPrevValue = nan
rfa.scrapeInterval = 0
} }
// rollupFunc must return rollup value for the given rfa. // rollupFunc must return rollup value for the given rfa.
@ -214,8 +212,8 @@ func (rc *rollupConfig) Do(dstValues []float64, values []float64, timestamps []i
rfa := getRollupFuncArg() rfa := getRollupFuncArg()
rfa.idx = 0 rfa.idx = 0
rfa.step = rc.Step rfa.step = rc.Step
rfa.window = window
rfa.realPrevValue = nan rfa.realPrevValue = nan
rfa.scrapeInterval = scrapeInterval
i := 0 i := 0
j := 0 j := 0
@ -729,16 +727,13 @@ func rollupDeltaInternal(rfa *rollupFuncArg, canUseRealPrevValue bool) float64 {
if len(values) == 0 { if len(values) == 0 {
return nan return nan
} }
if len(values) == 1 { // Assume that the previous non-existing value was 0.
if canUseRealPrevValue && !math.IsNaN(rfa.realPrevValue) { if canUseRealPrevValue && !math.IsNaN(rfa.realPrevValue) {
// Fix against removeCounterResets. // Fix against removeCounterResets.
return values[0] - rfa.realPrevValue prevValue = rfa.realPrevValue
} } else {
// Assume that the previous non-existing value was 0. prevValue = 0
return values[0]
} }
prevValue = values[0]
values = values[1:]
} }
if len(values) == 0 { if len(values) == 0 {
// Assume that the value didn't change on the given interval. // Assume that the value didn't change on the given interval.
@ -797,19 +792,14 @@ func rollupDerivFastInternal(rfa *rollupFuncArg, canUseRealPrevValue bool) float
if len(values) == 0 { if len(values) == 0 {
return nan return nan
} }
if len(values) == 1 { // Assume that the value changed from 0 to the current value during rfa.window
// Assume that the value changed from 0 to the current value during rfa.scrapeInterval. if canUseRealPrevValue && !math.IsNaN(rfa.realPrevValue) {
delta := values[0] // Fix against removeCounterResets.
if canUseRealPrevValue && !math.IsNaN(rfa.realPrevValue) { prevValue = rfa.realPrevValue
// Fix against removeCounterResets. } else {
delta -= rfa.realPrevValue prevValue = 0
}
return float64(delta) / float64(rfa.scrapeInterval)
} }
prevValue = values[0] prevTimestamp = timestamps[0] - rfa.window
prevTimestamp = timestamps[0]
values = values[1:]
timestamps = timestamps[1:]
} }
if len(values) == 0 { if len(values) == 0 {
// Assume that the value didn't change on the given interval. // Assume that the value didn't change on the given interval.

View File

@ -272,13 +272,13 @@ func TestRollupNewRollupFuncSuccess(t *testing.T) {
f("default_rollup", 34) f("default_rollup", 34)
f("changes", 11) f("changes", 11)
f("delta", -89) f("delta", 34)
f("deriv", -266.85860231406065) f("deriv", -266.85860231406065)
f("deriv_fast", -712) f("deriv_fast", 272)
f("idelta", 0) f("idelta", 0)
f("increase", 275) f("increase", 398)
f("irate", 0) f("irate", 0)
f("rate", 2200) f("rate", 3184)
f("resets", 5) f("resets", 5)
f("avg_over_time", 47.083333333333336) f("avg_over_time", 47.083333333333336)
f("min_over_time", 12) f("min_over_time", 12)
@ -614,7 +614,7 @@ func TestRollupFuncsNoWindow(t *testing.T) {
} }
rc.Timestamps = getTimestamps(rc.Start, rc.End, rc.Step) rc.Timestamps = getTimestamps(rc.Start, rc.End, rc.Step)
values := rc.Do(nil, testValues, testTimestamps) values := rc.Do(nil, testValues, testTimestamps)
valuesExpected := []float64{nan, -102, -9, 22, 0} valuesExpected := []float64{nan, nan, -9, 22, 0}
timestampsExpected := []int64{0, 40, 80, 120, 160} timestampsExpected := []int64{0, 40, 80, 120, 160}
testRowsEqual(t, values, rc.Timestamps, valuesExpected, timestampsExpected) testRowsEqual(t, values, rc.Timestamps, valuesExpected, timestampsExpected)
}) })
@ -782,7 +782,7 @@ func TestRollupFuncsNoWindow(t *testing.T) {
} }
rc.Timestamps = getTimestamps(rc.Start, rc.End, rc.Step) rc.Timestamps = getTimestamps(rc.Start, rc.End, rc.Step)
values := rc.Do(nil, testValues, testTimestamps) values := rc.Do(nil, testValues, testTimestamps)
valuesExpected := []float64{nan, nan, 10.25, 0, -8900, 0} valuesExpected := []float64{nan, nan, 30750, 0, -8900, 0}
timestampsExpected := []int64{0, 4, 8, 12, 16, 20} timestampsExpected := []int64{0, 4, 8, 12, 16, 20}
testRowsEqual(t, values, rc.Timestamps, valuesExpected, timestampsExpected) testRowsEqual(t, values, rc.Timestamps, valuesExpected, timestampsExpected)
}) })