Coverage for tests / test_dtd / test_python.py: 100%
36 statements
« prev ^ index » next coverage.py v7.13.3, created at 2026-02-08 15:04 -0800
« prev ^ index » next coverage.py v7.13.3, created at 2026-02-08 15:04 -0800
1"""Tests for Data Transformation Density (Python)."""
3from analyzers.python import analyze_source
6def _dtd(code: str) -> int:
7 """Return DTD of the first function in code."""
8 result = analyze_source(code)
9 assert result.functions, f"No functions found in:\n{code}"
10 return result.functions[0].dtd
13def _dtds(code: str) -> dict[str, int]:
14 """Return {name: dtd} for all functions in code."""
15 result = analyze_source(code)
16 return {f.name: f.dtd for f in result.functions}
19# --- Empty / no data ---
21def test_empty_function():
22 assert _dtd("def f(): pass") == 0
25def test_no_data_structures():
26 code = """
27def f(x):
28 return x + 1
29"""
30 assert _dtd(code) == 0
33# --- Flat structures ---
35def test_flat_dict():
36 code = """
37def f():
38 return {"a": 1, "b": 2, "c": 3}
39"""
40 # dict at depth 1, 3 pairs x 1 = 3
41 assert _dtd(code) == 3
44def test_flat_list():
45 code = """
46def f():
47 return [1, 2, 3]
48"""
49 # list at depth 1, 3 elements x 1 = 3
50 assert _dtd(code) == 3
53# --- Nested structures ---
55def test_nested_dict_in_list():
56 code = """
57def f():
58 return [{"a": 1}, {"b": 2}]
59"""
60 # list at depth 1: 2 elements x 1 = 2
61 # each dict at depth 2: 1 pair x 2 = 2 each -> 4
62 # total = 2 + 4 = 6
63 assert _dtd(code) == 6
66def test_deeply_nested():
67 code = """
68def f():
69 return {"outer": {"inner": [1, 2]}}
70"""
71 # outer dict depth 1: 1 pair x 1 = 1
72 # inner dict depth 2: 1 pair x 2 = 2
73 # list depth 3: 2 elements x 3 = 6
74 # total = 1 + 2 + 6 = 9
75 assert _dtd(code) == 9
78# --- Nested function skipped ---
80def test_nested_function_skipped():
81 code = """
82def outer():
83 x = {"a": 1}
84 def inner():
85 y = {"b": 2, "c": 3}
86 return x
87"""
88 dtds = _dtds(code)
89 assert dtds["outer"] == 1 # only {"a": 1}
90 assert dtds["inner"] == 2 # {"b": 2, "c": 3} -> 2 pairs x 1
93# --- Comprehensions ---
95def test_dict_comprehension():
96 code = """
97def f(items):
98 return {k: v for k, v in items}
99"""
100 # dict_comprehension is a container at depth 1
101 # pair inside at depth 1: 1 pair x 1 = 1
102 assert _dtd(code) == 1
105def test_list_comprehension():
106 code = """
107def f(items):
108 return [x for x in items]
109"""
110 # list_comprehension is a container at depth 1
111 # no explicit payload children (the inner expression isn't a pair/keyword_arg)
112 assert _dtd(code) == 0