CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/pypi-lizard

An extensible cyclomatic complexity analyzer for many programming languages including C/C++, Java, JavaScript, Python, Ruby, Swift, and more.

Pending
Overview
Eval results
Files

extensions-system.mddocs/

Extensions System

Extension framework for custom analysis metrics and output formats through the lizard_ext package. The system provides both built-in extensions for common analysis needs and an extensible architecture for custom extensions.

Capabilities

Extension Loading

Functions for loading and managing extensions during analysis.

def get_extensions(extension_names):
    """
    Loads and expands extension modules for analysis.
    
    Args:
        extension_names (list): List of extension names to load (e.g., ['nd', 'ns', 'wordcount'])
        
    Returns:
        list: List of extension objects ready for analysis
        
    Example:
        # Load nesting depth and nested structures extensions
        extensions = get_extensions(['nd', 'ns'])
        results = lizard.analyze_files(['app.py'], exts=extensions)
    """

Output Formatters

Built-in formatters for generating analysis reports in various formats.

def print_xml(results, options, _, total_factory):
    """
    Formats and prints XML output in cppncss-compatible format.
    
    Args:
        results: Iterator of analysis results
        options: Configuration options object
        _: Unused parameter (for interface compatibility)
        total_factory: Factory function for creating total results
        
    Returns:
        int: Exit code (0 for success)
    """

def print_csv(results, options, _, total_factory):
    """
    Formats and prints CSV output with function metrics.
    
    Args:
        results: Iterator of analysis results  
        options: Configuration options object
        _: Unused parameter
        total_factory: Factory function for creating total results
        
    Returns:
        int: Exit code (0 for success)
    """

def print_checkstyle(results, options, _, total_factory, file=None):
    """
    Formats and prints Checkstyle XML output for CI integration.
    
    Args:
        results: Iterator of analysis results
        options: Configuration options object  
        _: Unused parameter
        total_factory: Factory function for creating total results
        file: Output file object (optional, defaults to stdout)
        
    Returns:
        int: Exit code (0 for success)
    """

def html_output(result, options, *_):
    """
    Generates HTML reports using Jinja2 templates.
    
    Args:
        result: Analysis results object
        options: Configuration options
        
    Returns:
        str: HTML report content
    """

def csv_output(result, options):
    """
    Generates CSV format output with function metrics.
    
    Args:
        result: Analysis results object
        options: Configuration options
        
    Returns:
        str: CSV formatted output
    """

def xml_output(all_result, verbose):
    """
    Generates cppncss-compatible XML output.
    
    Args:
        all_result: Aggregated analysis results
        verbose (bool): Include detailed function information
        
    Returns:
        str: XML formatted output
    """

def checkstyle_output(all_result, verbose):
    """
    Generates Checkstyle XML format output.
    
    Args:
        all_result: Aggregated analysis results  
        verbose (bool): Include detailed information
        
    Returns:
        str: Checkstyle XML formatted output
    """

File Utilities

Smart file handling utilities with encoding detection.

def auto_open(*args, **kwargs):
    """
    Smart file opening with UTF-8 BOM detection and encoding fallback.
    
    Args:
        *args: Arguments passed to open()
        **kwargs: Keyword arguments passed to open()
        
    Returns:
        file object: Opened file with appropriate encoding
        
    Example:
        with auto_open('data.txt', 'r') as f:
            content = f.read()
    """

def auto_read(filename):
    """
    Smart file reading with fallback encoding handling.
    
    Args:
        filename (str): Path to file to read
        
    Returns:
        str: File content with detected encoding
        
    Example:
        content = auto_read('source_file.py')
        print(f"File length: {len(content)} characters")
    """

Analysis Extensions

Built-in extensions for specialized code analysis metrics.

Nesting Depth Extension

class LizardExtension:
    """
    Nesting Depth (ND) extension for analyzing maximum nesting depth.
    
    Command-line: -N, --ND
    Threshold: DEFAULT_ND_THRESHOLD = 7
    
    Function Info Added:
        max_nesting_depth: Maximum nesting depth in function
    """

Nested Structures Extension

class LizardExtension:
    """
    Nested Structures (NS) extension for counting nested control structures.
    
    Command-line: --NS  
    Threshold: DEFAULT_NS_THRESHOLD = 3
    
    Function Info Added:
        max_nested_structures: Count of nested control structures
    """

Word Count Extension

class LizardExtension:
    """
    Word Count extension for generating tag clouds from code.
    
    Command-line: -Ewordcount
    
    Features:
        - Counts word occurrences across codebase
        - Generates HTML tag cloud visualization
        - Filters common programming keywords
        - Cross-file analysis and aggregation
    """

Duplicate Detection Extension

class LizardExtension:
    """
    Duplicate code detection extension.
    
    Command-line: -Eduplicate
    
    Features:
        - Detects copy-paste code blocks
        - Configurable similarity thresholds
        - Hash-based duplicate identification
    """

