Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(404)

Side by Side Diff: third_party/WebKit/Source/bindings/scripts/code_generator_web_agent_api.py

Issue 2703653004: [WebAgentsAPI]: Start adding support for method arguments. (Closed)
Patch Set: Rebased. Created 3 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | third_party/WebKit/Source/bindings/scripts/code_generator_web_agent_api_test.py » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 # Copyright 2016 The Chromium Authors. All rights reserved. 1 # Copyright 2016 The Chromium Authors. All rights reserved.
2 # Use of this source code is governed by a BSD-style license that can be 2 # Use of this source code is governed by a BSD-style license that can be
3 # found in the LICENSE file. 3 # found in the LICENSE file.
4 4
5 # pylint: disable=import-error,print-statement,relative-import 5 # pylint: disable=import-error,print-statement,relative-import
6 6
7 """Generates Web Agent API bindings. 7 """Generates Web Agent API bindings.
8 8
9 The Web Agent API bindings provide a stable, IDL-generated interface for the 9 The Web Agent API bindings provide a stable, IDL-generated interface for the
10 Web Agents. 10 Web Agents.
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after
76 76
77 def type_from_definition(self, idl_definition): 77 def type_from_definition(self, idl_definition):
78 # TODO(dglazkov): The output of this method must be a reasonable C++ 78 # TODO(dglazkov): The output of this method must be a reasonable C++
79 # type that can be used directly in the jinja2 template. 79 # type that can be used directly in the jinja2 template.
80 return idl_definition.idl_type.base_type 80 return idl_definition.idl_type.base_type
81 81
82 def base_class_includes(self): 82 def base_class_includes(self):
83 return set(['platform/heap/Handle.h']) 83 return set(['platform/heap/Handle.h'])
84 84
85 85
86 class MethodOverloadSplitter(object):
87 """Because of union and optional types being used as arguments, some
88 operations may result in more than one generated method. This class
89 contains the logic for spliting an operation into multiple C++ overloads.
90 """
91
92 def __init__(self, idl_operation):
93 self.idl_operation = idl_operation
94
95 def _update_argument_lists(self, argument_lists, idl_types):
96 """Given a list of IdlTypes and an existing list of argument lists (yes,
97 this is a list of lists), produces a next generation of the list of
98 lists. This is the where the actual splitting into overloads happens.
haraken 2017/03/18 16:30:17 the place where
dglazkov 2017/03/20 03:25:33 Fixed. Thanks! :)
99 """
100 result = []
101 for argument_list in argument_lists:
102 for idl_type in idl_types:
103 new_argument_list = list(argument_list)
104 if idl_type is not None:
105 new_argument_list.append(idl_type)
106 result.append(new_argument_list)
107 return result
108
109 def _enumerate_argument_types(self, idl_argument):
110 """Given an IdlArgument, returns a list of types that are included
111 in this argument. If optional, the list will include a 'None'."""
112 argument_type = idl_argument.idl_type
113 # TODO(dglazkov): What should we do with primitive nullable args?
114 if (argument_type.is_nullable and
115 argument_type.inner_type.is_primitive_type):
116 raise ValueError('Primitive nullable types are not supported.')
117
118 idl_types = []
119 if idl_argument.is_optional:
120 idl_types.append(None) # None is used to convey optionality.
121 if argument_type.is_union_type:
122 idl_types = idl_types + argument_type.member_types
123 else:
124 idl_types.append(argument_type)
125 return idl_types
126
127 def split_into_overloads(self):
haraken 2017/03/18 16:30:17 It would be helpful to describe a concrete example
dglazkov 2017/03/20 03:25:33 Sure thing! I added an explanation with an example
128 argument_lists = [[]]
129 for idl_argument in self.idl_operation.arguments:
130 idl_types = self._enumerate_argument_types(idl_argument)
131 argument_lists = self._update_argument_lists(argument_lists,
132 idl_types)
133 return argument_lists
134
135
86 class InterfaceContextBuilder(object): 136 class InterfaceContextBuilder(object):
87 def __init__(self, code_generator, type_resolver): 137 def __init__(self, code_generator, type_resolver):
88 self.result = {'code_generator': code_generator} 138 self.result = {'code_generator': code_generator}
89 self.type_resolver = type_resolver 139 self.type_resolver = type_resolver
90 140
91 def set_class_name(self, class_name): 141 def set_class_name(self, class_name):
92 converter = NameStyleConverter(class_name) 142 converter = NameStyleConverter(class_name)
93 self.result['class_name'] = converter.to_all_cases() 143 self.result['class_name'] = converter.to_all_cases()
94 self._ensure_set('cpp_includes').update( 144 self._ensure_set('cpp_includes').update(
95 self.type_resolver.includes_from_interface(class_name)) 145 self.type_resolver.includes_from_interface(class_name))
(...skipping 15 matching lines...) Expand all
111 161
112 def add_attribute(self, idl_attribute): 162 def add_attribute(self, idl_attribute):
113 self._ensure_list('attributes').append( 163 self._ensure_list('attributes').append(
114 self.create_attribute(idl_attribute)) 164 self.create_attribute(idl_attribute))
115 self._ensure_set('cpp_includes').update( 165 self._ensure_set('cpp_includes').update(
116 self.type_resolver.includes_from_definition(idl_attribute)) 166 self.type_resolver.includes_from_definition(idl_attribute))
117 167
118 def add_operation(self, idl_operation): 168 def add_operation(self, idl_operation):
119 if not idl_operation.name: 169 if not idl_operation.name:
120 return 170 return
121 self._ensure_list('methods').append( 171 overload_splitter = MethodOverloadSplitter(idl_operation)
122 self.create_method(idl_operation)) 172 overloads = overload_splitter.split_into_overloads()
123 self._ensure_set('cpp_includes').update( 173 argument_names = [argument.name for argument
124 self.type_resolver.includes_from_definition(idl_operation)) 174 in idl_operation.arguments]
175 for argument_types in overloads:
176 arguments = []
177 for position, argument_type in enumerate(argument_types):
178 arguments.append(
179 self.create_argument(argument_names[position],
180 argument_type))
181 self._ensure_list('methods').append(
182 self.create_method(idl_operation, arguments))
183 self._ensure_set('cpp_includes').update(
184 self.type_resolver.includes_from_definition(idl_operation))
125 185
126 def create_method(self, idl_operation): 186 def create_argument(self, argument_name, argument_type):
127 name = idl_operation.name 187 name_converter = NameStyleConverter(argument_name)
188 return {
189 'name': name_converter.to_snake_case(),
190 'type': argument_type.base_type,
191 }
192
193 def create_method(self, idl_operation, arguments):
194 name_converter = NameStyleConverter(idl_operation.name)
128 return_type = self.type_resolver.type_from_definition(idl_operation) 195 return_type = self.type_resolver.type_from_definition(idl_operation)
129 return { 196 return {
130 'name': name, 197 'name': name_converter.to_upper_camel_case(),
131 'return_type': return_type 198 'type': return_type,
199 'arguments': arguments
132 } 200 }
133 201
134 def create_attribute(self, idl_attribute): 202 def create_attribute(self, idl_attribute):
135 name = idl_attribute.name 203 name = idl_attribute.name
136 return_type = self.type_resolver.type_from_definition(idl_attribute) 204 return_type = self.type_resolver.type_from_definition(idl_attribute)
137 return { 205 return {
138 'name': name, 206 'name': name,
139 'return_type': return_type 207 'type': return_type
140 } 208 }
141 209
142 def build(self): 210 def build(self):
143 return self.result 211 return self.result
144 212
145 213
146 class CodeGeneratorWebAgentAPI(CodeGeneratorBase): 214 class CodeGeneratorWebAgentAPI(CodeGeneratorBase):
147 def __init__(self, info_provider, cache_dir, output_dir): 215 def __init__(self, info_provider, cache_dir, output_dir):
148 CodeGeneratorBase.__init__(self, MODULE_PYNAME, info_provider, 216 CodeGeneratorBase.__init__(self, MODULE_PYNAME, info_provider,
149 cache_dir, output_dir) 217 cache_dir, output_dir)
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
181 249
182 # TODO(dglazkov): Implement dictionaries 250 # TODO(dglazkov): Implement dictionaries
183 if definition_name not in definitions.interfaces: 251 if definition_name not in definitions.interfaces:
184 return None 252 return None
185 253
186 interface = definitions.interfaces[definition_name] 254 interface = definitions.interfaces[definition_name]
187 if WEB_AGENT_API_IDL_ATTRIBUTE not in interface.extended_attributes: 255 if WEB_AGENT_API_IDL_ATTRIBUTE not in interface.extended_attributes:
188 return None 256 return None
189 257
190 return self.generate_interface_code(interface) 258 return self.generate_interface_code(interface)
OLDNEW
« no previous file with comments | « no previous file | third_party/WebKit/Source/bindings/scripts/code_generator_web_agent_api_test.py » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698