diff --git a/graphify/detect.py b/graphify/detect.py index d5521b3..d5811ad 100644 --- a/graphify/detect.py +++ b/graphify/detect.py @@ -370,6 +370,12 @@ _SKIP_DIRS = { ".pytest_cache", ".mypy_cache", ".ruff_cache", ".tox", ".eggs", "*.egg-info", "graphify-out", # never treat own output as source input (#524) + # Coverage/test-artefact dirs — generated, never architecturally meaningful + "coverage", "lcov-report", # Vitest/Istanbul/nyc HTML reports (#870) + "visual-tests", "visual-test", # Playwright/visual-regression bundles (#869) + "__snapshots__", "snapshots", # Jest/Vitest snapshot dirs + "storybook-static", # Storybook production build output + "dist-protected", # Protected dist variants (same noise as dist) } # Large generated files that are never useful to extract diff --git a/tests/test_detect.py b/tests/test_detect.py index c1754a7..740d1e4 100644 --- a/tests/test_detect.py +++ b/tests/test_detect.py @@ -316,3 +316,54 @@ def test_detect_video_not_in_words(tmp_path): result = detect(tmp_path) # Only video file present — total_words should be 0 assert result["total_words"] == 0 + + +def test_detect_skips_coverage_dir(tmp_path): + """coverage/ and lcov-report/ are noise dirs — HTML reports inside must be excluded (#870).""" + cov = tmp_path / "coverage" / "lcov-report" + cov.mkdir(parents=True) + (cov / "index.html").write_text("coverage report") + (cov / "src.ts.html").write_text("file coverage") + (tmp_path / "main.py").write_text("def hello(): pass") + result = detect(tmp_path) + all_files = [f for files in result["files"].values() for f in files] + cov_prefix = str(tmp_path / "coverage") + assert not any(f.startswith(cov_prefix) for f in all_files) + assert any("main.py" in f for f in all_files) + + +def test_detect_skips_visual_tests_dir(tmp_path): + """visual-tests/ bundles and snapshots are noise — must be excluded (#869).""" + vt = tmp_path / "visual-tests" + vt.mkdir() + (vt / "bundle.js").write_text("var u3=function(){};var d2=function(){}") + (vt / "screens.tsx").write_text("export const Screen = () =>
") + (tmp_path / "app.py").write_text("def main(): pass") + result = detect(tmp_path) + all_files = [f for files in result["files"].values() for f in files] + assert not any("visual-tests" in f for f in all_files) + assert any("app.py" in f for f in all_files) + + +def test_detect_skips_snapshots_dir(tmp_path): + """__snapshots__/ and snapshots/ are jest/vitest artefacts — must be excluded.""" + (tmp_path / "__snapshots__").mkdir() + (tmp_path / "__snapshots__" / "app.test.ts.snap").write_text("// Jest Snapshot\nexports[`test 1`] = `
`") + (tmp_path / "app.ts").write_text("export function greet() { return 'hi'; }") + result = detect(tmp_path) + all_files = [f for files in result["files"].values() for f in files] + assert not any("__snapshots__" in f for f in all_files) + assert any("app.ts" in f for f in all_files) + + +def test_detect_skips_storybook_static_dir(tmp_path): + """storybook-static/ is a build artefact — must be excluded.""" + sb = tmp_path / "storybook-static" + sb.mkdir() + (sb / "index.html").write_text("storybook") + (sb / "main.js").write_text("(function(){var s=1;})()") + (tmp_path / "Button.tsx").write_text("export const Button = () =>