promql: rename vector
This commit is contained in:
parent
15a931dbdb
commit
a62df87022
136
promql/engine.go
136
promql/engine.go
|
@ -51,7 +51,7 @@ type Value interface {
|
|||
}
|
||||
|
||||
func (matrix) Type() ValueType { return ValueTypeMatrix }
|
||||
func (vector) Type() ValueType { return ValueTypeVector }
|
||||
func (Vector) Type() ValueType { return ValueTypeVector }
|
||||
func (scalar) Type() ValueType { return ValueTypeScalar }
|
||||
func (stringVal) Type() ValueType { return ValueTypeString }
|
||||
|
||||
|
@ -61,7 +61,7 @@ type ValueType string
|
|||
// The valid value types.
|
||||
const (
|
||||
ValueTypeNone = "none"
|
||||
ValueTypeVector = "vector"
|
||||
ValueTypeVector = "Vector"
|
||||
ValueTypeScalar = "scalar"
|
||||
ValueTypeMatrix = "matrix"
|
||||
ValueTypeString = "string"
|
||||
|
@ -115,11 +115,11 @@ func (s sample) String() string {
|
|||
return ""
|
||||
}
|
||||
|
||||
// vector is basically only an alias for model.Samples, but the
|
||||
// Vector is basically only an alias for model.Samples, but the
|
||||
// contract is that in a Vector, all Samples have the same timestamp.
|
||||
type vector []sample
|
||||
type Vector []sample
|
||||
|
||||
func (vec vector) String() string {
|
||||
func (vec Vector) String() string {
|
||||
entries := make([]string, len(vec))
|
||||
for i, s := range vec {
|
||||
entries[i] = s.String()
|
||||
|
@ -149,15 +149,15 @@ type Result struct {
|
|||
Value Value
|
||||
}
|
||||
|
||||
// Vector returns a vector if the result value is one. An error is returned if
|
||||
// the result was an error or the result value is not a vector.
|
||||
func (r *Result) Vector() (vector, error) {
|
||||
// Vector returns a Vector if the result value is one. An error is returned if
|
||||
// the result was an error or the result value is not a Vector.
|
||||
func (r *Result) Vector() (Vector, error) {
|
||||
if r.Err != nil {
|
||||
return nil, r.Err
|
||||
}
|
||||
v, ok := r.Value.(vector)
|
||||
v, ok := r.Value.(Vector)
|
||||
if !ok {
|
||||
return nil, fmt.Errorf("query result is not a vector")
|
||||
return nil, fmt.Errorf("query result is not a Vector")
|
||||
}
|
||||
return v, nil
|
||||
}
|
||||
|
@ -170,7 +170,7 @@ func (r *Result) Matrix() (matrix, error) {
|
|||
}
|
||||
v, ok := r.Value.(matrix)
|
||||
if !ok {
|
||||
return nil, fmt.Errorf("query result is not a range vector")
|
||||
return nil, fmt.Errorf("query result is not a range Vector")
|
||||
}
|
||||
return v, nil
|
||||
}
|
||||
|
@ -336,7 +336,7 @@ func (ng *Engine) NewRangeQuery(qs string, start, end time.Time, interval time.D
|
|||
return nil, err
|
||||
}
|
||||
if expr.Type() != ValueTypeVector && expr.Type() != ValueTypeScalar {
|
||||
return nil, fmt.Errorf("invalid expression type %q for range query, must be scalar or instant vector", documentedType(expr.Type()))
|
||||
return nil, fmt.Errorf("invalid expression type %q for range query, must be scalar or instant Vector", documentedType(expr.Type()))
|
||||
}
|
||||
qry := ng.newQuery(expr, start, end, interval)
|
||||
qry.q = qs
|
||||
|
@ -482,7 +482,7 @@ func (ng *Engine) execEvalStmt(ctx context.Context, query *query, s *EvalStmt) (
|
|||
v: v.v,
|
||||
t: v.t,
|
||||
})
|
||||
case vector:
|
||||
case Vector:
|
||||
for _, sample := range v {
|
||||
h := sample.Metric.Hash()
|
||||
ss, ok := sampleStreams[h]
|
||||
|
@ -643,12 +643,12 @@ func (ev *evaluator) evalScalar(e Expr) scalar {
|
|||
return sv
|
||||
}
|
||||
|
||||
// evalVector attempts to evaluate e to a vector value and errors otherwise.
|
||||
func (ev *evaluator) evalVector(e Expr) vector {
|
||||
// evalVector attempts to evaluate e to a Vector value and errors otherwise.
|
||||
func (ev *evaluator) evalVector(e Expr) Vector {
|
||||
val := ev.eval(e)
|
||||
vec, ok := val.(vector)
|
||||
vec, ok := val.(Vector)
|
||||
if !ok {
|
||||
ev.errorf("expected instant vector but got %s", documentedType(val.Type()))
|
||||
ev.errorf("expected instant Vector but got %s", documentedType(val.Type()))
|
||||
}
|
||||
return vec
|
||||
}
|
||||
|
@ -669,13 +669,13 @@ func (ev *evaluator) evalFloat(e Expr) float64 {
|
|||
}
|
||||
|
||||
// evalMatrix attempts to evaluate e into a matrix and errors otherwise.
|
||||
// The error message uses the term "range vector" to match the user facing
|
||||
// The error message uses the term "range Vector" to match the user facing
|
||||
// documentation.
|
||||
func (ev *evaluator) evalMatrix(e Expr) matrix {
|
||||
val := ev.eval(e)
|
||||
mat, ok := val.(matrix)
|
||||
if !ok {
|
||||
ev.errorf("expected range vector but got %s", documentedType(val.Type()))
|
||||
ev.errorf("expected range Vector but got %s", documentedType(val.Type()))
|
||||
}
|
||||
return mat
|
||||
}
|
||||
|
@ -714,8 +714,8 @@ func (ev *evaluator) eval(expr Expr) Value {
|
|||
|
||||
switch e := expr.(type) {
|
||||
case *AggregateExpr:
|
||||
vector := ev.evalVector(e.Expr)
|
||||
return ev.aggregation(e.Op, e.Grouping, e.Without, e.KeepCommonLabels, e.Param, vector)
|
||||
Vector := ev.evalVector(e.Expr)
|
||||
return ev.aggregation(e.Op, e.Grouping, e.Without, e.KeepCommonLabels, e.Param, Vector)
|
||||
|
||||
case *BinaryExpr:
|
||||
lhs := ev.evalOneOf(e.LHS, ValueTypeScalar, ValueTypeVector)
|
||||
|
@ -731,19 +731,19 @@ func (ev *evaluator) eval(expr Expr) Value {
|
|||
case lt == ValueTypeVector && rt == ValueTypeVector:
|
||||
switch e.Op {
|
||||
case itemLAND:
|
||||
return ev.vectorAnd(lhs.(vector), rhs.(vector), e.VectorMatching)
|
||||
return ev.VectorAnd(lhs.(Vector), rhs.(Vector), e.VectorMatching)
|
||||
case itemLOR:
|
||||
return ev.vectorOr(lhs.(vector), rhs.(vector), e.VectorMatching)
|
||||
return ev.VectorOr(lhs.(Vector), rhs.(Vector), e.VectorMatching)
|
||||
case itemLUnless:
|
||||
return ev.vectorUnless(lhs.(vector), rhs.(vector), e.VectorMatching)
|
||||
return ev.VectorUnless(lhs.(Vector), rhs.(Vector), e.VectorMatching)
|
||||
default:
|
||||
return ev.vectorBinop(e.Op, lhs.(vector), rhs.(vector), e.VectorMatching, e.ReturnBool)
|
||||
return ev.VectorBinop(e.Op, lhs.(Vector), rhs.(Vector), e.VectorMatching, e.ReturnBool)
|
||||
}
|
||||
case lt == ValueTypeVector && rt == ValueTypeScalar:
|
||||
return ev.vectorScalarBinop(e.Op, lhs.(vector), rhs.(scalar), false, e.ReturnBool)
|
||||
return ev.VectorScalarBinop(e.Op, lhs.(Vector), rhs.(scalar), false, e.ReturnBool)
|
||||
|
||||
case lt == ValueTypeScalar && rt == ValueTypeVector:
|
||||
return ev.vectorScalarBinop(e.Op, rhs.(vector), lhs.(scalar), true, e.ReturnBool)
|
||||
return ev.VectorScalarBinop(e.Op, rhs.(Vector), lhs.(scalar), true, e.ReturnBool)
|
||||
}
|
||||
|
||||
case *Call:
|
||||
|
@ -768,7 +768,7 @@ func (ev *evaluator) eval(expr Expr) Value {
|
|||
switch v := se.(type) {
|
||||
case scalar:
|
||||
v.v = -v.v
|
||||
case vector:
|
||||
case Vector:
|
||||
for i, sv := range v {
|
||||
v[i].Value = -sv.Value
|
||||
}
|
||||
|
@ -777,16 +777,16 @@ func (ev *evaluator) eval(expr Expr) Value {
|
|||
return se
|
||||
|
||||
case *VectorSelector:
|
||||
return ev.vectorSelector(e)
|
||||
return ev.VectorSelector(e)
|
||||
}
|
||||
panic(fmt.Errorf("unhandled expression of type: %T", expr))
|
||||
}
|
||||
|
||||
// vectorSelector evaluates a *VectorSelector expression.
|
||||
func (ev *evaluator) vectorSelector(node *VectorSelector) vector {
|
||||
// VectorSelector evaluates a *VectorSelector expression.
|
||||
func (ev *evaluator) VectorSelector(node *VectorSelector) Vector {
|
||||
var (
|
||||
ok bool
|
||||
vec = make(vector, 0, len(node.series))
|
||||
vec = make(Vector, 0, len(node.series))
|
||||
refTime = ev.Timestamp - durationMilliseconds(node.Offset)
|
||||
)
|
||||
|
||||
|
@ -856,14 +856,14 @@ func (ev *evaluator) matrixSelector(node *MatrixSelector) matrix {
|
|||
return matrix
|
||||
}
|
||||
|
||||
func (ev *evaluator) vectorAnd(lhs, rhs vector, matching *VectorMatching) vector {
|
||||
func (ev *evaluator) VectorAnd(lhs, rhs Vector, matching *VectorMatching) Vector {
|
||||
if matching.Card != CardManyToMany {
|
||||
panic("set operations must only use many-to-many matching")
|
||||
}
|
||||
sigf := signatureFunc(matching.On, matching.MatchingLabels...)
|
||||
|
||||
var result vector
|
||||
// The set of signatures for the right-hand side vector.
|
||||
var result Vector
|
||||
// The set of signatures for the right-hand side Vector.
|
||||
rightSigs := map[uint64]struct{}{}
|
||||
// Add all rhs samples to a map so we can easily find matches later.
|
||||
for _, rs := range rhs {
|
||||
|
@ -871,7 +871,7 @@ func (ev *evaluator) vectorAnd(lhs, rhs vector, matching *VectorMatching) vector
|
|||
}
|
||||
|
||||
for _, ls := range lhs {
|
||||
// If there's a matching entry in the right-hand side vector, add the sample.
|
||||
// If there's a matching entry in the right-hand side Vector, add the sample.
|
||||
if _, ok := rightSigs[sigf(ls.Metric)]; ok {
|
||||
result = append(result, ls)
|
||||
}
|
||||
|
@ -879,15 +879,15 @@ func (ev *evaluator) vectorAnd(lhs, rhs vector, matching *VectorMatching) vector
|
|||
return result
|
||||
}
|
||||
|
||||
func (ev *evaluator) vectorOr(lhs, rhs vector, matching *VectorMatching) vector {
|
||||
func (ev *evaluator) VectorOr(lhs, rhs Vector, matching *VectorMatching) Vector {
|
||||
if matching.Card != CardManyToMany {
|
||||
panic("set operations must only use many-to-many matching")
|
||||
}
|
||||
sigf := signatureFunc(matching.On, matching.MatchingLabels...)
|
||||
|
||||
var result vector
|
||||
var result Vector
|
||||
leftSigs := map[uint64]struct{}{}
|
||||
// Add everything from the left-hand-side vector.
|
||||
// Add everything from the left-hand-side Vector.
|
||||
for _, ls := range lhs {
|
||||
leftSigs[sigf(ls.Metric)] = struct{}{}
|
||||
result = append(result, ls)
|
||||
|
@ -901,7 +901,7 @@ func (ev *evaluator) vectorOr(lhs, rhs vector, matching *VectorMatching) vector
|
|||
return result
|
||||
}
|
||||
|
||||
func (ev *evaluator) vectorUnless(lhs, rhs vector, matching *VectorMatching) vector {
|
||||
func (ev *evaluator) VectorUnless(lhs, rhs Vector, matching *VectorMatching) Vector {
|
||||
if matching.Card != CardManyToMany {
|
||||
panic("set operations must only use many-to-many matching")
|
||||
}
|
||||
|
@ -912,7 +912,7 @@ func (ev *evaluator) vectorUnless(lhs, rhs vector, matching *VectorMatching) vec
|
|||
rightSigs[sigf(rs.Metric)] = struct{}{}
|
||||
}
|
||||
|
||||
var result vector
|
||||
var result Vector
|
||||
for _, ls := range lhs {
|
||||
if _, ok := rightSigs[sigf(ls.Metric)]; !ok {
|
||||
result = append(result, ls)
|
||||
|
@ -921,13 +921,13 @@ func (ev *evaluator) vectorUnless(lhs, rhs vector, matching *VectorMatching) vec
|
|||
return result
|
||||
}
|
||||
|
||||
// vectorBinop evaluates a binary operation between two vectors, excluding set operators.
|
||||
func (ev *evaluator) vectorBinop(op itemType, lhs, rhs vector, matching *VectorMatching, returnBool bool) vector {
|
||||
// VectorBinop evaluates a binary operation between two Vectors, excluding set operators.
|
||||
func (ev *evaluator) VectorBinop(op itemType, lhs, rhs Vector, matching *VectorMatching, returnBool bool) Vector {
|
||||
if matching.Card == CardManyToMany {
|
||||
panic("many-to-many only allowed for set operators")
|
||||
}
|
||||
var (
|
||||
result = vector{}
|
||||
result = Vector{}
|
||||
sigf = signatureFunc(matching.On, matching.MatchingLabels...)
|
||||
)
|
||||
|
||||
|
@ -962,7 +962,7 @@ func (ev *evaluator) vectorBinop(op itemType, lhs, rhs vector, matching *VectorM
|
|||
for _, ls := range lhs {
|
||||
sig := sigf(ls.Metric)
|
||||
|
||||
rs, found := rightSigs[sig] // Look for a match in the rhs vector.
|
||||
rs, found := rightSigs[sig] // Look for a match in the rhs Vector.
|
||||
if !found {
|
||||
continue
|
||||
}
|
||||
|
@ -972,7 +972,7 @@ func (ev *evaluator) vectorBinop(op itemType, lhs, rhs vector, matching *VectorM
|
|||
if matching.Card == CardOneToMany {
|
||||
vl, vr = vr, vl
|
||||
}
|
||||
value, keep := vectorElemBinop(op, vl, vr)
|
||||
value, keep := VectorElemBinop(op, vl, vr)
|
||||
if returnBool {
|
||||
if keep {
|
||||
value = 1.0
|
||||
|
@ -992,7 +992,7 @@ func (ev *evaluator) vectorBinop(op itemType, lhs, rhs vector, matching *VectorM
|
|||
matchedSigs[sig] = nil // Set existence to true.
|
||||
} else {
|
||||
// In many-to-one matching the grouping labels have to ensure a unique metric
|
||||
// for the result vector. Check whether those labels have already been added for
|
||||
// for the result Vector. Check whether those labels have already been added for
|
||||
// the same matching labels.
|
||||
insertSig := metric.Hash()
|
||||
|
||||
|
@ -1059,7 +1059,7 @@ func signatureFunc(on bool, names ...string) func(labels.Labels) uint64 {
|
|||
return func(lset labels.Labels) uint64 { return hashWithoutLabels(lset, names...) }
|
||||
}
|
||||
|
||||
// resultMetric returns the metric for the given sample(s) based on the vector
|
||||
// resultMetric returns the metric for the given sample(s) based on the Vector
|
||||
// binary operation and the matching options.
|
||||
func resultMetric(lhs, rhs labels.Labels, op itemType, matching *VectorMatching) labels.Labels {
|
||||
// del and add hold modifications to the LHS input metric.
|
||||
|
@ -1116,18 +1116,18 @@ Outer:
|
|||
return res
|
||||
}
|
||||
|
||||
// vectorScalarBinop evaluates a binary operation between a vector and a scalar.
|
||||
func (ev *evaluator) vectorScalarBinop(op itemType, lhs vector, rhs scalar, swap, returnBool bool) vector {
|
||||
vec := make(vector, 0, len(lhs))
|
||||
// VectorScalarBinop evaluates a binary operation between a Vector and a scalar.
|
||||
func (ev *evaluator) VectorScalarBinop(op itemType, lhs Vector, rhs scalar, swap, returnBool bool) Vector {
|
||||
vec := make(Vector, 0, len(lhs))
|
||||
|
||||
for _, lhsSample := range lhs {
|
||||
lv, rv := lhsSample.Value, rhs.v
|
||||
// lhs always contains the vector. If the original position was different
|
||||
// lhs always contains the Vector. If the original position was different
|
||||
// swap for calculating the value.
|
||||
if swap {
|
||||
lv, rv = rv, lv
|
||||
}
|
||||
value, keep := vectorElemBinop(op, lv, rv)
|
||||
value, keep := VectorElemBinop(op, lv, rv)
|
||||
if returnBool {
|
||||
if keep {
|
||||
value = 1.0
|
||||
|
@ -1192,8 +1192,8 @@ func scalarBinop(op itemType, lhs, rhs float64) float64 {
|
|||
panic(fmt.Errorf("operator %q not allowed for scalar operations", op))
|
||||
}
|
||||
|
||||
// vectorElemBinop evaluates a binary operation between two vector elements.
|
||||
func vectorElemBinop(op itemType, lhs, rhs float64) (float64, bool) {
|
||||
// VectorElemBinop evaluates a binary operation between two Vector elements.
|
||||
func VectorElemBinop(op itemType, lhs, rhs float64) (float64, bool) {
|
||||
switch op {
|
||||
case itemADD:
|
||||
return lhs + rhs, true
|
||||
|
@ -1220,7 +1220,7 @@ func vectorElemBinop(op itemType, lhs, rhs float64) (float64, bool) {
|
|||
case itemLTE:
|
||||
return lhs, lhs <= rhs
|
||||
}
|
||||
panic(fmt.Errorf("operator %q not allowed for operations between vectors", op))
|
||||
panic(fmt.Errorf("operator %q not allowed for operations between Vectors", op))
|
||||
}
|
||||
|
||||
// intersection returns the metric of common label/value pairs of two input metrics.
|
||||
|
@ -1243,19 +1243,19 @@ type groupedAggregation struct {
|
|||
value float64
|
||||
valuesSquaredSum float64
|
||||
groupCount int
|
||||
heap vectorByValueHeap
|
||||
reverseHeap vectorByReverseValueHeap
|
||||
heap VectorByValueHeap
|
||||
reverseHeap VectorByReverseValueHeap
|
||||
}
|
||||
|
||||
// aggregation evaluates an aggregation operation on a vector.
|
||||
func (ev *evaluator) aggregation(op itemType, grouping []string, without bool, keepCommon bool, param Expr, vec vector) vector {
|
||||
// aggregation evaluates an aggregation operation on a Vector.
|
||||
func (ev *evaluator) aggregation(op itemType, grouping []string, without bool, keepCommon bool, param Expr, vec Vector) Vector {
|
||||
|
||||
result := map[uint64]*groupedAggregation{}
|
||||
var k int64
|
||||
if op == itemTopK || op == itemBottomK {
|
||||
k = ev.evalInt(param)
|
||||
if k < 1 {
|
||||
return vector{}
|
||||
return Vector{}
|
||||
}
|
||||
}
|
||||
var q float64
|
||||
|
@ -1313,10 +1313,10 @@ func (ev *evaluator) aggregation(op itemType, grouping []string, without bool, k
|
|||
groupCount: 1,
|
||||
}
|
||||
if op == itemTopK || op == itemQuantile {
|
||||
result[groupingKey].heap = make(vectorByValueHeap, 0, k)
|
||||
result[groupingKey].heap = make(VectorByValueHeap, 0, k)
|
||||
heap.Push(&result[groupingKey].heap, &sample{Value: s.Value, Metric: s.Metric})
|
||||
} else if op == itemBottomK {
|
||||
result[groupingKey].reverseHeap = make(vectorByReverseValueHeap, 0, k)
|
||||
result[groupingKey].reverseHeap = make(VectorByReverseValueHeap, 0, k)
|
||||
heap.Push(&result[groupingKey].reverseHeap, &sample{Value: s.Value, Metric: s.Metric})
|
||||
}
|
||||
continue
|
||||
|
@ -1376,8 +1376,8 @@ func (ev *evaluator) aggregation(op itemType, grouping []string, without bool, k
|
|||
}
|
||||
}
|
||||
|
||||
// Construct the result vector from the aggregated groups.
|
||||
resultVector := make(vector, 0, len(result))
|
||||
// Construct the result Vector from the aggregated groups.
|
||||
resultVector := make(Vector, 0, len(result))
|
||||
|
||||
for _, aggr := range result {
|
||||
switch op {
|
||||
|
@ -1494,10 +1494,10 @@ func (g *queryGate) Done() {
|
|||
// user facing terminology as defined in the documentation.
|
||||
func documentedType(t ValueType) string {
|
||||
switch t {
|
||||
case "vector":
|
||||
return "instant vector"
|
||||
case "Vector":
|
||||
return "instant Vector"
|
||||
case "matrix":
|
||||
return "range vector"
|
||||
return "range Vector"
|
||||
default:
|
||||
return string(t)
|
||||
}
|
||||
|
|
|
@ -52,12 +52,12 @@ func extrapolatedRate(ev *evaluator, arg Expr, isCounter bool, isRate bool) Valu
|
|||
rangeStart := ev.Timestamp - durationMilliseconds(ms.Range+ms.Offset)
|
||||
rangeEnd := ev.Timestamp - durationMilliseconds(ms.Offset)
|
||||
|
||||
resultVector := vector{}
|
||||
resultVector := Vector{}
|
||||
|
||||
matrixValue := ev.evalMatrix(ms)
|
||||
for _, samples := range matrixValue {
|
||||
// No sense in trying to compute a rate without at least two points. Drop
|
||||
// this vector element.
|
||||
// this Vector element.
|
||||
if len(samples.Values) < 2 {
|
||||
continue
|
||||
}
|
||||
|
@ -151,10 +151,10 @@ func funcIdelta(ev *evaluator, args Expressions) Value {
|
|||
}
|
||||
|
||||
func instantValue(ev *evaluator, arg Expr, isRate bool) Value {
|
||||
resultVector := vector{}
|
||||
resultVector := Vector{}
|
||||
for _, samples := range ev.evalMatrix(arg) {
|
||||
// No sense in trying to compute a rate without at least two points. Drop
|
||||
// this vector element.
|
||||
// this Vector element.
|
||||
if len(samples.Values) < 2 {
|
||||
continue
|
||||
}
|
||||
|
@ -230,8 +230,8 @@ func funcHoltWinters(ev *evaluator, args Expressions) Value {
|
|||
ev.errorf("invalid trend factor. Expected: 0 < tf < 1 got: %f", sf)
|
||||
}
|
||||
|
||||
// Make an output vector large enough to hold the entire result.
|
||||
resultVector := make(vector, 0, len(mat))
|
||||
// Make an output Vector large enough to hold the entire result.
|
||||
resultVector := make(Vector, 0, len(mat))
|
||||
|
||||
// Create scratch values.
|
||||
var s, b, d []float64
|
||||
|
@ -276,7 +276,7 @@ func funcHoltWinters(ev *evaluator, args Expressions) Value {
|
|||
|
||||
resultVector = append(resultVector, sample{
|
||||
Metric: copyLabels(samples.Metric, false),
|
||||
Value: s[len(s)-1], // The last value in the vector is the smoothed result.
|
||||
Value: s[len(s)-1], // The last value in the Vector is the smoothed result.
|
||||
Timestamp: ev.Timestamp,
|
||||
})
|
||||
}
|
||||
|
@ -288,21 +288,21 @@ func funcHoltWinters(ev *evaluator, args Expressions) Value {
|
|||
func funcSort(ev *evaluator, args Expressions) Value {
|
||||
// NaN should sort to the bottom, so take descending sort with NaN first and
|
||||
// reverse it.
|
||||
byValueSorter := vectorByReverseValueHeap(ev.evalVector(args[0]))
|
||||
byValueSorter := VectorByReverseValueHeap(ev.evalVector(args[0]))
|
||||
sort.Sort(sort.Reverse(byValueSorter))
|
||||
return vector(byValueSorter)
|
||||
return Vector(byValueSorter)
|
||||
}
|
||||
|
||||
// === sortDesc(node ValueTypeVector) Vector ===
|
||||
func funcSortDesc(ev *evaluator, args Expressions) Value {
|
||||
// NaN should sort to the bottom, so take ascending sort with NaN first and
|
||||
// reverse it.
|
||||
byValueSorter := vectorByValueHeap(ev.evalVector(args[0]))
|
||||
byValueSorter := VectorByValueHeap(ev.evalVector(args[0]))
|
||||
sort.Sort(sort.Reverse(byValueSorter))
|
||||
return vector(byValueSorter)
|
||||
return Vector(byValueSorter)
|
||||
}
|
||||
|
||||
// === clamp_max(vector ValueTypeVector, max Scalar) Vector ===
|
||||
// === clamp_max(Vector ValueTypeVector, max Scalar) Vector ===
|
||||
func funcClampMax(ev *evaluator, args Expressions) Value {
|
||||
vec := ev.evalVector(args[0])
|
||||
max := ev.evalFloat(args[1])
|
||||
|
@ -313,7 +313,7 @@ func funcClampMax(ev *evaluator, args Expressions) Value {
|
|||
return vec
|
||||
}
|
||||
|
||||
// === clamp_min(vector ValueTypeVector, min Scalar) Vector ===
|
||||
// === clamp_min(Vector ValueTypeVector, min Scalar) Vector ===
|
||||
func funcClampMin(ev *evaluator, args Expressions) Value {
|
||||
vec := ev.evalVector(args[0])
|
||||
min := ev.evalFloat(args[1])
|
||||
|
@ -328,7 +328,7 @@ func funcClampMin(ev *evaluator, args Expressions) Value {
|
|||
func funcDropCommonLabels(ev *evaluator, args Expressions) Value {
|
||||
vec := ev.evalVector(args[0])
|
||||
if len(vec) < 1 {
|
||||
return vector{}
|
||||
return Vector{}
|
||||
}
|
||||
common := map[string]string{}
|
||||
|
||||
|
@ -365,7 +365,7 @@ func funcDropCommonLabels(ev *evaluator, args Expressions) Value {
|
|||
return vec
|
||||
}
|
||||
|
||||
// === round(vector ValueTypeVector, toNearest=1 Scalar) Vector ===
|
||||
// === round(Vector ValueTypeVector, toNearest=1 Scalar) Vector ===
|
||||
func funcRound(ev *evaluator, args Expressions) Value {
|
||||
// round returns a number rounded to toNearest.
|
||||
// Ties are solved by rounding up.
|
||||
|
@ -399,7 +399,7 @@ func funcScalar(ev *evaluator, args Expressions) Value {
|
|||
}
|
||||
}
|
||||
|
||||
// === count_scalar(vector ValueTypeVector) float64 ===
|
||||
// === count_scalar(Vector ValueTypeVector) float64 ===
|
||||
func funcCountScalar(ev *evaluator, args Expressions) Value {
|
||||
return scalar{
|
||||
v: float64(len(ev.evalVector(args[0]))),
|
||||
|
@ -409,7 +409,7 @@ func funcCountScalar(ev *evaluator, args Expressions) Value {
|
|||
|
||||
func aggrOverTime(ev *evaluator, args Expressions, aggrFn func([]samplePair) float64) Value {
|
||||
mat := ev.evalMatrix(args[0])
|
||||
resultVector := vector{}
|
||||
resultVector := Vector{}
|
||||
|
||||
for _, el := range mat {
|
||||
if len(el.Values) == 0 {
|
||||
|
@ -443,14 +443,14 @@ func funcCountOverTime(ev *evaluator, args Expressions) Value {
|
|||
})
|
||||
}
|
||||
|
||||
// === floor(vector ValueTypeVector) Vector ===
|
||||
// === floor(Vector ValueTypeVector) Vector ===
|
||||
func funcFloor(ev *evaluator, args Expressions) Value {
|
||||
vector := ev.evalVector(args[0])
|
||||
for _, el := range vector {
|
||||
Vector := ev.evalVector(args[0])
|
||||
for _, el := range Vector {
|
||||
el.Metric = copyLabels(el.Metric, false)
|
||||
el.Value = math.Floor(float64(el.Value))
|
||||
}
|
||||
return vector
|
||||
return Vector
|
||||
}
|
||||
|
||||
// === max_over_time(matrix ValueTypeMatrix) Vector ===
|
||||
|
@ -490,7 +490,7 @@ func funcSumOverTime(ev *evaluator, args Expressions) Value {
|
|||
func funcQuantileOverTime(ev *evaluator, args Expressions) Value {
|
||||
q := ev.evalFloat(args[0])
|
||||
mat := ev.evalMatrix(args[1])
|
||||
resultVector := vector{}
|
||||
resultVector := Vector{}
|
||||
|
||||
for _, el := range mat {
|
||||
if len(el.Values) == 0 {
|
||||
|
@ -498,7 +498,7 @@ func funcQuantileOverTime(ev *evaluator, args Expressions) Value {
|
|||
}
|
||||
|
||||
el.Metric = copyLabels(el.Metric, false)
|
||||
values := make(vectorByValueHeap, 0, len(el.Values))
|
||||
values := make(VectorByValueHeap, 0, len(el.Values))
|
||||
for _, v := range el.Values {
|
||||
values = append(values, sample{Value: v.v})
|
||||
}
|
||||
|
@ -539,20 +539,20 @@ func funcStdvarOverTime(ev *evaluator, args Expressions) Value {
|
|||
})
|
||||
}
|
||||
|
||||
// === abs(vector ValueTypeVector) Vector ===
|
||||
// === abs(Vector ValueTypeVector) Vector ===
|
||||
func funcAbs(ev *evaluator, args Expressions) Value {
|
||||
vector := ev.evalVector(args[0])
|
||||
for _, el := range vector {
|
||||
Vector := ev.evalVector(args[0])
|
||||
for _, el := range Vector {
|
||||
el.Metric = copyLabels(el.Metric, false)
|
||||
el.Value = math.Abs(float64(el.Value))
|
||||
}
|
||||
return vector
|
||||
return Vector
|
||||
}
|
||||
|
||||
// === absent(vector ValueTypeVector) Vector ===
|
||||
// === absent(Vector ValueTypeVector) Vector ===
|
||||
func funcAbsent(ev *evaluator, args Expressions) Value {
|
||||
if len(ev.evalVector(args[0])) > 0 {
|
||||
return vector{}
|
||||
return Vector{}
|
||||
}
|
||||
m := []labels.Label{}
|
||||
|
||||
|
@ -563,7 +563,7 @@ func funcAbsent(ev *evaluator, args Expressions) Value {
|
|||
}
|
||||
}
|
||||
}
|
||||
return vector{
|
||||
return Vector{
|
||||
sample{
|
||||
Metric: labels.New(m...),
|
||||
Value: 1,
|
||||
|
@ -572,64 +572,64 @@ func funcAbsent(ev *evaluator, args Expressions) Value {
|
|||
}
|
||||
}
|
||||
|
||||
// === ceil(vector ValueTypeVector) Vector ===
|
||||
// === ceil(Vector ValueTypeVector) Vector ===
|
||||
func funcCeil(ev *evaluator, args Expressions) Value {
|
||||
vector := ev.evalVector(args[0])
|
||||
for _, el := range vector {
|
||||
Vector := ev.evalVector(args[0])
|
||||
for _, el := range Vector {
|
||||
el.Metric = copyLabels(el.Metric, false)
|
||||
el.Value = math.Ceil(float64(el.Value))
|
||||
}
|
||||
return vector
|
||||
return Vector
|
||||
}
|
||||
|
||||
// === exp(vector ValueTypeVector) Vector ===
|
||||
// === exp(Vector ValueTypeVector) Vector ===
|
||||
func funcExp(ev *evaluator, args Expressions) Value {
|
||||
vector := ev.evalVector(args[0])
|
||||
for _, el := range vector {
|
||||
Vector := ev.evalVector(args[0])
|
||||
for _, el := range Vector {
|
||||
el.Metric = copyLabels(el.Metric, false)
|
||||
el.Value = math.Exp(float64(el.Value))
|
||||
}
|
||||
return vector
|
||||
return Vector
|
||||
}
|
||||
|
||||
// === sqrt(vector VectorNode) Vector ===
|
||||
// === sqrt(Vector VectorNode) Vector ===
|
||||
func funcSqrt(ev *evaluator, args Expressions) Value {
|
||||
vector := ev.evalVector(args[0])
|
||||
for _, el := range vector {
|
||||
Vector := ev.evalVector(args[0])
|
||||
for _, el := range Vector {
|
||||
el.Metric = copyLabels(el.Metric, false)
|
||||
el.Value = math.Sqrt(float64(el.Value))
|
||||
}
|
||||
return vector
|
||||
return Vector
|
||||
}
|
||||
|
||||
// === ln(vector ValueTypeVector) Vector ===
|
||||
// === ln(Vector ValueTypeVector) Vector ===
|
||||
func funcLn(ev *evaluator, args Expressions) Value {
|
||||
vector := ev.evalVector(args[0])
|
||||
for _, el := range vector {
|
||||
Vector := ev.evalVector(args[0])
|
||||
for _, el := range Vector {
|
||||
el.Metric = copyLabels(el.Metric, false)
|
||||
el.Value = math.Log(float64(el.Value))
|
||||
}
|
||||
return vector
|
||||
return Vector
|
||||
}
|
||||
|
||||
// === log2(vector ValueTypeVector) Vector ===
|
||||
// === log2(Vector ValueTypeVector) Vector ===
|
||||
func funcLog2(ev *evaluator, args Expressions) Value {
|
||||
vector := ev.evalVector(args[0])
|
||||
for _, el := range vector {
|
||||
Vector := ev.evalVector(args[0])
|
||||
for _, el := range Vector {
|
||||
el.Metric = copyLabels(el.Metric, false)
|
||||
el.Value = math.Log2(float64(el.Value))
|
||||
}
|
||||
return vector
|
||||
return Vector
|
||||
}
|
||||
|
||||
// === log10(vector ValueTypeVector) Vector ===
|
||||
// === log10(Vector ValueTypeVector) Vector ===
|
||||
func funcLog10(ev *evaluator, args Expressions) Value {
|
||||
vector := ev.evalVector(args[0])
|
||||
for _, el := range vector {
|
||||
Vector := ev.evalVector(args[0])
|
||||
for _, el := range Vector {
|
||||
el.Metric = copyLabels(el.Metric, false)
|
||||
el.Value = math.Log10(float64(el.Value))
|
||||
}
|
||||
return vector
|
||||
return Vector
|
||||
}
|
||||
|
||||
// linearRegression performs a least-square linear regression analysis on the
|
||||
|
@ -660,11 +660,11 @@ func linearRegression(samples []samplePair, interceptTime int64) (slope, interce
|
|||
// === deriv(node ValueTypeMatrix) Vector ===
|
||||
func funcDeriv(ev *evaluator, args Expressions) Value {
|
||||
mat := ev.evalMatrix(args[0])
|
||||
resultVector := make(vector, 0, len(mat))
|
||||
resultVector := make(Vector, 0, len(mat))
|
||||
|
||||
for _, samples := range mat {
|
||||
// No sense in trying to compute a derivative without at least two points.
|
||||
// Drop this vector element.
|
||||
// Drop this Vector element.
|
||||
if len(samples.Values) < 2 {
|
||||
continue
|
||||
}
|
||||
|
@ -683,12 +683,12 @@ func funcDeriv(ev *evaluator, args Expressions) Value {
|
|||
// === predict_linear(node ValueTypeMatrix, k ValueTypeScalar) Vector ===
|
||||
func funcPredictLinear(ev *evaluator, args Expressions) Value {
|
||||
mat := ev.evalMatrix(args[0])
|
||||
resultVector := make(vector, 0, len(mat))
|
||||
resultVector := make(Vector, 0, len(mat))
|
||||
duration := ev.evalFloat(args[1])
|
||||
|
||||
for _, samples := range mat {
|
||||
// No sense in trying to predict anything without at least two points.
|
||||
// Drop this vector element.
|
||||
// Drop this Vector element.
|
||||
if len(samples.Values) < 2 {
|
||||
continue
|
||||
}
|
||||
|
@ -703,12 +703,12 @@ func funcPredictLinear(ev *evaluator, args Expressions) Value {
|
|||
return resultVector
|
||||
}
|
||||
|
||||
// === histogram_quantile(k ValueTypeScalar, vector ValueTypeVector) Vector ===
|
||||
// === histogram_quantile(k ValueTypeScalar, Vector ValueTypeVector) Vector ===
|
||||
func funcHistogramQuantile(ev *evaluator, args Expressions) Value {
|
||||
q := ev.evalFloat(args[0])
|
||||
inVec := ev.evalVector(args[1])
|
||||
|
||||
outVec := vector{}
|
||||
outVec := Vector{}
|
||||
signatureToMetricWithBuckets := map[uint64]*metricWithBuckets{}
|
||||
for _, el := range inVec {
|
||||
upperBound, err := strconv.ParseFloat(
|
||||
|
@ -748,7 +748,7 @@ func funcHistogramQuantile(ev *evaluator, args Expressions) Value {
|
|||
// === resets(matrix ValueTypeMatrix) Vector ===
|
||||
func funcResets(ev *evaluator, args Expressions) Value {
|
||||
in := ev.evalMatrix(args[0])
|
||||
out := make(vector, 0, len(in))
|
||||
out := make(Vector, 0, len(in))
|
||||
|
||||
for _, samples := range in {
|
||||
resets := 0
|
||||
|
@ -773,7 +773,7 @@ func funcResets(ev *evaluator, args Expressions) Value {
|
|||
// === changes(matrix ValueTypeMatrix) Vector ===
|
||||
func funcChanges(ev *evaluator, args Expressions) Value {
|
||||
in := ev.evalMatrix(args[0])
|
||||
out := make(vector, 0, len(in))
|
||||
out := make(Vector, 0, len(in))
|
||||
|
||||
for _, samples := range in {
|
||||
changes := 0
|
||||
|
@ -795,10 +795,10 @@ func funcChanges(ev *evaluator, args Expressions) Value {
|
|||
return out
|
||||
}
|
||||
|
||||
// === label_replace(vector ValueTypeVector, dst_label, replacement, src_labelname, regex ValueTypeString) Vector ===
|
||||
// === label_replace(Vector ValueTypeVector, dst_label, replacement, src_labelname, regex ValueTypeString) Vector ===
|
||||
func funcLabelReplace(ev *evaluator, args Expressions) Value {
|
||||
var (
|
||||
vector = ev.evalVector(args[0])
|
||||
Vector = ev.evalVector(args[0])
|
||||
dst = ev.evalString(args[1]).s
|
||||
repl = ev.evalString(args[2]).s
|
||||
src = ev.evalString(args[3]).s
|
||||
|
@ -813,8 +813,8 @@ func funcLabelReplace(ev *evaluator, args Expressions) Value {
|
|||
ev.errorf("invalid destination label name in label_replace(): %s", dst)
|
||||
}
|
||||
|
||||
outSet := make(map[uint64]struct{}, len(vector))
|
||||
for _, el := range vector {
|
||||
outSet := make(map[uint64]struct{}, len(Vector))
|
||||
for _, el := range Vector {
|
||||
srcVal := el.Metric.Get(src)
|
||||
indexes := regex.FindStringSubmatchIndex(srcVal)
|
||||
// If there is no match, no replacement should take place.
|
||||
|
@ -837,12 +837,12 @@ func funcLabelReplace(ev *evaluator, args Expressions) Value {
|
|||
}
|
||||
}
|
||||
|
||||
return vector
|
||||
return Vector
|
||||
}
|
||||
|
||||
// === vector(s scalar) Vector ===
|
||||
// === Vector(s scalar) Vector ===
|
||||
func funcVector(ev *evaluator, args Expressions) Value {
|
||||
return vector{
|
||||
return Vector{
|
||||
sample{
|
||||
Metric: labels.Labels{},
|
||||
Value: ev.evalFloat(args[0]),
|
||||
|
@ -853,9 +853,9 @@ func funcVector(ev *evaluator, args Expressions) Value {
|
|||
|
||||
// Common code for date related functions.
|
||||
func dateWrapper(ev *evaluator, args Expressions, f func(time.Time) float64) Value {
|
||||
var v vector
|
||||
var v Vector
|
||||
if len(args) == 0 {
|
||||
v = vector{
|
||||
v = Vector{
|
||||
sample{
|
||||
Metric: labels.Labels{},
|
||||
Value: float64(ev.Timestamp) / 1000,
|
||||
|
@ -872,49 +872,49 @@ func dateWrapper(ev *evaluator, args Expressions, f func(time.Time) float64) Val
|
|||
return v
|
||||
}
|
||||
|
||||
// === days_in_month(v vector) scalar ===
|
||||
// === days_in_month(v Vector) scalar ===
|
||||
func funcDaysInMonth(ev *evaluator, args Expressions) Value {
|
||||
return dateWrapper(ev, args, func(t time.Time) float64 {
|
||||
return float64(32 - time.Date(t.Year(), t.Month(), 32, 0, 0, 0, 0, time.UTC).Day())
|
||||
})
|
||||
}
|
||||
|
||||
// === day_of_month(v vector) scalar ===
|
||||
// === day_of_month(v Vector) scalar ===
|
||||
func funcDayOfMonth(ev *evaluator, args Expressions) Value {
|
||||
return dateWrapper(ev, args, func(t time.Time) float64 {
|
||||
return float64(t.Day())
|
||||
})
|
||||
}
|
||||
|
||||
// === day_of_week(v vector) scalar ===
|
||||
// === day_of_week(v Vector) scalar ===
|
||||
func funcDayOfWeek(ev *evaluator, args Expressions) Value {
|
||||
return dateWrapper(ev, args, func(t time.Time) float64 {
|
||||
return float64(t.Weekday())
|
||||
})
|
||||
}
|
||||
|
||||
// === hour(v vector) scalar ===
|
||||
// === hour(v Vector) scalar ===
|
||||
func funcHour(ev *evaluator, args Expressions) Value {
|
||||
return dateWrapper(ev, args, func(t time.Time) float64 {
|
||||
return float64(t.Hour())
|
||||
})
|
||||
}
|
||||
|
||||
// === minute(v vector) scalar ===
|
||||
// === minute(v Vector) scalar ===
|
||||
func funcMinute(ev *evaluator, args Expressions) Value {
|
||||
return dateWrapper(ev, args, func(t time.Time) float64 {
|
||||
return float64(t.Minute())
|
||||
})
|
||||
}
|
||||
|
||||
// === month(v vector) scalar ===
|
||||
// === month(v Vector) scalar ===
|
||||
func funcMonth(ev *evaluator, args Expressions) Value {
|
||||
return dateWrapper(ev, args, func(t time.Time) float64 {
|
||||
return float64(t.Month())
|
||||
})
|
||||
}
|
||||
|
||||
// === year(v vector) scalar ===
|
||||
// === year(v Vector) scalar ===
|
||||
func funcYear(ev *evaluator, args Expressions) Value {
|
||||
return dateWrapper(ev, args, func(t time.Time) float64 {
|
||||
return float64(t.Year())
|
||||
|
@ -1193,8 +1193,8 @@ var functions = map[string]*Function{
|
|||
ReturnType: ValueTypeScalar,
|
||||
Call: funcTime,
|
||||
},
|
||||
"vector": {
|
||||
Name: "vector",
|
||||
"Vector": {
|
||||
Name: "Vector",
|
||||
ArgTypes: []ValueType{ValueTypeScalar},
|
||||
ReturnType: ValueTypeVector,
|
||||
Call: funcVector,
|
||||
|
@ -1214,28 +1214,28 @@ func getFunction(name string) (*Function, bool) {
|
|||
return function, ok
|
||||
}
|
||||
|
||||
type vectorByValueHeap vector
|
||||
type VectorByValueHeap Vector
|
||||
|
||||
func (s vectorByValueHeap) Len() int {
|
||||
func (s VectorByValueHeap) Len() int {
|
||||
return len(s)
|
||||
}
|
||||
|
||||
func (s vectorByValueHeap) Less(i, j int) bool {
|
||||
func (s VectorByValueHeap) Less(i, j int) bool {
|
||||
if math.IsNaN(float64(s[i].Value)) {
|
||||
return true
|
||||
}
|
||||
return s[i].Value < s[j].Value
|
||||
}
|
||||
|
||||
func (s vectorByValueHeap) Swap(i, j int) {
|
||||
func (s VectorByValueHeap) Swap(i, j int) {
|
||||
s[i], s[j] = s[j], s[i]
|
||||
}
|
||||
|
||||
func (s *vectorByValueHeap) Push(x interface{}) {
|
||||
func (s *VectorByValueHeap) Push(x interface{}) {
|
||||
*s = append(*s, x.(sample))
|
||||
}
|
||||
|
||||
func (s *vectorByValueHeap) Pop() interface{} {
|
||||
func (s *VectorByValueHeap) Pop() interface{} {
|
||||
old := *s
|
||||
n := len(old)
|
||||
el := old[n-1]
|
||||
|
@ -1243,28 +1243,28 @@ func (s *vectorByValueHeap) Pop() interface{} {
|
|||
return el
|
||||
}
|
||||
|
||||
type vectorByReverseValueHeap vector
|
||||
type VectorByReverseValueHeap Vector
|
||||
|
||||
func (s vectorByReverseValueHeap) Len() int {
|
||||
func (s VectorByReverseValueHeap) Len() int {
|
||||
return len(s)
|
||||
}
|
||||
|
||||
func (s vectorByReverseValueHeap) Less(i, j int) bool {
|
||||
func (s VectorByReverseValueHeap) Less(i, j int) bool {
|
||||
if math.IsNaN(float64(s[i].Value)) {
|
||||
return true
|
||||
}
|
||||
return s[i].Value > s[j].Value
|
||||
}
|
||||
|
||||
func (s vectorByReverseValueHeap) Swap(i, j int) {
|
||||
func (s VectorByReverseValueHeap) Swap(i, j int) {
|
||||
s[i], s[j] = s[j], s[i]
|
||||
}
|
||||
|
||||
func (s *vectorByReverseValueHeap) Push(x interface{}) {
|
||||
func (s *VectorByReverseValueHeap) Push(x interface{}) {
|
||||
*s = append(*s, x.(sample))
|
||||
}
|
||||
|
||||
func (s *vectorByReverseValueHeap) Pop() interface{} {
|
||||
func (s *VectorByReverseValueHeap) Pop() interface{} {
|
||||
old := *s
|
||||
n := len(old)
|
||||
el := old[n-1]
|
||||
|
|
|
@ -95,7 +95,7 @@ func ParseMetricSelector(input string) (m []*LabelMatcher, err error) {
|
|||
if t := p.peek().typ; t == itemMetricIdentifier || t == itemIdentifier {
|
||||
name = p.next().val
|
||||
}
|
||||
vs := p.vectorSelector(name)
|
||||
vs := p.VectorSelector(name)
|
||||
if p.peek().typ != itemEOF {
|
||||
p.errorf("could not parse remaining input %.15q...", p.lex.input[p.lex.lastPos:])
|
||||
}
|
||||
|
@ -367,7 +367,7 @@ func (p *parser) alertStmt() *AlertStmt {
|
|||
|
||||
p.expect(itemAlert, ctx)
|
||||
name := p.expect(itemIdentifier, ctx)
|
||||
// Alerts require a vector typed expression.
|
||||
// Alerts require a Vector typed expression.
|
||||
p.expect(itemIf, ctx)
|
||||
expr := p.expr()
|
||||
|
||||
|
@ -531,7 +531,7 @@ func (p *parser) balance(lhs Expr, op itemType, rhs Expr, vecMatching *VectorMat
|
|||
|
||||
// unaryExpr parses a unary expression.
|
||||
//
|
||||
// <vector_selector> | <matrix_selector> | (+|-) <number_literal> | '(' <expr> ')'
|
||||
// <Vector_selector> | <matrix_selector> | (+|-) <number_literal> | '(' <expr> ')'
|
||||
//
|
||||
func (p *parser) unaryExpr() Expr {
|
||||
switch t := p.peek(); t.typ {
|
||||
|
@ -584,9 +584,9 @@ func (p *parser) unaryExpr() Expr {
|
|||
}
|
||||
|
||||
// rangeSelector parses a matrix (a.k.a. range) selector based on a given
|
||||
// vector selector.
|
||||
// Vector selector.
|
||||
//
|
||||
// <vector_selector> '[' <duration> ']'
|
||||
// <Vector_selector> '[' <duration> ']'
|
||||
//
|
||||
func (p *parser) rangeSelector(vs *VectorSelector) *MatrixSelector {
|
||||
const ctx = "range selector"
|
||||
|
@ -626,7 +626,7 @@ func (p *parser) number(val string) float64 {
|
|||
|
||||
// primaryExpr parses a primary expression.
|
||||
//
|
||||
// <metric_name> | <function_call> | <vector_aggregation> | <literal>
|
||||
// <metric_name> | <function_call> | <Vector_aggregation> | <literal>
|
||||
//
|
||||
func (p *parser) primaryExpr() Expr {
|
||||
switch t := p.next(); {
|
||||
|
@ -640,7 +640,7 @@ func (p *parser) primaryExpr() Expr {
|
|||
case t.typ == itemLeftBrace:
|
||||
// Metric selector without metric name.
|
||||
p.backup()
|
||||
return p.vectorSelector("")
|
||||
return p.VectorSelector("")
|
||||
|
||||
case t.typ == itemIdentifier:
|
||||
// Check for function call.
|
||||
|
@ -650,7 +650,7 @@ func (p *parser) primaryExpr() Expr {
|
|||
fallthrough // Else metric selector.
|
||||
|
||||
case t.typ == itemMetricIdentifier:
|
||||
return p.vectorSelector(t.val)
|
||||
return p.VectorSelector(t.val)
|
||||
|
||||
case t.typ.isAggregator():
|
||||
p.backup()
|
||||
|
@ -693,8 +693,8 @@ func (p *parser) labels() []string {
|
|||
|
||||
// aggrExpr parses an aggregation expression.
|
||||
//
|
||||
// <aggr_op> (<vector_expr>) [by <labels>] [keep_common]
|
||||
// <aggr_op> [by <labels>] [keep_common] (<vector_expr>)
|
||||
// <aggr_op> (<Vector_expr>) [by <labels>] [keep_common]
|
||||
// <aggr_op> [by <labels>] [keep_common] (<Vector_expr>)
|
||||
//
|
||||
func (p *parser) aggrExpr() *AggregateExpr {
|
||||
const ctx = "aggregation"
|
||||
|
@ -935,12 +935,12 @@ func (p *parser) offset() time.Duration {
|
|||
return offset
|
||||
}
|
||||
|
||||
// vectorSelector parses a new (instant) vector selector.
|
||||
// VectorSelector parses a new (instant) Vector selector.
|
||||
//
|
||||
// <metric_identifier> [<label_matchers>]
|
||||
// [<metric_identifier>] <label_matchers>
|
||||
//
|
||||
func (p *parser) vectorSelector(name string) *VectorSelector {
|
||||
func (p *parser) VectorSelector(name string) *VectorSelector {
|
||||
var matchers []*LabelMatcher
|
||||
// Parse label matching if any.
|
||||
if t := p.peek(); t.typ == itemLeftBrace {
|
||||
|
@ -949,7 +949,7 @@ func (p *parser) vectorSelector(name string) *VectorSelector {
|
|||
// Metric name must not be set in the label matchers and before at the same time.
|
||||
if name != "" {
|
||||
for _, m := range matchers {
|
||||
if m.Name == model.MetricNameLabel {
|
||||
if m.Name == MetricNameLabel {
|
||||
p.errorf("metric name must not be set twice: %q or %q", name, m.Value)
|
||||
}
|
||||
}
|
||||
|
@ -962,9 +962,9 @@ func (p *parser) vectorSelector(name string) *VectorSelector {
|
|||
}
|
||||
|
||||
if len(matchers) == 0 {
|
||||
p.errorf("vector selector must contain label matchers or metric name")
|
||||
p.errorf("Vector selector must contain label matchers or metric name")
|
||||
}
|
||||
// A vector selector must contain at least one non-empty matcher to prevent
|
||||
// A Vector selector must contain at least one non-empty matcher to prevent
|
||||
// implicit selection of all metrics (e.g. by a typo).
|
||||
notEmpty := false
|
||||
for _, lm := range matchers {
|
||||
|
@ -974,7 +974,7 @@ func (p *parser) vectorSelector(name string) *VectorSelector {
|
|||
}
|
||||
}
|
||||
if !notEmpty {
|
||||
p.errorf("vector selector must contain at least one non-empty matcher")
|
||||
p.errorf("Vector selector must contain at least one non-empty matcher")
|
||||
}
|
||||
|
||||
return &VectorSelector{
|
||||
|
@ -1028,7 +1028,7 @@ func (p *parser) checkType(node Node) (typ ValueType) {
|
|||
case *RecordStmt:
|
||||
ty := p.checkType(n.Expr)
|
||||
if ty != ValueTypeVector && ty != ValueTypeScalar {
|
||||
p.errorf("record statement must have a valid expression of type instant vector or scalar but got %s", documentedType(ty))
|
||||
p.errorf("record statement must have a valid expression of type instant Vector or scalar but got %s", documentedType(ty))
|
||||
}
|
||||
|
||||
case Expressions:
|
||||
|
@ -1058,16 +1058,16 @@ func (p *parser) checkType(node Node) (typ ValueType) {
|
|||
p.errorf("binary expression does not support operator %q", n.Op)
|
||||
}
|
||||
if (lt != ValueTypeScalar && lt != ValueTypeVector) || (rt != ValueTypeScalar && rt != ValueTypeVector) {
|
||||
p.errorf("binary expression must contain only scalar and instant vector types")
|
||||
p.errorf("binary expression must contain only scalar and instant Vector types")
|
||||
}
|
||||
|
||||
if (lt != ValueTypeVector || rt != ValueTypeVector) && n.VectorMatching != nil {
|
||||
if len(n.VectorMatching.MatchingLabels) > 0 {
|
||||
p.errorf("vector matching only allowed between instant vectors")
|
||||
p.errorf("Vector matching only allowed between instant Vectors")
|
||||
}
|
||||
n.VectorMatching = nil
|
||||
} else {
|
||||
// Both operands are vectors.
|
||||
// Both operands are Vectors.
|
||||
if n.Op.isSetOperator() {
|
||||
if n.VectorMatching.Card == CardOneToMany || n.VectorMatching.Card == CardManyToOne {
|
||||
p.errorf("no grouping allowed for %q operation", n.Op)
|
||||
|
@ -1102,7 +1102,7 @@ func (p *parser) checkType(node Node) (typ ValueType) {
|
|||
p.errorf("only + and - operators allowed for unary expressions")
|
||||
}
|
||||
if t := p.checkType(n.Expr); t != ValueTypeScalar && t != ValueTypeVector {
|
||||
p.errorf("unary expression only allowed on expressions of type scalar or instant vector, got %q", documentedType(t))
|
||||
p.errorf("unary expression only allowed on expressions of type scalar or instant Vector, got %q", documentedType(t))
|
||||
}
|
||||
|
||||
case *NumberLiteral, *MatrixSelector, *StringLiteral, *VectorSelector:
|
||||
|
|
|
@ -236,11 +236,11 @@ var testExpr = []struct {
|
|||
}, {
|
||||
input: `-"string"`,
|
||||
fail: true,
|
||||
errMsg: `unary expression only allowed on expressions of type scalar or instant vector, got "string"`,
|
||||
errMsg: `unary expression only allowed on expressions of type scalar or instant Vector, got "string"`,
|
||||
}, {
|
||||
input: `-test[5m]`,
|
||||
fail: true,
|
||||
errMsg: `unary expression only allowed on expressions of type scalar or instant vector, got "range vector"`,
|
||||
errMsg: `unary expression only allowed on expressions of type scalar or instant Vector, got "range Vector"`,
|
||||
}, {
|
||||
input: `*test`,
|
||||
fail: true,
|
||||
|
@ -771,11 +771,11 @@ var testExpr = []struct {
|
|||
}, {
|
||||
input: "1 or on(bar) foo",
|
||||
fail: true,
|
||||
errMsg: "vector matching only allowed between instant vectors",
|
||||
errMsg: "Vector matching only allowed between instant Vectors",
|
||||
}, {
|
||||
input: "foo == on(bar) 10",
|
||||
fail: true,
|
||||
errMsg: "vector matching only allowed between instant vectors",
|
||||
errMsg: "Vector matching only allowed between instant Vectors",
|
||||
}, {
|
||||
input: "foo and on(bar) group_left(baz) bar",
|
||||
fail: true,
|
||||
|
@ -817,7 +817,7 @@ var testExpr = []struct {
|
|||
fail: true,
|
||||
errMsg: "bool modifier can only be used on comparison operators",
|
||||
},
|
||||
// Test vector selector.
|
||||
// Test Vector selector.
|
||||
{
|
||||
input: "foo",
|
||||
expected: &VectorSelector{
|
||||
|
@ -914,23 +914,23 @@ var testExpr = []struct {
|
|||
}, {
|
||||
input: `{}`,
|
||||
fail: true,
|
||||
errMsg: "vector selector must contain label matchers or metric name",
|
||||
errMsg: "Vector selector must contain label matchers or metric name",
|
||||
}, {
|
||||
input: `{x=""}`,
|
||||
fail: true,
|
||||
errMsg: "vector selector must contain at least one non-empty matcher",
|
||||
errMsg: "Vector selector must contain at least one non-empty matcher",
|
||||
}, {
|
||||
input: `{x=~".*"}`,
|
||||
fail: true,
|
||||
errMsg: "vector selector must contain at least one non-empty matcher",
|
||||
errMsg: "Vector selector must contain at least one non-empty matcher",
|
||||
}, {
|
||||
input: `{x!~".+"}`,
|
||||
fail: true,
|
||||
errMsg: "vector selector must contain at least one non-empty matcher",
|
||||
errMsg: "Vector selector must contain at least one non-empty matcher",
|
||||
}, {
|
||||
input: `{x!="a"}`,
|
||||
fail: true,
|
||||
errMsg: "vector selector must contain at least one non-empty matcher",
|
||||
errMsg: "Vector selector must contain at least one non-empty matcher",
|
||||
}, {
|
||||
input: `foo{__name__="bar"}`,
|
||||
fail: true,
|
||||
|
@ -1285,7 +1285,7 @@ var testExpr = []struct {
|
|||
}, {
|
||||
input: `topk(some_metric, other_metric)`,
|
||||
fail: true,
|
||||
errMsg: "parse error at char 32: expected type scalar in aggregation parameter, got instant vector",
|
||||
errMsg: "parse error at char 32: expected type scalar in aggregation parameter, got instant Vector",
|
||||
}, {
|
||||
input: `count_values(5, other_metric)`,
|
||||
fail: true,
|
||||
|
@ -1363,7 +1363,7 @@ var testExpr = []struct {
|
|||
}, {
|
||||
input: "floor(1)",
|
||||
fail: true,
|
||||
errMsg: "expected type instant vector in call to function \"floor\", got scalar",
|
||||
errMsg: "expected type instant Vector in call to function \"floor\", got scalar",
|
||||
}, {
|
||||
input: "non_existent_function_far_bar()",
|
||||
fail: true,
|
||||
|
@ -1371,7 +1371,7 @@ var testExpr = []struct {
|
|||
}, {
|
||||
input: "rate(some_metric)",
|
||||
fail: true,
|
||||
errMsg: "expected type range vector in call to function \"rate\", got instant vector",
|
||||
errMsg: "expected type range Vector in call to function \"rate\", got instant Vector",
|
||||
},
|
||||
// Fuzzing regression tests.
|
||||
{
|
||||
|
|
|
@ -106,13 +106,13 @@ func bucketQuantile(q float64, buckets buckets) float64 {
|
|||
return bucketStart + (bucketEnd-bucketStart)*float64(rank/count)
|
||||
}
|
||||
|
||||
// qauntile calculates the given quantile of a vector of samples.
|
||||
// qauntile calculates the given quantile of a Vector of samples.
|
||||
//
|
||||
// The vector will be sorted.
|
||||
// The Vector will be sorted.
|
||||
// If 'values' has zero elements, NaN is returned.
|
||||
// If q<0, -Inf is returned.
|
||||
// If q>1, +Inf is returned.
|
||||
func quantile(q float64, values vectorByValueHeap) float64 {
|
||||
func quantile(q float64, values VectorByValueHeap) float64 {
|
||||
if len(values) == 0 {
|
||||
return math.NaN()
|
||||
}
|
||||
|
|
|
@ -378,7 +378,7 @@ func (ev *evalCmd) compareResult(result Value) error {
|
|||
}
|
||||
}
|
||||
|
||||
case vector:
|
||||
case Vector:
|
||||
if !ev.instant {
|
||||
return fmt.Errorf("received instant result on range evaluation")
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue