prolog-trace-viz 1.1.2 → 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (46) hide show
  1. package/README.md +43 -30
  2. package/dist/analyzer.d.ts.map +1 -1
  3. package/dist/analyzer.js +268 -96
  4. package/dist/analyzer.js.map +1 -1
  5. package/dist/build-info.d.ts +3 -3
  6. package/dist/build-info.js +3 -3
  7. package/dist/clauses.d.ts +11 -0
  8. package/dist/clauses.d.ts.map +1 -1
  9. package/dist/clauses.js +12 -0
  10. package/dist/clauses.js.map +1 -1
  11. package/dist/cli.d.ts +4 -6
  12. package/dist/cli.d.ts.map +1 -1
  13. package/dist/cli.js +2 -25
  14. package/dist/cli.js.map +1 -1
  15. package/dist/index.js +80 -22
  16. package/dist/index.js.map +1 -1
  17. package/dist/markdown-generator.d.ts +24 -0
  18. package/dist/markdown-generator.d.ts.map +1 -0
  19. package/dist/markdown-generator.js +124 -0
  20. package/dist/markdown-generator.js.map +1 -0
  21. package/dist/parser.d.ts +12 -1
  22. package/dist/parser.d.ts.map +1 -1
  23. package/dist/parser.js +67 -35
  24. package/dist/parser.js.map +1 -1
  25. package/dist/timeline-formatter.d.ts +9 -0
  26. package/dist/timeline-formatter.d.ts.map +1 -0
  27. package/dist/timeline-formatter.js +149 -0
  28. package/dist/timeline-formatter.js.map +1 -0
  29. package/dist/timeline.d.ts +148 -0
  30. package/dist/timeline.d.ts.map +1 -0
  31. package/dist/timeline.js +601 -0
  32. package/dist/timeline.js.map +1 -0
  33. package/dist/tree-formatter.d.ts +13 -0
  34. package/dist/tree-formatter.d.ts.map +1 -0
  35. package/dist/tree-formatter.js +136 -0
  36. package/dist/tree-formatter.js.map +1 -0
  37. package/dist/tree.d.ts +75 -0
  38. package/dist/tree.d.ts.map +1 -0
  39. package/dist/tree.js +267 -0
  40. package/dist/tree.js.map +1 -0
  41. package/dist/wrapper.d.ts +8 -1
  42. package/dist/wrapper.d.ts.map +1 -1
  43. package/dist/wrapper.js +41 -17
  44. package/dist/wrapper.js.map +1 -1
  45. package/package.json +1 -1
  46. package/tracer.pl +127 -16
package/tracer.pl CHANGED
@@ -3,10 +3,17 @@
3
3
 
4
4
  :- dynamic trace_event/1.
5
5
  :- dynamic trace_active/0.
6
+ :- dynamic max_trace_depth/1.
6
7
 
7
8
  %% install_tracer/0
8
- % Install the trace interception hook
9
+ % Install the trace interception hook with default depth
9
10
  install_tracer :-
11
+ install_tracer(100).
12
+
13
+ %% install_tracer/1
14
+ % Install the trace interception hook with specified max depth
15
+ install_tracer(MaxDepth) :-
16
+ asserta(max_trace_depth(MaxDepth)),
10
17
  asserta(trace_active),
11
18
  trace.
12
19
 
@@ -15,6 +22,7 @@ install_tracer :-
15
22
  remove_tracer :-
16
23
  notrace,
17
24
  retractall(trace_active),
25
+ retractall(max_trace_depth(_)),
18
26
  clear_trace.
19
27
 
20
28
  %% clear_trace/0
@@ -26,14 +34,47 @@ clear_trace :-
26
34
  % Hook predicate that intercepts trace events
27
35
  user:prolog_trace_interception(Port, Frame, _Choice, continue) :-
28
36
  trace_active,
37
+ % Check depth limit
38
+ prolog_frame_attribute(Frame, level, Level),
39
+ max_trace_depth(MaxDepth),
40
+ Level =< MaxDepth,
41
+ % Don't trace our own operations
42
+ prolog_frame_attribute(Frame, goal, Goal),
43
+ \+ is_tracer_goal(Goal),
29
44
  !,
