Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 21 additions & 1 deletion tests/test_flow_engine.py
Original file line number Diff line number Diff line change
Expand Up @@ -384,14 +384,34 @@ def test_trace_path_keeps_the_keys_cli_consumes(engine):

def test_format_node_step_shape_is_unchanged(engine):
step = engine._format_node_step(API_CTRL)
assert set(step) == {"id", "label", "layer_id", "layer", "file", "is_test", "intent", "input_fields", "output_fields", "fields"}
assert set(step) == {
"id", "label", "layer_id", "layer", "file", "source_location", "line",
"is_test", "intent", "input_fields", "output_fields", "fields",
}
assert step["label"] == "OrdersController"
assert step["source_location"] == "L1"
assert step["line"] == 1


def test_render_markdown_table_still_renders(engine):
table = FlowEngine.render_markdown_table(engine.trace_path("DeskView")["steps"])
assert "Component / Symbol" in table
assert "OrdersController" in table
assert "backend/src/orders/orders.controller.ts:1" in table


def test_render_markdown_table_omits_line_suffix_when_unknown():
table = FlowEngine.render_markdown_table([
{
"layer": L3,
"label": "NoLineService",
"intent": "No line data",
"file": "backend/src/no-line.service.ts",
"line": None,
}
])
assert "backend/src/no-line.service.ts" in table
assert "backend/src/no-line.service.ts:None" not in table


def test_export_flows_yaml_round_trips(engine, tmp_path):
Expand Down
14 changes: 13 additions & 1 deletion tldrgraph/flow_engine.py
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,7 @@
from .hierarchy import is_test_node
from .layers import get_registry, layer_id_of
from .vector_store import LocalVectorStore
from .visualizer.source import parse_line_number


class FlowEngine:
Expand Down Expand Up @@ -189,6 +190,7 @@ def _format_node_step(self, node_id: str) -> Dict[str, Any]:
input_fields = node_data.get("input_fields", [])
output_fields = node_data.get("output_fields", [])
fields = node_data.get("fields", []) or (list(input_fields) + list(output_fields))
source_location = node_data.get("source_location")
is_test = node_data.get("is_test")
if is_test is None:
is_test = is_test_node(node_data.get("file", ""), node_data.get("label", ""))
Expand All @@ -198,6 +200,8 @@ def _format_node_step(self, node_id: str) -> Dict[str, Any]:
"layer_id": self._layer_id_of(node_id),
"layer": node_data.get("layer", "Unknown"),
"file": node_data.get("file", ""),
"source_location": source_location,
"line": parse_line_number(source_location),
"is_test": bool(is_test),
"intent": node_data.get("intent") or node_data.get("summary", ""),
"input_fields": input_fields,
Expand All @@ -215,14 +219,22 @@ def export_flows_yaml(self, flows: List[Dict[str, Any]], filename: str = ".tldrg
@staticmethod
def render_markdown_table(steps: List[Dict[str, Any]]) -> str:
headers = ["Layer", "Component / Symbol", "Intent & Action", "Input Fields", "Output Fields", "File Location"]

def file_location(step: Dict[str, Any]) -> str:
file_path = step.get("file", "")
line = step.get("line")
if file_path and line:
return f"{file_path}:{line}"
return file_path

rows = [
[
s.get("layer", ""),
s.get("label", s.get("id", "")),
s.get("intent", ""),
", ".join(s.get("input_fields", [])) if s.get("input_fields") else (", ".join(s.get("fields", [])) if s.get("fields") else "-"),
", ".join(s.get("output_fields", [])) if s.get("output_fields") else "-",
s.get("file", ""),
file_location(s),
]
for s in steps
]
Expand Down
Loading