@@ -64,139 +64,180 @@ void AppendEscaped(std::string* result, std::string_view str, bool escape_dot) {
6464 }
6565}
6666
67- absl::Status AppendTypeParameters (std::string* result, const Type& type );
67+ absl::Status AppendTypeDesc (std::string* result, const TypeSpec& type_spec );
6868
69- // Recursively appends a string representation of the given `type` to `result`.
70- // Type parameters are enclosed in angle brackets and separated by commas.
71- //
72- // Grammar:
73- // TypeDesc = NamespaceIdentifier [ "<" TypeList ">" ] ;
74- // NamespaceIdentifier = [ "." ] Identifier { "." Identifier } ;
75- // TypeList = TypeElem { "," TypeElem } ;
76- // TypeElem = TypeDesc | TypeParam
77- // TypeParam = "~" Alpha ;
78- // Identifier = ( Alpha | "_" ) { AlphaNumeric | "_" } ;
79- // (* Terminals *)
80- // Alpha = "a"..."z" | "A"..."Z" ;
81- // Digit = "0"..."9" ;
82- // AlphaNumeric = Alpha | Digit ;
83- //
84- // For compatibility, the implementation allows unexpected characters in
85- // type names and parameters and escapes them with a backslash.
86- absl::Status AppendTypeDesc (std::string* result, const Type& type) {
87- switch (type.kind ()) {
88- case TypeKind::kNull :
89- absl::StrAppend (result, " null" );
90- break ;
91- case TypeKind::kBool :
92- absl::StrAppend (result, " bool" );
93- break ;
94- case TypeKind::kInt :
95- absl::StrAppend (result, " int" );
96- break ;
97- case TypeKind::kUint :
98- absl::StrAppend (result, " uint" );
99- break ;
100- case TypeKind::kDouble :
101- absl::StrAppend (result, " double" );
102- break ;
103- case TypeKind::kString :
104- absl::StrAppend (result, " string" );
105- break ;
106- case TypeKind::kBytes :
107- absl::StrAppend (result, " bytes" );
108- break ;
109- case TypeKind::kDuration :
110- absl::StrAppend (result, " duration" );
111- break ;
112- case TypeKind::kTimestamp :
113- absl::StrAppend (result, " timestamp" );
114- break ;
115- case TypeKind::kAny :
116- absl::StrAppend (result, " any" );
117- break ;
118- case TypeKind::kDyn :
119- absl::StrAppend (result, " dyn" );
120- break ;
121- case TypeKind::kBoolWrapper :
122- absl::StrAppend (result, " bool_wrapper" );
123- break ;
124- case TypeKind::kIntWrapper :
125- absl::StrAppend (result, " int_wrapper" );
126- break ;
127- case TypeKind::kUintWrapper :
128- absl::StrAppend (result, " uint_wrapper" );
129- break ;
130- case TypeKind::kDoubleWrapper :
131- absl::StrAppend (result, " double_wrapper" );
132- break ;
133- case TypeKind::kStringWrapper :
134- absl::StrAppend (result, " string_wrapper" );
135- break ;
136- case TypeKind::kBytesWrapper :
137- absl::StrAppend (result, " bytes_wrapper" );
138- break ;
139- case TypeKind::kList :
140- absl::StrAppend (result, " list" );
141- CEL_RETURN_IF_ERROR (AppendTypeParameters (result, type));
142- break ;
143- case TypeKind::kMap :
144- absl::StrAppend (result, " map" );
145- CEL_RETURN_IF_ERROR (AppendTypeParameters (result, type));
146- break ;
147- case TypeKind::kFunction :
148- absl::StrAppend (result, " function" );
149- CEL_RETURN_IF_ERROR (AppendTypeParameters (result, type));
150- break ;
151- case TypeKind::kType :
152- absl::StrAppend (result, " type" );
153- CEL_RETURN_IF_ERROR (AppendTypeParameters (result, type));
154- break ;
155- case TypeKind::kTypeParam :
156- absl::StrAppend (result, " ~" );
157- AppendEscaped (result, type.GetTypeParam ().name (), /* escape_dot=*/ true );
158- break ;
159- case TypeKind::kOpaque :
160- AppendEscaped (result, type.name (), /* escape_dot=*/ false );
161- CEL_RETURN_IF_ERROR (AppendTypeParameters (result, type));
162- break ;
163- case TypeKind::kStruct :
164- AppendEscaped (result, type.name (), /* escape_dot=*/ false );
165- CEL_RETURN_IF_ERROR (AppendTypeParameters (result, type));
166- break ;
167- default :
168- return absl::InvalidArgumentError (
169- absl::StrFormat (" Type kind: %s is not supported in CEL declarations" ,
170- type.DebugString ()));
69+ absl::Status AppendTypeSpecList (std::string* result,
70+ const std::vector<TypeSpec>& params) {
71+ if (!params.empty ()) {
72+ result->push_back (' <' );
73+ for (size_t i = 0 ; i < params.size (); ++i) {
74+ CEL_RETURN_IF_ERROR (AppendTypeDesc (result, params[i]));
75+ if (i < params.size () - 1 ) {
76+ result->push_back (' ,' );
77+ }
78+ }
79+ result->push_back (' >' );
17180 }
17281 return absl::OkStatus ();
17382}
17483
175- absl::Status AppendTypeParameters (std::string* result, const Type& type) {
176- const auto & parameters = type.GetParameters ();
177- if (!parameters.empty ()) {
178- result->push_back (' <' );
179- for (size_t i = 0 ; i < parameters.size (); ++i) {
180- CEL_RETURN_IF_ERROR (AppendTypeDesc (result, parameters[i]));
181- if (i < parameters.size () - 1 ) {
84+ absl::Status AppendTypeDesc (std::string* result, const TypeSpec& type_spec) {
85+ if (type_spec.has_null ()) {
86+ absl::StrAppend (result, " null" );
87+ } else if (type_spec.has_dyn ()) {
88+ absl::StrAppend (result, " dyn" );
89+ } else if (type_spec.has_primitive ()) {
90+ switch (type_spec.primitive ()) {
91+ case PrimitiveType::kBool :
92+ absl::StrAppend (result, " bool" );
93+ break ;
94+ case PrimitiveType::kInt64 :
95+ absl::StrAppend (result, " int" );
96+ break ;
97+ case PrimitiveType::kUint64 :
98+ absl::StrAppend (result, " uint" );
99+ break ;
100+ case PrimitiveType::kDouble :
101+ absl::StrAppend (result, " double" );
102+ break ;
103+ case PrimitiveType::kString :
104+ absl::StrAppend (result, " string" );
105+ break ;
106+ case PrimitiveType::kBytes :
107+ absl::StrAppend (result, " bytes" );
108+ break ;
109+ default :
110+ return absl::InvalidArgumentError (" Unsupported primitive type" );
111+ }
112+ } else if (type_spec.has_well_known ()) {
113+ switch (type_spec.well_known ()) {
114+ case WellKnownTypeSpec::kAny :
115+ absl::StrAppend (result, " any" );
116+ break ;
117+ case WellKnownTypeSpec::kTimestamp :
118+ absl::StrAppend (result, " timestamp" );
119+ break ;
120+ case WellKnownTypeSpec::kDuration :
121+ absl::StrAppend (result, " duration" );
122+ break ;
123+ default :
124+ return absl::InvalidArgumentError (" Unsupported well-known type" );
125+ }
126+ } else if (type_spec.has_wrapper ()) {
127+ switch (type_spec.wrapper ()) {
128+ case PrimitiveType::kBool :
129+ absl::StrAppend (result, " bool_wrapper" );
130+ break ;
131+ case PrimitiveType::kInt64 :
132+ absl::StrAppend (result, " int_wrapper" );
133+ break ;
134+ case PrimitiveType::kUint64 :
135+ absl::StrAppend (result, " uint_wrapper" );
136+ break ;
137+ case PrimitiveType::kDouble :
138+ absl::StrAppend (result, " double_wrapper" );
139+ break ;
140+ case PrimitiveType::kString :
141+ absl::StrAppend (result, " string_wrapper" );
142+ break ;
143+ case PrimitiveType::kBytes :
144+ absl::StrAppend (result, " bytes_wrapper" );
145+ break ;
146+ default :
147+ return absl::InvalidArgumentError (" Unsupported wrapper type" );
148+ }
149+ } else if (type_spec.has_list_type ()) {
150+ absl::StrAppend (result, " list" );
151+ if (type_spec.list_type ().has_elem_type ()) {
152+ result->push_back (' <' );
153+ CEL_RETURN_IF_ERROR (
154+ AppendTypeDesc (result, type_spec.list_type ().elem_type ()));
155+ result->push_back (' >' );
156+ }
157+ } else if (type_spec.has_map_type ()) {
158+ absl::StrAppend (result, " map" );
159+ if (type_spec.map_type ().has_key_type ()) {
160+ result->push_back (' <' );
161+ CEL_RETURN_IF_ERROR (
162+ AppendTypeDesc (result, type_spec.map_type ().key_type ()));
163+ result->push_back (' ,' );
164+ if (type_spec.map_type ().has_value_type ()) {
165+ CEL_RETURN_IF_ERROR (
166+ AppendTypeDesc (result, type_spec.map_type ().value_type ()));
167+ } else {
168+ absl::StrAppend (result, " dyn" );
169+ }
170+ result->push_back (' >' );
171+ }
172+ } else if (type_spec.has_function ()) {
173+ absl::StrAppend (result, " function" );
174+ if (type_spec.function ().has_result_type () ||
175+ !type_spec.function ().arg_types ().empty ()) {
176+ result->push_back (' <' );
177+ if (type_spec.function ().has_result_type ()) {
178+ CEL_RETURN_IF_ERROR (
179+ AppendTypeDesc (result, type_spec.function ().result_type ()));
180+ } else {
181+ absl::StrAppend (result, " dyn" );
182+ }
183+ for (const auto & arg : type_spec.function ().arg_types ()) {
182184 result->push_back (' ,' );
185+ CEL_RETURN_IF_ERROR (AppendTypeDesc (result, arg));
183186 }
187+ result->push_back (' >' );
184188 }
189+ } else if (type_spec.has_type ()) {
190+ absl::StrAppend (result, " type" );
191+ result->push_back (' <' );
192+ CEL_RETURN_IF_ERROR (AppendTypeDesc (result, type_spec.type ()));
185193 result->push_back (' >' );
194+ } else if (type_spec.has_type_param ()) {
195+ absl::StrAppend (result, " ~" );
196+ AppendEscaped (result, type_spec.type_param ().type (), /* escape_dot=*/ true );
197+ } else if (type_spec.has_abstract_type ()) {
198+ AppendEscaped (result, type_spec.abstract_type ().name (),
199+ /* escape_dot=*/ false );
200+ CEL_RETURN_IF_ERROR (AppendTypeSpecList (
201+ result, type_spec.abstract_type ().parameter_types ()));
202+ } else if (type_spec.has_message_type ()) {
203+ AppendEscaped (result, type_spec.message_type ().type (),
204+ /* escape_dot=*/ false );
205+ } else {
206+ return absl::InvalidArgumentError (absl::StrCat (
207+ " Unsupported type in signature: " , FormatTypeSpec (type_spec)));
186208 }
187209 return absl::OkStatus ();
188210}
189211} // namespace
190212
191213absl::StatusOr<std::string> MakeTypeSignature (const Type& type) {
192214 std::string result;
193- CEL_RETURN_IF_ERROR (AppendTypeDesc (&result, type));
215+ CEL_ASSIGN_OR_RETURN (TypeSpec type_spec, ConvertTypeToTypeSpec (type));
216+ CEL_RETURN_IF_ERROR (AppendTypeDesc (&result, type_spec));
217+ return result;
218+ }
219+
220+ absl::StatusOr<std::string> MakeTypeSpecSignature (const TypeSpec& type_spec) {
221+ std::string result;
222+ CEL_RETURN_IF_ERROR (AppendTypeDesc (&result, type_spec));
194223 return result;
195224}
196225
197226absl::StatusOr<std::string> MakeOverloadSignature (
198227 std::string_view function_name, const std::vector<Type>& args,
199228 bool is_member) {
229+ std::vector<TypeSpec> arg_type_specs;
230+ arg_type_specs.reserve (args.size ());
231+ for (const auto & arg : args) {
232+ CEL_ASSIGN_OR_RETURN (TypeSpec type_spec, ConvertTypeToTypeSpec (arg));
233+ arg_type_specs.push_back (type_spec);
234+ }
235+ return MakeOverloadSignature (function_name, arg_type_specs, is_member);
236+ }
237+
238+ absl::StatusOr<std::string> MakeOverloadSignature (
239+ std::string_view function_name, const std::vector<TypeSpec>& args,
240+ bool is_member) {
200241 std::string result;
201242 if (is_member) {
202243 if (!args.empty ()) {
@@ -589,10 +630,14 @@ absl::StatusOr<ParsedFunctionOverload> ParseFunctionSignature(
589630 return out;
590631}
591632
633+ absl::StatusOr<TypeSpec> ParseTypeSpec (std::string_view signature) {
634+ std::string stripped_sig = StripUnescapedWhitespace (signature);
635+ return ParseTypeSignature (stripped_sig);
636+ }
637+
592638absl::StatusOr<Type> ParseType (std::string_view signature, google::protobuf::Arena* arena,
593639 const google::protobuf::DescriptorPool& pool) {
594- std::string stripped_sig = StripUnescapedWhitespace (signature);
595- CEL_ASSIGN_OR_RETURN (auto type_spec, ParseTypeSignature (stripped_sig));
640+ CEL_ASSIGN_OR_RETURN (auto type_spec, ParseTypeSpec (signature));
596641 return cel::ConvertTypeSpecToType (type_spec, arena, pool);
597642}
598643
0 commit comments