-
Notifications
You must be signed in to change notification settings - Fork 73
Expand file tree
/
Copy pathtype_checker_builder.h
More file actions
186 lines (158 loc) · 7.19 KB
/
Copy pathtype_checker_builder.h
File metadata and controls
186 lines (158 loc) · 7.19 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
// Copyright 2024 Google LLC
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// https://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef THIRD_PARTY_CEL_CPP_CHECKER_TYPE_CHECKER_BUILDER_H_
#define THIRD_PARTY_CEL_CPP_CHECKER_TYPE_CHECKER_BUILDER_H_
#include <memory>
#include <string>
#include <vector>
#include "absl/base/nullability.h"
#include "absl/functional/any_invocable.h"
#include "absl/status/status.h"
#include "absl/status/statusor.h"
#include "absl/strings/string_view.h"
#include "checker/checker_options.h"
#include "checker/type_checker.h"
#include "common/container.h"
#include "common/decl.h"
#include "common/type.h"
#include "common/type_introspector.h"
#include "google/protobuf/arena.h"
#include "google/protobuf/descriptor.h"
namespace cel {
class TypeCheckerBuilder;
// Functional implementation to apply the library features to a
// TypeCheckerBuilder.
using TypeCheckerBuilderConfigurer =
absl::AnyInvocable<absl::Status(TypeCheckerBuilder&) const>;
struct CheckerLibrary {
// Optional identifier to avoid collisions re-adding the same declarations.
// If id is empty, it is not considered.
std::string id;
TypeCheckerBuilderConfigurer configure;
};
// Represents a declaration to only use a subset of a library.
struct TypeCheckerSubset {
using FunctionPredicate = absl::AnyInvocable<bool(
absl::string_view function, const OverloadDecl& overload) const>;
// The id of the library to subset. Only one subset can be applied per
// library id.
//
// Must be non-empty.
std::string library_id;
// Predicate to apply to function overloads. If true, the overload will be
// included in the subset. If no overload for a function is included, the
// entire function is excluded.
FunctionPredicate should_include_overload;
};
// Interface for TypeCheckerBuilders.
class TypeCheckerBuilder {
public:
virtual ~TypeCheckerBuilder() = default;
// Adds a library to the TypeChecker being built.
//
// Libraries are applied in the order they are added. They effectively
// apply before any direct calls to AddVariable, AddFunction, etc.
virtual absl::Status AddLibrary(CheckerLibrary library) = 0;
// Adds a subset declaration for a library to the TypeChecker being built.
//
// At most one subset can be applied per library id.
virtual absl::Status AddLibrarySubset(TypeCheckerSubset subset) = 0;
// Adds a variable declaration that may be referenced in expressions checked
// with the resulting type checker.
virtual absl::Status AddVariable(const VariableDecl& decl) = 0;
// Adds a variable declaration that may be referenced in expressions checked
// with the resulting type checker.
//
// This version replaces any existing variable declaration with the same name.
virtual absl::Status AddOrReplaceVariable(const VariableDecl& decl) = 0;
// Declares struct type by fully qualified name as a context declaration.
//
// Context declarations are a way to declare a group of variables based on the
// definition of a struct type. Each top level field of the struct is declared
// as an individual variable of the field type.
//
// It is an error if the type contains a field that overlaps with another
// declared variable.
//
// Note: only protobuf backed struct types are supported at this time.
virtual absl::Status AddContextDeclaration(absl::string_view type) = 0;
// Declares struct type by fully qualified name as a context declaration.
//
// This version accepts a mask in terms of field selections from the
// context type. The mask specifies which fields are visible on the
// struct and its members. The visible fields for a type accumulate
// across calls. This is a lightweight way to adjust the type checking
// behavior for a group of related types.
//
// Context declarations are a way to declare a group of variables based on the
// definition of a struct type. Each top level field of the struct that is
// also the first field name in a field path is declared as an individual
// variable of the field type.
//
// It is an error if the type contains a field that overlaps with another
// declared variable. It is an error if the input field paths is the empty
// set.
//
// Note: only protobuf backed struct types are supported at this time.
virtual absl::Status AddContextDeclarationWithProtoTypeMask(
absl::string_view type, std::vector<std::string> field_paths) = 0;
// Adds a function declaration that may be referenced in expressions checked
// with the resulting TypeChecker.
virtual absl::Status AddFunction(const FunctionDecl& decl) = 0;
// Adds function declaration overloads to the TypeChecker being built.
//
// Attempts to merge with any existing overloads for a function decl with the
// same name. If the overloads are not compatible, an error is returned and
// no change is made.
virtual absl::Status MergeFunction(const FunctionDecl& decl) = 0;
// Sets the expected type for checked expressions.
//
// Validation will fail with an ERROR level issue if the deduced type of the
// expression is not assignable to this type.
//
// Note: if set multiple times, the last value is used.
virtual void SetExpectedType(const Type& type) = 0;
// Adds a type provider to the TypeChecker being built.
//
// Type providers are used to describe custom types with typed field
// traversal. This is not needed for built-in types or protobuf messages
// described by the associated descriptor pool.
virtual void AddTypeProvider(std::unique_ptr<TypeIntrospector> provider) = 0;
// Set the container for the TypeChecker being built.
//
// This is used for resolving references in the expressions being built.
//
// Prefer setting the container via SetExpressionContainer().
//
// Note: if set multiple times, the last value is used. This can lead to
// surprising behavior if used in a custom library. If container is not a
// valid container name, the operation is ignored.
virtual void set_container(absl::string_view container) = 0;
virtual void SetExpressionContainer(
ExpressionContainer expression_container) = 0;
// The current options for the TypeChecker being built.
virtual const CheckerOptions& options() const = 0;
// Builds a new TypeChecker instance.
virtual absl::StatusOr<std::unique_ptr<TypeChecker>> Build() = 0;
// Returns a pointer to an arena that can be used to allocate memory for types
// that will be used by the TypeChecker being built.
//
// On Build(), the arena is transferred to the TypeChecker being built.
virtual google::protobuf::Arena* absl_nonnull arena() = 0;
// The configured descriptor pool.
virtual const google::protobuf::DescriptorPool* absl_nonnull descriptor_pool()
const = 0;
};
} // namespace cel
#endif // THIRD_PARTY_CEL_CPP_CHECKER_TYPE_CHECKER_BUILDER_H_