30
45
  catch(
31
46
  capture_trace_event(Port, Frame),
32
47
  Error,
33
48
  handle_trace_error(Error, Port, Frame)
34
49
  ).
50
+ user:prolog_trace_interception(Port, Frame, _Choice, continue) :-
51
+ trace_active,
52
+ % Exceeded depth limit - record truncation marker once
53
+ prolog_frame_attribute(Frame, level, Level),
54
+ max_trace_depth(MaxDepth),
55
+ Level > MaxDepth,
56
+ \+ trace_event(truncated(MaxDepth)),
57
+ !,
58
+ assertz(trace_event(truncated(MaxDepth))).
35
59
  user:prolog_trace_interception(_, _, _, continue).
36
60
 
61
+ %% is_tracer_goal(+Goal)
62
+ % Check if a goal is part of the tracer infrastructure
63
+ is_tracer_goal(Goal) :-
64
+ functor(Goal, Functor, _),
65
+ tracer_predicate(Functor).
66
+
67
+ tracer_predicate(trace_event).
68
+ tracer_predicate(call_goal).
69
+ tracer_predicate(assertz).
70
+ tracer_predicate(retract).
71
+ tracer_predicate(retractall).
72
+ tracer_predicate(findall).
73
+ tracer_predicate(format).
74
+ tracer_predicate(write).
75
+ tracer_predicate(open).
76
+ tracer_predicate(close).
77
+
37
78
  %% handle_trace_error(+Error, +Port, +Frame)
38
79
  % Handle errors during trace event capture
39
80
  handle_trace_error(Error, Port, Frame) :-
@@ -61,11 +102,14 @@ capture_trace_event(Port, Frame) :-
61
102
  ; Arguments = []
62
103
  ),
63
104
 
64
- % Extract clause information
65
- extract_clause_info(Frame, Goal, ClauseInfo),
105
+ % Extract clause information with enhanced data
106
+ extract_clause_info_enhanced(Frame, Goal, Port, ClauseInfo),
66
107
 
67
- % Record the event
68
- assertz(trace_event(event(Port, Level, Goal, Arguments, ClauseInfo, Predicate))).
108
+ % Extract parent information
109
+ extract_parent_info(Frame, ParentInfo),
110
+
111
+ % Record the event with enhanced information
112
+ assertz(trace_event(event(Port, Level, Goal, Arguments, ClauseInfo, Predicate, ParentInfo))).
69
113
 
70
114
  %% extract_frame_arguments(+Frame, +Arity, -Arguments)
71
115
  % Extract actual argument values from a frame
@@ -94,6 +138,27 @@ extract_clause_info(Frame, Goal, clause(Head, Body, Line)) :-
94
138
  !.
95
139
  extract_clause_info(_, _, no_clause).
96
140
 
141
+ %% extract_clause_info_enhanced(+Frame, +Goal, +Port, -ClauseInfo)
142
+ % Extract clause information - keep it simple, TypeScript will handle variable names
143
+ extract_clause_info_enhanced(Frame, Goal, _, ClauseInfo) :-
144
+ extract_clause_info(Frame, Goal, ClauseInfo).
145
+
146
+ %% extract_parent_info(+Frame, -ParentInfo)
147
+ % Extract information about the parent frame
148
+ extract_parent_info(Frame, parent(ParentLevel, ParentGoal)) :-
149
+ catch(
150
+ (
151
+ prolog_frame_attribute(Frame, parent, ParentFrame),
152
+ ParentFrame \= 0,
153
+ prolog_frame_attribute(ParentFrame, level, ParentLevel),
154
+ prolog_frame_attribute(ParentFrame, goal, ParentGoal)
155
+ ),
156
+ _,
157
+ fail
158
+ ),
159
+ !.
160
+ extract_parent_info(_, no_parent).
161
+
97
162
  %% export_trace_json(+File)
98
163
  % Export all trace events as JSON
99
164
  export_trace_json(File) :-
@@ -115,16 +180,24 @@ write_events_list(_, []).
115
180
  write_events_list(Stream, [Event]) :-
116
181
  !,
117
182
  write(Stream, ' '),
118
- write_json_event(Stream, Event).
183
+ write_json_event_or_marker(Stream, Event).
119
184
  write_events_list(Stream, [Event|Rest]) :-
120
185
  write(Stream, ' '),
