cloudflare/pint

Public

mirrored from https://github.com/cloudflare/pintAvailable

CodeCommitsIssuesPull requestsActionsInsightsSecurity
v0.57.1

Branches

Tags

  • No tags available.
0Branches0Tags
Go to file
Add file
Code

Clone

HTTPS

Download ZIP

internal/parser/utils/absent.go

78lines · modecode

1package utils
2
3import (
4 "log/slog"
5
6 "github.com/cloudflare/pint/internal/parser"
7
8 promParser "github.com/prometheus/prometheus/promql/parser"
9)
10
11type PromQLFragment struct {
12 Fragment *parser.PromQLNode
13 BinExpr *promParser.BinaryExpr
14}
15
16func HasOuterAbsent(node *parser.PromQLNode) (calls []PromQLFragment) {
17 if n, ok := node.Expr.(*promParser.Call); ok && n.Func.Name == "absent" {
18 calls = append(calls, PromQLFragment{Fragment: node})
19 return calls
20 }
21
22 if n, ok := node.Expr.(*promParser.BinaryExpr); ok {
23 if n.VectorMatching != nil {
24 switch n.VectorMatching.Card {
25 // bar / absent(foo)
26 // absent(foo) / bar
27 case promParser.CardOneToOne:
28
29 // absent(foo{job="bar"}) * on(job) group_left(xxx) bar
30 // bar * on() group_left(xxx) absent(foo{job="bar"})
31 case promParser.CardManyToOne:
32 if ln, ok := n.LHS.(*promParser.Call); ok && ln.Func.Name == "absent" {
33 calls = append(calls, PromQLFragment{
34 Fragment: node.Children[0],
35 BinExpr: n,
36 })
37 }
38
39 // bar * on() group_right(xxx) absent(foo{job="bar"})
40 // absent(foo{job="bar"}) * on(job) group_right(xxx) bar
41 case promParser.CardOneToMany:
42 if rn, ok := n.RHS.(*promParser.Call); ok && rn.Func.Name == "absent" {
43 calls = append(calls, PromQLFragment{
44 Fragment: node.Children[1],
45 BinExpr: n,
46 })
47 }
48
49 // bar AND absent(foo{job="bar"})
50 // bar OR absent(foo{job="bar"})
51 // bar UNLESS absent(foo{job="bar"})
52 case promParser.CardManyToMany:
53 if n.Op == promParser.LOR {
54 for _, child := range node.Children {
55 calls = append(calls, HasOuterAbsent(child)...)
56 }
57 } else {
58 if ln, ok := n.LHS.(*promParser.Call); ok && ln.Func.Name == "absent" {
59 calls = append(calls, PromQLFragment{
60 Fragment: node.Children[0],
61 BinExpr: n,
62 })
63 }
64 }
65
66 default:
67 slog.Warn("Unsupported VectorMatching operation", slog.String("matching", n.VectorMatching.Card.String()))
68 }
69 return calls
70 }
71 }
72
73 for _, child := range node.Children {
74 calls = append(calls, HasOuterAbsent(child)...)
75 }
76
77 return calls
78}
79