diff --git a/pkg/logql/syntax/ast.go b/pkg/logql/syntax/ast.go index 2e7b8a2e0e19d..e391291c23242 100644 --- a/pkg/logql/syntax/ast.go +++ b/pkg/logql/syntax/ast.go @@ -185,16 +185,22 @@ func (m MultiStageExpr) reorderStages() []StageExpr { func combineFilters(in []*LineFilterExpr) StageExpr { result := in[len(in)-1] for i := len(in) - 2; i >= 0; i-- { - leafNode(result).Left = in[i] + leaf := leafNode(result, in[i]) + if leaf != nil { + leaf.Left = in[i] + } } return result } -func leafNode(in *LineFilterExpr) *LineFilterExpr { +func leafNode(in *LineFilterExpr, child *LineFilterExpr) *LineFilterExpr { current := in //nolint:revive for ; current.Left != nil; current = current.Left { + if current == child || current.Left == child { + return nil + } } return current } diff --git a/pkg/logql/syntax/ast_test.go b/pkg/logql/syntax/ast_test.go index cb36cb2e7cd8e..ddb6302f389f7 100644 --- a/pkg/logql/syntax/ast_test.go +++ b/pkg/logql/syntax/ast_test.go @@ -1093,3 +1093,24 @@ func TestGroupingString(t *testing.T) { } require.Equal(t, " without ()", g.String()) } + +func TestCombineFilters(t *testing.T) { + in := []*LineFilterExpr{ + {LineFilter: LineFilter{Ty: log.LineMatchEqual, Match: "test1"}}, + {LineFilter: LineFilter{Ty: log.LineMatchEqual, Match: "test2"}}, + } + + var combineFilter StageExpr + for i := 0; i < 2; i++ { + combineFilter = combineFilters(in) + } + + current := combineFilter.(*LineFilterExpr) + i := 0 + for ; current.Left != nil; current = current.Left { + i++ + if i > 2 { + t.Fatalf("left num isn't a correct number") + } + } +}