Coverage for apis_core/documentation/utils.py: 24%

51 statements  

« prev     ^ index     » next       coverage.py v7.6.4, created at 2024-11-22 07:51 +0000

1from collections import defaultdict 

2 

3from django.conf import settings 

4from django.contrib.contenttypes.models import ContentType 

5from django.utils.encoding import force_str 

6 

7from apis_core.apis_entities.utils import get_entity_content_types 

8 

9 

10class Datamodel: 

11 entities: [object] 

12 relations: [object] = [] 

13 graph: dict() = {} 

14 

15 def __init__(self): 

16 self.entities = get_entity_content_types() 

17 if "apis_core.relations" in settings.INSTALLED_APPS: 

18 from apis_core.relations.utils import relation_content_types 

19 

20 self.relations = relation_content_types() 

21 self.make_graph() 

22 

23 def edges(self): 

24 edges = defaultdict(list) 

25 if "apis_core.apis_relations" in settings.INSTALLED_APPS: 

26 from apis_core.apis_relations.models import Property 

27 

28 for prop in Property.objects.all(): 

29 for subj_class in prop.subj_class.all(): 

30 for obj_class in prop.obj_class.all(): 

31 key = ( 

32 subj_class.name, 

33 obj_class.name, 

34 ) 

35 edges[key].append(prop.name_forward) 

36 

37 for rel in self.relations: 

38 for subj_class in rel.model_class().subj_list(): 

39 for obj_class in rel.model_class().obj_list(): 

40 key = ( 

41 ContentType.objects.get_for_model(subj_class).name, 

42 ContentType.objects.get_for_model(obj_class).name, 

43 ) 

44 edges[key].append(force_str(rel.model_class().name())) 

45 return edges 

46 

47 def make_graph(self): 

48 try: 

49 from pydot import Dot, Edge, Node 

50 

51 graph = Dot(graph_type="digraph") 

52 graph.set_node_defaults(shape="record", rankdir="TB") 

53 graph.set_graph_defaults(nodesep="1", ranksep="1", TBbalance="max") 

54 for content_type in self.entities: 

55 model_class = content_type.model_class() 

56 node = Node( 

57 content_type.name, label=force_str(model_class._meta.verbose_name) 

58 ) 

59 node.set_URL(model_class.get_listview_url()) 

60 node.set_fillcolor("#3399ff") 

61 node.set_style("filled") 

62 graph.add_node(node) 

63 for (subj, obj), names in self.edges().items(): 

64 e = Edge(subj, obj, label="\n".join(names)) 

65 graph.add_edge(e) 

66 self.graph = {"svg": graph.create_svg().decode(), "dot": graph.to_string()} 

67 except ImportError as e: 

68 self.graph["error"] = str(e) 

69 except FileNotFoundError as e: 

70 self.graph["error"] = "Please install graphviz - " + str(e)