def sub_links(string,project):
LINK_TYPES    = { '<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT:type>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT:file>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>' }<EOL>SUBLINK_TYPES = { '<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT:type>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': '<STR_LIT>' }<EOL>def convert_link(match):<EOL><INDENT>ERR = '<STR_LIT>'<EOL>url = '<STR_LIT>'<EOL>name = '<STR_LIT>'<EOL>found = False<EOL>searchlist = []<EOL>item = None<EOL>if not match.group(<NUM_LIT:2>):<EOL><INDENT>for key, val in LINK_TYPES.items():<EOL><INDENT>searchlist.extend(getattr(project,val))<EOL><DEDENT><DEDENT>else:<EOL><INDENT>if match.group(<NUM_LIT:2>).lower() in LINK_TYPES:<EOL><INDENT>searchlist.extend(getattr(project,LINK_TYPES[match.group(<NUM_LIT:2>).lower()]))<EOL><DEDENT>else:<EOL><INDENT>print(ERR.format(match.group(),'<STR_LIT>'.format(match.group(<NUM_LIT:2>))))<EOL>return match.group()<EOL><DEDENT><DEDENT>for obj in searchlist:<EOL><INDENT>if match.group(<NUM_LIT:1>).lower() == obj.name.lower():<EOL><INDENT>url = obj.get_url()<EOL>name = obj.name<EOL>found = True<EOL>item = obj<EOL>break<EOL><DEDENT><DEDENT>else:<EOL><INDENT>print(ERR.format(match.group(),'<STR_LIT>'.format(match.group(<NUM_LIT:1>))))<EOL>url = '<STR_LIT>'<EOL>name = match.group(<NUM_LIT:1>)<EOL><DEDENT>if found and match.group(<NUM_LIT:3>):<EOL><INDENT>searchlist = []<EOL>if not match.group(<NUM_LIT:4>):<EOL><INDENT>for key, val in SUBLINK_TYPES.items():<EOL><INDENT>if val == '<STR_LIT>':<EOL><INDENT>if getattr(item,'<STR_LIT>', False):<EOL><INDENT>searchlist.append(item.constructor)<EOL><DEDENT>else:<EOL><INDENT>continue<EOL><DEDENT><DEDENT>else:<EOL><INDENT>searchlist.extend(getattr(item,val,[]))<EOL><DEDENT><DEDENT><DEDENT>else:<EOL><INDENT>if match.group(<NUM_LIT:4>).lower() in SUBLINK_TYPES:<EOL><INDENT>if hasattr(item,SUBLINK_TYPES[match.group(<NUM_LIT:4>).lower()]):<EOL><INDENT>if match.group(<NUM_LIT:4>).lower == '<STR_LIT>':<EOL><INDENT>if item.constructor:<EOL><INDENT>searchlist.append(item.constructor)<EOL><DEDENT><DEDENT>else:<EOL><INDENT>searchlist.extend(getattr(item,SUBLINK_TYPES[match.group(<NUM_LIT:4>).lower()]))<EOL><DEDENT><DEDENT>else:<EOL><INDENT>print(ERR.format(match.group(),'<STR_LIT>'.format(match.group(<NUM_LIT:4>),item.obj)))<EOL>return match.group()<EOL><DEDENT><DEDENT>else:<EOL><INDENT>print(ERR.format(match.group(),'<STR_LIT>'.format(match.group(<NUM_LIT:2>))))<EOL>return match.group()<EOL><DEDENT><DEDENT>for obj in searchlist:<EOL><INDENT>if match.group(<NUM_LIT:3>).lower() == obj.name.lower():<EOL><INDENT>url = url + '<STR_LIT:#>' + obj.anchor<EOL>name = obj.name<EOL>item = obj<EOL>break<EOL><DEDENT><DEDENT>else:<EOL><INDENT>print(ERR.format(match.group(),'<STR_LIT>'.format(match.group(<NUM_LIT:3>),name)))<EOL><DEDENT><DEDENT>if found:<EOL><INDENT>return '<STR_LIT>'.format(url,name)<EOL><DEDENT>else:<EOL><INDENT>return '<STR_LIT>'.format(name)<EOL><DEDENT><DEDENT>string = LINK_RE.sub(convert_link,string)<EOL>return string<EOL>
Replace links to different parts of the program, formatted as
[[name]] or [[name(object-type)]] with the appropriate URL. Can also
link to an item's entry in another's page with the syntax
[[parent-name:name]]. The object type can be placed in parentheses
for either or both of these parts.