# This script is intended to take an API-style class from OpenBR and output # structured Markdown text in the OpenBR documentation format. The class details # should then be filled in. import sys import re def find_name_parent(content): name_re = re.compile('class(.*?):') name = name_re.search(content).group()[:-1].strip().split(' ')[-1] parent_re = re.compile('public.*') parent = parent_re.search(content).group().strip().split(' ')[-1] return name, parent def find_properties(content): properties = [] property_re = re.compile('Q_PROPERTY\((.*?)\)') it = property_re.finditer(content) for prop in it: prop_type = prop.group()[11:-1].split(' ')[0] prop_name = prop.group()[11:-1].split(' ')[1] properties.append((prop_name, prop_type)) return properties def find_members(content): members = [] member_re = re.compile('(\w+(<\w+>)*)\s(\w+);') it = member_re.finditer(content) for member in it: member_type = member.group()[:-1].strip().split(' ')[0] member_name = member.group()[:-1].strip().split(' ')[1] members.append((member_name, member_type)) return members def find_constructors(name, content): constructors = [] constructor_re = re.compile('(.*)' + name + '\(\)') it = constructor_re.finditer(content) for constructor in it: constructors.append(constructor.group().strip()) return constructors def find_functions(content): functions = [] function_re = re.compile('(.*)[^PROPERTY]\(.*\).*;') it = function_re.finditer(content) for func in it: function = {} function['Full'] = func.group()[:-1].strip() #don't include semi colon func_split = func.group().strip().split(' ') if func_split[0] == "static": function['Type'] = 'static' function['Return'] = func_split[1] function['Name'] = func_split[2].split('(')[0] elif func_split[0] == "virtual": function['Type'] = 'virtual' function['Return'] = func_split[1] function['Name'] = func_split[2].split('(')[0] else: function['Type'] = 'normal' function['Return'] = func_split[0] function['Name'] = func_split[1].split('(')[0] args = [] args_list = func.group()[func.group().find('(')+1:func.group().find(')')].split(',') for arg in args_list: arg = arg.strip() split_idx = arg.rfind(' ') if arg[split_idx:].strip()[0] == '*' or arg[split_idx:].strip()[0] == '&': split_idx += 2 args.append((arg[split_idx:].strip(), arg[:split_idx].strip())) function['Args'] = args functions.append(function) return functions def parse(content): name, parent = find_name_parent(content) properties = find_properties(content) members = find_members(content) constructors = find_constructors(name, content) functions = find_functions(content) return name, parent, properties, members, constructors, functions def function_builder(name, function): markdown = "" markdown += "### " + function["Full"] + " {: #" + name.lower() + "-function-" + function['Name'].lower() + "}\n\n" markdown += "DOCUMENT ME\n\n" markdown += "* **function definition:**\n\n" markdown += "\t\t" + function['Full'] + "\n\n" markdown += "* **parameters:**" if len(function['Args']) == 0: markdown += " NONE\n" else: markdown += "\n\n" markdown += "\tParameter | Type | Description\n" markdown += "\t--- | --- | ---\n" for arg in function['Args']: markdown += "\t" + arg[0] + " | " + arg[1] + " | DOCUMENT ME\n" markdown += "\n" markdown += "* **output:** (" + function['Return'] + ") DOCUMENT ME\n\n\n" return markdown def format_md(name, parent, properties, members, constructors, functions): markdown = "" markdown += "# " + name + "\n\n" markdown += "Inherits from [" + parent + "](#" + parent.lower() + ")\n\n" markdown += "## Properties {: #" + name.lower() + "-properties }\n\n" if len(properties) == 0: markdown += "NONE\n\n" else: markdown += "Property | Type | Description\n" markdown += "--- | --- | ---\n" for prop in properties: markdown += '' markdown += prop[0] + " | " + prop[1] + " | DOCUMENT ME\n" markdown += "\n" markdown += "## Members {: #" + name.lower() + "-members }\n\n" if len(members) == 0: markdown += "NONE\n\n" else: markdown += "Member | Type | Description\n" markdown += "--- | --- | ---\n" for member in members: markdown += '' markdown += member[0] + " | " + member[1] + " | DOCUMENT ME\n" markdown += "\n" markdown += "## Constructors {: #" + name.lower() + "-constructors }\n\n" if len(constructors) == 0: markdown += "NONE\n\n" else: markdown += "Constructor \| Destructor | Description\n" markdown += "--- | ---\n" for constructor in constructors: markdown += constructor + " | DOCUMENT ME\n" markdown += "\n" markdown += "## Static Functions {: #" + name.lower() + "-static-functions }\n\n" for function in functions: if function['Type'] == 'static': markdown += function_builder(name, function) markdown += "## Functions {: #" + name.lower() + "-functions }\n\n" for function in functions: if not function['Type'] == 'static': markdown += function_builder(name, function) return markdown def main(): if len(sys.argv) != 3: print 'Inputs => class documentation' sys.exit(1) class_file = open(sys.argv[1], 'r') doc_file = open(sys.argv[2], 'w+') name, parent, properties, members, constructors, functions = parse(class_file.read()) doc_file.write(format_md(name, parent, properties, members, constructors, functions)) main()