A Python tool to parse a project's imports and build a dependency graph of modules and packages. Detects cycles, dead code, and oversized modules. Provides ASCII maps and Graphviz exports. Warns about risky dynamic imports.
- AST-based Parsing: Walks Python ASTs to extract imports and module structure
- Dependency Graph: Builds a complete dependency graph of all modules
- Cycle Detection: Identifies circular dependencies
- Dead Code Detection: Finds unused modules and unreachable code
- Oversized Module Detection: Flags modules exceeding size thresholds
- Module Split Suggestions: Heuristic-based suggestions for refactoring large modules
- Dynamic Import Detection: Warns about risky dynamic imports
- ASCII Visualization: Prints human-readable dependency maps
- Graphviz Export: Exports graphs in DOT, PNG, SVG, or PDF formats
- Fast Performance: Optimized for medium-sized repositories, suitable for pre-commit hooks
The project is split into two equal-weight components:
ast_parser.py: AST walking and parsingimport_resolver.py: Import resolution to file pathsgraph_builder.py: Dependency graph constructiondynamic_import_detector.py: Dynamic import detection
cycle_detector.py: Cycle detection algorithmsdead_code_detector.py: Dead code detectionmodule_analyzer.py: Module size and complexity analysissplit_suggester.py: Module split suggestionsvisualizer.py: ASCII maps and Graphviz export
- Python 3.7+
- Standard library only (no external dependencies required)
- Optional: Graphviz (for PNG/SVG/PDF export)
- Clone or download this repository
- No installation required - just run
python cli.py
For Graphviz export to PNG/SVG/PDF:
# macOS
brew install graphviz
# Ubuntu/Debian
sudo apt-get install graphviz
# Windows
# Download from https://graphviz.org/download/See cli_description.md for detailed CLI documentation.
A representative sample fixture lives under tests/sample_project. It includes circular imports, dynamic imports, oversized modules, dead code, and unused scripts so every analyzer feature has meaningful output. A helper script tests/run_sample_demo.sh runs the full suite.
# run manually
python cli.py tests/sample_project \
--cycles \
--dead-code \
--oversized 150 \
--suggest-splits \
--dynamic-imports \
--ascii \
--summary
# or use the helper
bash tests/run_sample_demo.sh# Basic analysis
python cli.py .
# Detect cycles
python cli.py . --cycles
# Generate ASCII map
python cli.py . --ascii
# Export to Graphviz
python cli.py . --graphviz deps.dot
# Full analysis
python cli.py . --cycles --dead-code --oversized 500 --suggest-splits --ascii --graphviz deps.dotpython cli.py /path/to/project --cyclesOutput:
⚠️ CIRCULAR DEPENDENCIES DETECTED: 2 cycle(s)
Cycle 1: module_a.py -> module_b.py -> module_c.py -> module_a.py -> ...
Cycle 2: utils.py -> helpers.py -> utils.py -> ...
python cli.py . --oversized 300Output:
⚠️ OVERSIZED MODULES (> 300 lines): 3 module(s)
- parser/ast_parser.py: 450 lines
- analyzer/visualizer.py: 380 lines
- main.py: 320 lines
python cli.py . --suggest-splitsOutput:
💡 MODULE SPLIT SUGGESTIONS: 2 module(s)
parser/ast_parser.py:
- Split into separate modules by class groups
Reason: Module has 5 classes that could be grouped
utils.py:
- Consider splitting into domain-specific utility modules
Reason: Large utility module with 25 functions
# ASCII map
python cli.py . --ascii --max-depth 4
# Graphviz (DOT)
python cli.py . --graphviz deps.dot
# Graphviz (PNG - requires Graphviz)
python cli.py . --graphviz deps.png --format pngAdd to .pre-commit-config.yaml:
repos:
- repo: local
hooks:
- id: dependency-check
name: Check for circular dependencies
entry: python cli.py
language: system
args: ['.', '--cycles']
pass_filenames: false
always_run: true- Cycle Detection: Uses DFS (Depth-First Search) with recursion stack tracking
- Dead Code Detection: BFS (Breadth-First Search) from entry points to find reachable nodes
- Graph Building: Constructs directed graph with nodes (files) and edges (imports)
- Time Complexity: O(V + E) for most operations where V = vertices, E = edges
- Space Complexity: O(V + E) for graph storage
- Typically completes in seconds for projects with hundreds of files
- Only analyzes static imports (dynamic imports are detected but not fully resolved)
- Dead code detection uses heuristics (may have false positives)
- Split suggestions are heuristic-based
- External dependencies are not fully resolved
This is a student project. The codebase is split into two equal-weight components for two developers.
This project is for educational purposes.
- Sagar Veeresh Halladakeri - 251810700276
- Nesar Ravishankar Kavri - 251810700211
Group - 127