Coverage Report

Created: 2025-11-29 07:01

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/proc/self/cwd/parser/macro_expr_factory.cc
Line
Count
Source
1
// Copyright 2024 Google LLC
2
//
3
// Licensed under the Apache License, Version 2.0 (the "License");
4
// you may not use this file except in compliance with the License.
5
// You may obtain a copy of the License at
6
//
7
//     https://www.apache.org/licenses/LICENSE-2.0
8
//
9
// Unless required by applicable law or agreed to in writing, software
10
// distributed under the License is distributed on an "AS IS" BASIS,
11
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
// See the License for the specific language governing permissions and
13
// limitations under the License.
14
15
#include "parser/macro_expr_factory.h"
16
17
#include <utility>
18
#include <vector>
19
20
#include "absl/functional/overload.h"
21
#include "absl/types/optional.h"
22
#include "absl/types/variant.h"
23
#include "common/constant.h"
24
#include "common/expr.h"
25
26
namespace cel {
27
28
0
Expr MacroExprFactory::Copy(const Expr& expr) {
29
  // Copying logic is recursive at the moment, we alter it to be iterative in
30
  // the future.
31
0
  return absl::visit(
32
0
      absl::Overload(
33
0
          [this, &expr](const UnspecifiedExpr&) -> Expr {
34
0
            return NewUnspecified(CopyId(expr));
35
0
          },
36
0
          [this, &expr](const Constant& const_expr) -> Expr {
37
0
            return NewConst(CopyId(expr), const_expr);
38
0
          },
39
0
          [this, &expr](const IdentExpr& ident_expr) -> Expr {
40
0
            return NewIdent(CopyId(expr), ident_expr.name());
41
0
          },
42
0
          [this, &expr](const SelectExpr& select_expr) -> Expr {
43
0
            const auto id = CopyId(expr);
44
0
            return select_expr.test_only()
45
0
                       ? NewPresenceTest(id, Copy(select_expr.operand()),
46
0
                                         select_expr.field())
47
0
                       : NewSelect(id, Copy(select_expr.operand()),
48
0
                                   select_expr.field());
49
0
          },
50
0
          [this, &expr](const CallExpr& call_expr) -> Expr {
51
0
            const auto id = CopyId(expr);
52
0
            absl::optional<Expr> target;
53
0
            if (call_expr.has_target()) {
54
0
              target = Copy(call_expr.target());
55
0
            }
56
0
            std::vector<Expr> args;
57
0
            args.reserve(call_expr.args().size());
58
0
            for (const auto& arg : call_expr.args()) {
59
0
              args.push_back(Copy(arg));
60
0
            }
61
0
            return target.has_value()
62
0
                       ? NewMemberCall(id, call_expr.function(),
63
0
                                       std::move(*target), std::move(args))
64
0
                       : NewCall(id, call_expr.function(), std::move(args));
65
0
          },
66
0
          [this, &expr](const ListExpr& list_expr) -> Expr {
67
0
            const auto id = CopyId(expr);
68
0
            std::vector<ListExprElement> elements;
69
0
            elements.reserve(list_expr.elements().size());
70
0
            for (const auto& element : list_expr.elements()) {
71
0
              elements.push_back(Copy(element));
72
0
            }
73
0
            return NewList(id, std::move(elements));
74
0
          },
75
0
          [this, &expr](const StructExpr& struct_expr) -> Expr {
76
0
            const auto id = CopyId(expr);
77
0
            std::vector<StructExprField> fields;
78
0
            fields.reserve(struct_expr.fields().size());
79
0
            for (const auto& field : struct_expr.fields()) {
80
0
              fields.push_back(Copy(field));
81
0
            }
82
0
            return NewStruct(id, struct_expr.name(), std::move(fields));
83
0
          },
84
0
          [this, &expr](const MapExpr& map_expr) -> Expr {
85
0
            const auto id = CopyId(expr);
86
0
            std::vector<MapExprEntry> entries;
87
0
            entries.reserve(map_expr.entries().size());
88
0
            for (const auto& entry : map_expr.entries()) {
89
0
              entries.push_back(Copy(entry));
90
0
            }
91
0
            return NewMap(id, std::move(entries));
92
0
          },
93
0
          [this, &expr](const ComprehensionExpr& comprehension_expr) -> Expr {
94
0
            const auto id = CopyId(expr);
95
0
            auto iter_range = Copy(comprehension_expr.iter_range());
96
0
            auto accu_init = Copy(comprehension_expr.accu_init());
97
0
            auto loop_condition = Copy(comprehension_expr.loop_condition());
98
0
            auto loop_step = Copy(comprehension_expr.loop_step());
99
0
            auto result = Copy(comprehension_expr.result());
100
0
            return NewComprehension(
101
0
                id, comprehension_expr.iter_var(), std::move(iter_range),
102
0
                comprehension_expr.accu_var(), std::move(accu_init),
103
0
                std::move(loop_condition), std::move(loop_step),
104
0
                std::move(result));
105
0
          }),
106
0
      expr.kind());
107
0
}
108
109
0
ListExprElement MacroExprFactory::Copy(const ListExprElement& element) {
110
0
  return NewListElement(Copy(element.expr()), element.optional());
111
0
}
112
113
0
StructExprField MacroExprFactory::Copy(const StructExprField& field) {
114
0
  auto field_id = CopyId(field.id());
115
0
  auto field_value = Copy(field.value());
116
0
  return NewStructField(field_id, field.name(), std::move(field_value),
117
0
                        field.optional());
118
0
}
119
120
0
MapExprEntry MacroExprFactory::Copy(const MapExprEntry& entry) {
121
0
  auto entry_id = CopyId(entry.id());
122
0
  auto entry_key = Copy(entry.key());
123
0
  auto entry_value = Copy(entry.value());
124
0
  return NewMapEntry(entry_id, std::move(entry_key), std::move(entry_value),
125
0
                     entry.optional());
126
0
}
127
128
}  // namespace cel