#!/usr/bin/python3 # coding=utf-8 #FLOWchart GRa(F) generation # The person who associated a work with this deed has dedicated # the work to the public domain by waiving all of his or her rights # to the work worldwide under copyright law, including all related # and neighboring rights, to the extent allowed by law. # You can copy, modify, distribute and perform the work, even for # commercial purposes, all without asking permission. # In no way are the patent or trademark rights of any person affected by # CC0, nor are the rights that other persons may have in the work or in # how the work is used, such as publicity or privacy rights. # Unless expressly stated otherwise, the person who associated a work with # this deed makes no warranties about the work, and disclaims liability # for all uses of the work, to the fullest extent permitted by applicable law. # When using or citing the work, you should not imply endorsement by the # author or the affirmer. # https://creativecommons.org/publicdomain/zero/1.0/ import re import os import sys import time import codecs import pprint import collections from watchdog.observers import Observer from watchdog.events import FileSystemEventHandler from pathlib import Path diaghead='digraph {\ncharset=\"utf-8\";' diaghead+='overlap=\"false\";\n' diaghead+='splines=\"true\";\n' diaghead+='sep=\"+10\";\n' hd='' home = str(Path.home())+'/sync' out=home+'/websites/site/'+sys.argv[1]+'/graph/' rootdfd=home+'/websites/source/'+sys.argv[1]+'/' version='' def rendergv(path): fil=path.replace('/','.') os.system("dot -Tsvg '"+out+fil+".gv' -o '"+out+fil+".svg'") os.system("inkscape '"+out+fil+".svg' -l '"+out+fil+".svg'") os.system("inkscape '"+out+fil+".svg' -e '"+out+fil+".png'") fff = codecs.open(out+fil+'.svg', mode='r', encoding='utf-8') rawsvg=fff.read().replace('','
') rawsvg=rawsvg.replace('fill="#012312"','fill="currentColor"\nstroke="currentColor"') rawsvg=rawsvg.replace('xmlns:dc="http://purl.org/dc/elements/1.1/"\n','') rawsvg=rawsvg.replace('xmlns:cc="http://creativecommons.org/ns#"\n','') rawsvg=rawsvg.replace('xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"\n','') rawsvg=rawsvg.replace('xmlns:svg="http://www.w3.org/2000/svg"\n','') rawsvg=rawsvg.replace('xmlns:xlink="http://www.w3.org/1999/xlink"\n','') rawsvg=rawsvg.replace('','',rawsvg,flags=re.DOTALL) fff.close rawsvg2=rawsvg.replace('
','') fff = codecs.open(out+fil+'.e.svg', mode='w', encoding='utf-8') fff.write(rawsvg2) fff.close header="" try: numlev=level[level.rfind('/')+1:] numrest=level[:level.rfind('/')] headingraw=rootdfd+numrest+'/'+numlev+'.title.txt' with open(headingraw,'r') as hdraw: headr=hdraw.read() heading=headr.replace('\n',' ') except: header='' with open(rootdfd+'title.txt','r') as hdraw: headr=hdraw.read() heading=headr.replace('\n',' ') f = codecs.open(out+fil+'.txt', mode='w', encoding='utf-8') tp='
'+header+'
'+heading+'
' tp+='
'+header+'
'+heading+'
' f.write(tp+rawsvg) f.close def createflow(path): labels={} global hd graph=[] for root,dirs,files in os.walk(rootdfd+path+'/', followlinks=False): for fname in files: if not fname.startswith('.') and fname[-11:]!='details.txt' and fname.find('^^')==-1 and fname.find('_has_specified')==-1 and fname.find('_component_destination')==-1: p=os.path.join(root,fname) bits=re.compile(re.escape(rootdfd+path+'/')+r'(.+)/(has_flow_destination)/(.+)') try: m = bits.match(p) subject=m.group(1) predicate=m.group(2) objctraw=m.group(3) ttl=objctraw.find('title.txt') if ttl==-1: objct=objctraw[:-4] objctp=objctraw else: objct=objctraw[:ttl-1] objctp=objctraw lbl='' lblline='' print('pth: '+rootdfd+path+'/'+subject+'/'+predicate+'/'+objct+'.details.txt') if os.path.isfile(rootdfd+path+'/'+subject+'/'+predicate+'/'+objct+'.details.txt'): with open(rootdfd+path+'/'+subject+'/'+predicate+'/'+objct+'.details.txt','r') as linelbl: lblline=linelbl.read().replace('\n',' ') print('fn: '+lblline) else: lblline='' graph.append('"'+subject+'" -> "'+objct+'" [fontname=monospace label="\u2007'+lblline+'\u2007"];') lbls='' with open(rootdfd+path+'/'+subject+'.txt','r') as label: for line in label: lbls+=line.rstrip()+r'\n' with open(rootdfd+path+'/'+objct+'.txt','r') as label: for line in label: lbl+=line.rstrip()+r'\n' if subject[0]=='T': labels[subject]='"'+subject+'" [shape="box" fontname=monospace margin=0.15 style=rounded label="'+lbls+'" ];' if objct[0]=='T': labels[objct]='"'+objct+'" [shape="box" fontname=monospace margin=0.15 style=rounded label="'+lbl+'" ];' if objct[0]=='P': labels[objct]='"'+objct+'" [shape="box" fontname=monospace margin=0.15 label="'+lbl+'" ];' if subject[0]=='P': labels[subject]='"'+subject+'" [shape="box" fontname=monospace margin=0.15 label="'+lbls+'" ];' if objct[0]=='D': labels[objct]='"'+objct+'" [shape="diamond" fontname=monospace margin=0.15 style="" label="'+lbl+'" ];' if subject[0]=='D': labels[subject]='"'+subject+'" [shape="diamond" fontname=monospace margin=0.15 style="" label="'+lbls+'" ];' lbl='' with open(rootdfd+path+'/'+subject+'.title.txt','r') as label: for line in label: lbl+=line.rstrip()+r'\n' try: with open(rootdfd+path+'/'+subject+'.details.txt','r') as linelbl: lblline=linelbl.read().replace('\n',' ') lbllinel='*' except: lblline='' lbllinel='' end=('tooltip="'+lblline+'"];') labels[subject]='"'+subject+'" [fontname=monospace fontcolor="#000000" label="{ '+lbllinel+' '+subject+'| '+lbl+'\n\n\n}" shape=Mrecord '+end except: six=9 alll='' for line in labels: alll+=labels[line]+'\n' for line in graph: alll+=line+'\n' with open(out+path.replace('/','.')+'.gv', 'w+') as fa: fa.write(diaghead+alll+'}'+'\n') rendergv(path) def update(evt): print(evt) proc='' hass=evt.find('/has_flow') if hass !=-1: subject=evt[:hass].rfind('/') createflow(evt[len(rootdfd):subject]) class changes(FileSystemEventHandler): def on_modified(self, event): update(event.src_path) def on_created(self, event): update(event.src_path) if __name__ == "__main__": event_handler = changes() observer = Observer() observer.schedule(event_handler, rootdfd, recursive=True) observer.start() try: while True: time.sleep(1) except KeyboardInterrupt: observer.stop() observer.join()