121
- write_json_event(Stream, Event),
186
+ write_json_event_or_marker(Stream, Event),
122
187
  write(Stream, ',\n'),
123
188
  write_events_list(Stream, Rest).
124
189
 
190
+ %% write_json_event_or_marker(+Stream, +EventOrMarker)
191
+ % Write either a regular event or a truncation marker
192
+ write_json_event_or_marker(Stream, truncated(MaxDepth)) :-
193
+ !,
194
+ format(Stream, '{"truncated": true, "max_depth": ~w}', [MaxDepth]).
195
+ write_json_event_or_marker(Stream, Event) :-
196
+ write_json_event(Stream, Event).
197
+
125
198
  %% write_json_event(+Stream, +Event)
126
199
  % Write a single event as JSON object
127
- write_json_event(Stream, event(Port, Level, Goal, Arguments, ClauseInfo, Predicate)) :-
200
+ write_json_event(Stream, event(Port, Level, Goal, Arguments, ClauseInfo, Predicate, ParentInfo)) :-
128
201
  format(Stream, '{', []),
129
202
  format(Stream, '"port": "~w"', [Port]),
130
203
  format(Stream, ', "level": ~w', [Level]),
@@ -140,18 +213,56 @@ write_json_event(Stream, event(Port, Level, Goal, Arguments, ClauseInfo, Predica
140
213
  ),
141
214
 
142
215
  % Write clause info if present
143
- ( ClauseInfo = clause(Head, Body, Line)
144
- -> format(Stream, ', "clause": {', []),
145
- format(Stream, '"head": ', []),
146
- write_json_term(Stream, Head),
147
- format(Stream, ', "body": ', []),
148
- write_json_term(Stream, Body),
149
- format(Stream, ', "line": ~w', [Line]),
150
- format(Stream, '}', [])
216
+ write_clause_info_json(Stream, ClauseInfo),
217
+
218
+ % Write parent info if present
219
+ write_parent_info_json(Stream, ParentInfo),
220
+
221
+ format(Stream, '}', []).
222
+ % Backward compatibility: handle old event format without ParentInfo
223
+ write_json_event(Stream, event(Port, Level, Goal, Arguments, ClauseInfo, Predicate)) :-
224
+ format(Stream, '{', []),
225
+ format(Stream, '"port": "~w"', [Port]),
226
+ format(Stream, ', "level": ~w', [Level]),
227
+ format(Stream, ', "goal": ', []),
228
+ write_json_term(Stream, Goal),
229
+ format(Stream, ', "predicate": "~w"', [Predicate]),
230
+
231
+ % Write arguments if present (exit port)
232
+ ( Arguments \= []
233
+ -> format(Stream, ', "arguments": ', []),
234
+ write_json_list(Stream, Arguments)
151
235
  ; true
152
236
  ),
153
237
 
238
+ % Write clause info if present
239
+ write_clause_info_json(Stream, ClauseInfo),
240
+
241
+ format(Stream, '}', []).
242
+
243
+ %% write_clause_info_json(+Stream, +ClauseInfo)
244
+ % Write clause information as JSON
245
+ write_clause_info_json(Stream, clause(Head, Body, Line)) :-
246
+ !,
247
+ format(Stream, ', "clause": {', []),
248
+ format(Stream, '"head": ', []),
249
+ write_json_term(Stream, Head),
250
+ format(Stream, ', "body": ', []),
251
+ write_json_term(Stream, Body),
252
+ format(Stream, ', "line": ~w', [Line]),
253
+ format(Stream, '}', []).
254
+ write_clause_info_json(_, no_clause).
255
+
256
+ %% write_parent_info_json(+Stream, +ParentInfo)
257
+ % Write parent information as JSON
258
+ write_parent_info_json(Stream, parent(ParentLevel, ParentGoal)) :-
259
+ !,
260
+ format(Stream, ', "parent_info": {', []),
261
+ format(Stream, '"level": ~w', [ParentLevel]),
262
+ format(Stream, ', "goal": ', []),
263
+ write_json_term(Stream, ParentGoal),
154
264
  format(Stream, '}', []).
265
+ write_parent_info_json(_, no_parent).
155
266
 
156
267
  %% write_json_term(+Stream, +Term)
157
268
  % Write a Prolog term as JSON string