| Index: bindings/scripts/collect_idls_into_json.py
|
| diff --git a/bindings/scripts/collect_idls_into_json.py b/bindings/scripts/collect_idls_into_json.py
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..a03026f78fb677f491f142d819c17ca8bd618a5a
|
| --- /dev/null
|
| +++ b/bindings/scripts/collect_idls_into_json.py
|
| @@ -0,0 +1,432 @@
|
| +#!/usr/bin/env python
|
| +# Copyright 2015 The Chromium Authors. All rights reserved.
|
| +# Use of this source code is governed by a BSD-style license that can be
|
| +# found in the LICENSE file.
|
| +
|
| +"""Usage: collect_idls_into_json.py path_file.txt json_file.json
|
| +This script collects and organizes interface information and that information dumps into json file.
|
| +"""
|
| +
|
| +import json
|
| +import os
|
| +import sys
|
| +import utilities
|
| +
|
| +
|
| +from blink_idl_parser import parse_file, BlinkIDLParser
|
| +
|
| +_INTERFACE = 'Interface'
|
| +_IMPLEMENT = 'Implements'
|
| +_PARTIAL = 'Partial'
|
| +_NAME = 'Name'
|
| +_TYPE = 'Type'
|
| +_UNIONTYPE = 'UnionType'
|
| +_ARRAY = 'Array'
|
| +_ANY = 'Any'
|
| +_SEQUENCE = 'Sequence'
|
| +_PROP_VALUE = 'VALUE'
|
| +_VALUE = 'Value'
|
| +_PARENT = 'Parent'
|
| +_FILEPATH = 'FilePath'
|
| +_PROP_FILENAME = 'FILENAME'
|
| +_PROP_READONLY = 'READONLY'
|
| +_READONLY = 'Readonly'
|
| +_PROP_STATIC = 'STATIC'
|
| +_STATIC = 'Static'
|
| +_CONSTS = 'Consts'
|
| +_CONST = 'Const'
|
| +_ATTRIBUTES = 'Attributes'
|
| +_ATTRIBUTE = 'Attribute'
|
| +_OPERATIONS = 'Operations'
|
| +_OPERATION = 'Operation'
|
| +_PROP_GETTER = 'GETTER'
|
| +_NAMED_GETTER = '__getter__'
|
| +_PROP_SETTER = 'SETTER'
|
| +_NAMED_SETTER = '__setter__'
|
| +_PROP_DELETER = 'DELETER'
|
| +_NAMED_DELETER = '__deleter__'
|
| +_ARGUMENTS = 'Arguments'
|
| +_ARGUMENT = 'Argument'
|
| +_EXTATTRIBUTES = 'ExtAttributes'
|
| +_EXTATTRIBUTE = 'ExtAttribute'
|
| +_INHERIT = 'Inherit'
|
| +_PROP_REFERENCE = 'REFERENCE'
|
| +_PARTIAL_FILEPATH = 'Partial_FilePaths'
|
| +_MEMBERS = [_CONSTS, _ATTRIBUTES, _OPERATIONS]
|
| +
|
| +
|
| +def get_definitions(paths):
|
| + """Returns a generator of IDL node.
|
| + Args:
|
| + paths: list of IDL file path
|
| + Returns:
|
| + a generator which yields IDL node objects
|
| + """
|
| + parser = BlinkIDLParser()
|
| + for path in paths:
|
| + definitions = parse_file(parser, path)
|
| + for definition in definitions.GetChildren():
|
| + yield definition
|
| +
|
| +
|
| +def is_implements(definition):
|
| + """Returns True if class of |definition| is Implements, otherwise False.
|
| + Args:
|
| + definition: IDL node
|
| + Returns:
|
| + True if class of |definition| is Implements, otherwise False.
|
| + """
|
| + return definition.GetClass() == _IMPLEMENT
|
| +
|
| +
|
| +def is_partial(definition):
|
| + """Returns True if |definition| is 'partial interface' class, otherwise False.
|
| + Args:
|
| + definition: IDL node
|
| + Return:
|
| + True if |definition| is 'partial interface' class, otherwise False.
|
| + """
|
| + return definition.GetClass() == _INTERFACE and definition.GetProperty(_PARTIAL)
|
| +
|
| +
|
| +def get_filepath(interface_node):
|
| + """Returns relative path to the IDL in which |interface_node| is defined.
|
| + Args:
|
| + interface_node: IDL interface
|
| + Returns:
|
| + str which is |interface_node|'s file path
|
| + """
|
| + filename = interface_node.GetProperty(_PROP_FILENAME)
|
| + return os.path.relpath(filename)
|
| +
|
| +
|
| +def get_const_node_list(interface_node):
|
| + """Returns a list of Const node.
|
| + Args:
|
| + interface_node: interface node
|
| + Returns:
|
| + A list of const node
|
| + """
|
| + return interface_node.GetListOf(_CONST)
|
| +
|
| +
|
| +def get_const_type(const_node):
|
| + """Returns const's type.
|
| + Args:
|
| + const_node: const node
|
| + Returns:
|
| + str which is constant type.
|
| + """
|
| + return const_node.GetChildren()[0].GetName()
|
| +
|
| +
|
| +def get_const_value(const_node):
|
| + """Returns const's value.
|
| + This function only supports primitive types.
|
| +
|
| + Args:
|
| + const_node: const node
|
| + Returns:
|
| + str which is name of constant's value.
|
| + """
|
| + if const_node.GetChildren()[1].GetName():
|
| + return const_node.GetChildren()[1].GetName()
|
| + else:
|
| + for const_child in const_node.GetChildren():
|
| + if const_child.GetClass() == _VALUE and not const_child.GetName():
|
| + return const_child.GetProperty(_PROP_VALUE)
|
| + raise Exception('Constant value is empty')
|
| +
|
| +
|
| +def const_node_to_dict(const_node):
|
| + """Returns dictionary of const's information.
|
| + Args:
|
| + const_node: const node
|
| + Returns:
|
| + dictionary of const's information
|
| + """
|
| + return {
|
| + _NAME: const_node.GetName(),
|
| + _TYPE: get_const_type(const_node),
|
| + _VALUE: get_const_value(const_node),
|
| + _EXTATTRIBUTES: [extattr_node_to_dict(extattr) for extattr in get_extattribute_node_list(const_node)],
|
| + }
|
| +
|
| +
|
| +def get_attribute_node_list(interface_node):
|
| + """Returns list of Attribute if the interface have one.
|
| + Args:
|
| + interface_node: interface node
|
| + Returns:
|
| + list of attribute node
|
| + """
|
| + return interface_node.GetListOf(_ATTRIBUTE)
|
| +
|
| +
|
| +def get_attribute_type(attribute_node):
|
| + """Returns type of attribute.
|
| + Args:
|
| + attribute_node: attribute node
|
| + Returns:
|
| + name of attribute's type
|
| + """
|
| + attr_type = attribute_node.GetOneOf(_TYPE).GetChildren()[0]
|
| + type_list = []
|
| + if attr_type.GetClass() == _UNIONTYPE:
|
| + union_member_list = attr_type.GetListOf(_TYPE)
|
| + for union_member in union_member_list:
|
| + for type_component in union_member.GetChildren():
|
| + if type_component.GetClass() == _ARRAY:
|
| + type_list[-1] += '[]'
|
| + elif type_component.GetClass() == _SEQUENCE:
|
| + for seq_type in type_component.GetOneOf(_TYPE).GetChildren():
|
| + type_list.append('<' + seq_type.GetName() + '>')
|
| + else:
|
| + type_list.append(type_component.GetName())
|
| + return type_list
|
| + elif attr_type.GetClass() == _SEQUENCE:
|
| + union_member_types = []
|
| + if attr_type.GetOneOf(_TYPE).GetChildren()[0].GetClass() == _UNIONTYPE:
|
| + for union_member in attr_type.GetOneOf(_TYPE).GetOneOf(_UNIONTYPE).GetListOf(_TYPE):
|
| + if len(union_member.GetChildren()) != 1:
|
| + raise Exception('Complex type in a union in a sequence is not yet supported')
|
| + type_component = union_member.GetChildren()[0]
|
| + union_member_types.append(type_component.GetName())
|
| + return '<' + str(union_member_types) + '>'
|
| + else:
|
| + for type_component in attr_type.GetOneOf(_TYPE).GetChildren():
|
| + if type_component.GetClass() == _SEQUENCE:
|
| + raise Exception('Sequence in another sequence is not yet supported')
|
| + else:
|
| + if type_component.GetClass() == _ARRAY:
|
| + type_list[-1] += []
|
| + else:
|
| + type_list.append(type_component.GetName())
|
| + return '<' + type_list[0] + '>'
|
| + elif attr_type.GetClass() == _ANY:
|
| + return _ANY
|
| + else:
|
| + for type_component in attribute_node.GetOneOf(_TYPE).GetChildren():
|
| + if type_component.GetClass() == _ARRAY:
|
| + type_list[-1] += '[]'
|
| + else:
|
| + type_list.append(type_component.GetName())
|
| + return type_list[0]
|
| +
|
| +
|
| +get_operation_type = get_attribute_type
|
| +get_argument_type = get_attribute_type
|
| +
|
| +
|
| +def attribute_node_to_dict(attribute_node):
|
| + """Returns dictioary of attribute's information.
|
| + Args:
|
| + attribute_node: attribute node
|
| + Returns:
|
| + dictionary of attribute's information
|
| + """
|
| + return {
|
| + _NAME: attribute_node.GetName(),
|
| + _TYPE: get_attribute_type(attribute_node),
|
| + _EXTATTRIBUTES: [extattr_node_to_dict(extattr) for extattr in get_extattribute_node_list(attribute_node)],
|
| + _READONLY: attribute_node.GetProperty(_PROP_READONLY, default=False),
|
| + _STATIC: attribute_node.GetProperty(_PROP_STATIC, default=False),
|
| + }
|
| +
|
| +
|
| +def get_operation_node_list(interface_node):
|
| + """Returns operations node list.
|
| + Args:
|
| + interface_node: interface node
|
| + Returns:
|
| + list of oparation node
|
| + """
|
| + return interface_node.GetListOf(_OPERATION)
|
| +
|
| +
|
| +def get_argument_node_list(operation_node):
|
| + """Returns list of argument.
|
| + Args:
|
| + operation_node: operation node
|
| + Returns:
|
| + list of argument node
|
| + """
|
| + return operation_node.GetOneOf(_ARGUMENTS).GetListOf(_ARGUMENT)
|
| +
|
| +
|
| +def argument_node_to_dict(argument_node):
|
| + """Returns dictionary of argument's information.
|
| + Args:
|
| + argument_node: argument node
|
| + Returns:
|
| + dictionary of argument's information
|
| + """
|
| + return {
|
| + _NAME: argument_node.GetName(),
|
| + _TYPE: get_argument_type(argument_node),
|
| + }
|
| +
|
| +
|
| +def get_operation_name(operation_node):
|
| + """Returns openration's name.
|
| + Args:
|
| + operation_node: operation node
|
| + Returns:
|
| + name of operation
|
| + """
|
| + if operation_node.GetProperty(_PROP_GETTER):
|
| + return _NAMED_GETTER
|
| + elif operation_node.GetProperty(_PROP_SETTER):
|
| + return _NAMED_SETTER
|
| + elif operation_node.GetProperty(_PROP_DELETER):
|
| + return _NAMED_DELETER
|
| + else:
|
| + return operation_node.GetName()
|
| +
|
| +
|
| +def operation_node_to_dict(operation_node):
|
| + """Returns dictionary of operation's information.
|
| + Args:
|
| + operation_node: operation node
|
| + Returns:
|
| + dictionary of operation's informantion
|
| + """
|
| + return {
|
| + _NAME: get_operation_name(operation_node),
|
| + _ARGUMENTS: [argument_node_to_dict(argument) for argument in get_argument_node_list(operation_node) if argument_node_to_dict(argument)],
|
| + _TYPE: get_operation_type(operation_node),
|
| + _EXTATTRIBUTES: [extattr_node_to_dict(extattr) for extattr in get_extattribute_node_list(operation_node)],
|
| + _STATIC: operation_node.GetProperty(_PROP_STATIC, default=False),
|
| + }
|
| +
|
| +
|
| +def get_extattribute_node_list(node):
|
| + """Returns list of ExtAttribute.
|
| + Args:
|
| + node: IDL node
|
| + Returns:
|
| + list of ExtAttrbute
|
| + """
|
| + if node.GetOneOf(_EXTATTRIBUTES):
|
| + return node.GetOneOf(_EXTATTRIBUTES).GetListOf(_EXTATTRIBUTE)
|
| + else:
|
| + return []
|
| +
|
| +
|
| +def extattr_node_to_dict(extattr):
|
| + """Returns dictionary of ExtAttribute's information.
|
| + Args:
|
| + extattr: ExtAttribute node
|
| + Returns:
|
| + dictionary of ExtAttribute's information
|
| + """
|
| + return {
|
| + _NAME: extattr.GetName(),
|
| + }
|
| +
|
| +
|
| +def inherit_node_to_dict(interface_node):
|
| + """Returns a dictionary of inheritance information.
|
| + Args:
|
| + interface_node: interface node
|
| + Returns:
|
| + A dictioanry of inheritance information.
|
| + """
|
| + inherit = interface_node.GetOneOf(_INHERIT)
|
| + if inherit:
|
| + return {_PARENT: inherit.GetName()}
|
| + else:
|
| + return {_PARENT: None}
|
| +
|
| +
|
| +def interface_node_to_dict(interface_node):
|
| + """Returns a dictioary of interface information.
|
| + Args:
|
| + interface_node: interface node
|
| + Returns:
|
| + A dictionary of the interface information.
|
| + """
|
| + return {
|
| + _NAME: interface_node.GetName(),
|
| + _FILEPATH: get_filepath(interface_node),
|
| + _CONSTS: [const_node_to_dict(const) for const in get_const_node_list(interface_node)],
|
| + _ATTRIBUTES: [attribute_node_to_dict(attr) for attr in get_attribute_node_list(interface_node) if attr],
|
| + _OPERATIONS: [operation_node_to_dict(operation) for operation in get_operation_node_list(interface_node) if operation],
|
| + _EXTATTRIBUTES: [extattr_node_to_dict(extattr) for extattr in get_extattribute_node_list(interface_node)],
|
| + _INHERIT: inherit_node_to_dict(interface_node)
|
| + }
|
| +
|
| +
|
| +def merge_partial_dicts(interfaces_dict, partials_dict):
|
| + """Merges partial interface into non-partial interface.
|
| + Args:
|
| + interfaces_dict: A dict of the non-partial interfaces.
|
| + partial_dict: A dict of partial interfaces.
|
| + Returns:
|
| + A merged dictionary of |interface_dict| with |partial_dict|.
|
| + """
|
| + for interface_name, partial in partials_dict.iteritems():
|
| + interface = interfaces_dict.get(interface_name)
|
| + if not interface:
|
| + raise Exception('There is a partial interface, but the corresponding non-partial interface was not found.')
|
| + for member in _MEMBERS:
|
| + interface[member].extend(partial.get(member))
|
| + interface.setdefault(_PARTIAL_FILEPATH, []).append(partial[_FILEPATH])
|
| + return interfaces_dict
|
| +
|
| +
|
| +def merge_implement_nodes(interfaces_dict, implement_node_list):
|
| + """Combines a dict of interface information with referenced interface information.
|
| + Args:
|
| + interfaces_dict: dict of interface information
|
| + implement_nodes: list of implemented interface node
|
| + Returns:
|
| + A dict of interface information combined with implements nodes.
|
| + """
|
| + for implement in implement_node_list:
|
| + reference = implement.GetProperty(_PROP_REFERENCE)
|
| + implement = implement.GetName()
|
| + if reference not in interfaces_dict.keys() or implement not in interfaces_dict.keys():
|
| + raise Exception('There is not corresponding implement or reference interface.')
|
| + for member in _MEMBERS:
|
| + interfaces_dict[implement][member].extend(interfaces_dict[reference].get(member))
|
| + return interfaces_dict
|
| +
|
| +
|
| +def export_to_jsonfile(dictionary, json_file):
|
| + """Writes a Python dict into a JSON file.
|
| + Args:
|
| + dictioary: interface dictionary
|
| + json_file: json file for output
|
| + """
|
| + with open(json_file, 'w') as f:
|
| + json.dump(dictionary, f, sort_keys=True)
|
| +
|
| +
|
| +def usage():
|
| + sys.stdout.write('Usage: collect_idls_into_json.py <path_file.txt> <output_file.json>\n')
|
| +
|
| +
|
| +def main(args):
|
| + if len(args) != 2:
|
| + usage()
|
| + exit(1)
|
| + path_file = args[0]
|
| + json_file = args[1]
|
| + path_list = utilities.read_file_to_list(path_file)
|
| + implement_node_list = [definition
|
| + for definition in get_definitions(path_list)
|
| + if is_implements(definition)]
|
| + interfaces_dict = {definition.GetName(): interface_node_to_dict(definition)
|
| + for definition in get_definitions(path_list)
|
| + if not is_partial(definition)}
|
| + partials_dict = {definition.GetName(): interface_node_to_dict(definition)
|
| + for definition in get_definitions(path_list)
|
| + if is_partial(definition)}
|
| + dictionary = merge_partial_dicts(interfaces_dict, partials_dict)
|
| + interfaces_dict = merge_implement_nodes(interfaces_dict, implement_node_list)
|
| + export_to_jsonfile(dictionary, json_file)
|
| +
|
| +
|
| +if __name__ == '__main__':
|
| + main(sys.argv[1:])
|
|
|