Extension Base Classes

Base classes for creating custom extensions.

class ExtensionBase:
    """
    Base class for all lizard extensions.
    
    Methods to override:
        __call__(self, tokens, reader): Process tokens during analysis
        set_args(parser): Add command-line arguments  
        cross_file_process(fileinfos): Process results across multiple files
    """

Available Extensions

Complete list of built-in extensions with their capabilities:

# Core Analysis Extensions
class LizardExtension:  # lizardnd.py
    """Nesting depth analysis (max_nesting_depth metric)"""

class LizardExtension:  # lizardns.py  
    """Nested structures counting (max_nested_structures metric)"""

class LizardExtension:  # lizardmccabe.py
    """McCabe complexity metrics"""

class LizardExtension:  # lizardmodified.py
    """Modified complexity calculations"""

# Code Quality Extensions  
class LizardExtension:  # lizardduplicate.py
    """Duplicate code detection and reporting"""

class LizardExtension:  # lizardduplicatedparamlist.py
    """Duplicate parameter list detection"""

class LizardExtension:  # lizardboolcount.py
    """Boolean complexity counting"""

class LizardExtension:  # lizardcomplextags.py
    """Complex tag analysis"""

# Statement and Flow Extensions
class LizardExtension:  # lizardexitcount.py
    """Exit/return statement counting (exit_count metric)"""

class LizardExtension:  # lizardgotocount.py
    """Goto statement counting"""

class LizardExtension:  # lizardstatementcount.py
    """Statement counting and analysis"""

# Language-Specific Extensions
class LizardExtension:  # lizardcpre.py
    """C preprocessor directive filtering"""

class LizardExtension:  # lizardignoreassert.py
    """Assert statement handling and filtering"""

class LizardExtension:  # lizardnonstrict.py
    """Non-strict parsing mode"""

# Analysis and Reporting Extensions
class LizardExtension:  # lizardwordcount.py
    """Word frequency analysis and tag cloud generation"""

class LizardExtension:  # lizardio.py
    """I/O operation analysis"""

class LizardExtension:  # lizarddependencycount.py
    """Dependency counting and analysis"""

class LizardExtension:  # lizardoutside.py
    """External scope analysis"""

class LizardExtension:  # lizarddumpcomments.py
    """Comment extraction and dumping"""

Usage Examples

Basic Extension Usage

import lizard

# Use nesting depth extension
extensions = lizard.get_extensions(['nd'])
results = lizard.analyze(['src/'], exts=extensions)

for file_info in results:
    for func in file_info.function_list:
        if hasattr(func, 'max_nesting_depth'):
            print(f"{func.name}: ND={func.max_nesting_depth}")

Multiple Extensions

import lizard

# Combine multiple extensions
extensions = lizard.get_extensions(['nd', 'ns', 'exitcount'])
results = lizard.analyze(['src/'], exts=extensions)

for file_info in results:
    for func in file_info.function_list:
        metrics = []
        if hasattr(func, 'max_nesting_depth'):
            metrics.append(f"ND={func.max_nesting_depth}")
        if hasattr(func, 'max_nested_structures'):
            metrics.append(f"NS={func.max_nested_structures}")
        if hasattr(func, 'exit_count'):
            metrics.append(f"Exits={func.exit_count}")
        
        print(f"{func.name}: {', '.join(metrics)}")

Command-Line Extension Usage

import lizard

# Equivalent of: lizard -Ewordcount -Eduplicate -N src/
lizard.main(['-Ewordcount', '-Eduplicate', '-N', 'src/'])

# Multiple output formats with extensions  
lizard.main(['-Ewordcount', '--xml', '-N', 'src/'])

Custom Output Processing

from lizard_ext import html_output, csv_output
import lizard

# Generate analysis results
extensions = lizard.get_extensions(['nd', 'ns'])
results = list(lizard.analyze(['src/'], exts=extensions))

# Create custom options object
class Options:
    def __init__(self):
        self.verbose = True
        self.fields = ['nloc', 'ccn', 'max_nesting_depth']

options = Options()

# Generate HTML report
html_report = html_output(results, options)
with open('analysis_report.html', 'w') as f:
    f.write(html_report)

# Generate CSV data  
csv_data = csv_output(results, options)
with open('analysis_data.csv', 'w') as f:
    f.write(csv_data)

File Encoding Utilities

from lizard_ext import auto_open, auto_read

# Smart file reading with encoding detection
try:
    content = auto_read('source_file_with_unicode.py')
    print(f"Successfully read {len(content)} characters")
except Exception as e:
    print(f"Failed to read file: {e}")

# Smart file opening
with auto_open('output.txt', 'w', encoding='utf-8') as f:
    f.write("Analysis results with unicode: 你好 world")

Install with Tessl CLI

npx tessl i tessl/pypi-lizard

docs

core-analysis.md

data-models.md

extensions-system.md

index.md

language-support.md

utility-functions.md

tile.json