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

data-models.mddocs/

Data Models

Core data structures representing analysis results including function information, file statistics, and complexity metrics. These classes provide structured access to all code analysis data.

Capabilities

Function Information

Represents detailed information about individual functions with complexity metrics and location data.

class FunctionInfo(Nesting):
    """
    Represents function information with complexity metrics.
    
    Attributes:
        name (str): Function name
        cyclomatic_complexity (int): McCabe cyclomatic complexity number
        nloc (int): Number of lines of code without comments  
        token_count (int): Number of tokens in the function
        parameter_count (int): Number of function parameters
        parameters (list): List of parameter names extracted from full_parameters
        length (int): Total lines including comments and blank lines
        location (str): File path and line number (e.g., "file.py:25")
        start_line (int): Starting line number of the function
        end_line (int): Ending line number of the function  
        filename (str): File containing the function
        long_name (str): Full qualified name with namespace
        full_parameters (str): Raw parameter list as string
        fan_in (int): Number of functions calling this function
        fan_out (int): Number of functions called by this function
        general_fan_out (int): General fan-out metric
        max_nesting_depth (int): Maximum nesting depth reached in the function
        top_nesting_level (int): Top-level nesting information
        unqualified_name (str): Function name without namespace qualifiers
    """
    
    def add_to_function_name(self, app):
        """
        Appends text to the function name.
        
        Args:
            app (str): Text to append to function name
        """
    
    def add_to_long_name(self, app):
        """
        Appends text to the long function name (includes namespace).
        
        Args:
            app (str): Text to append to long name
        """
    
    def add_parameter(self, token):
        """
        Adds a parameter to the function's parameter count.
        
        Args:
            token (str): Parameter token to add
        """

File Information

Contains comprehensive file-level statistics and the list of functions found in the file.

class FileInformation:
    """
    Contains file-level statistics and function list.
    
    Attributes:
        filename (str): Path to the analyzed file
        nloc (int): Total lines of code without comments in file
        function_list (list): List of FunctionInfo objects for functions in file
        average_nloc (float): Average lines of code per function
        average_token_count (float): Average token count per function  
        average_cyclomatic_complexity (float): Average cyclomatic complexity per function
        CCN (int): Total cyclomatic complexity for the file
        ND (int): Total of maximum nesting depths across all functions in the file
        token_count (int): Total token count for the file
    """
    
    def functions_average(self, attr_name):
        """
        Calculates average of a function attribute across all functions.
        
        Args:
            attr_name (str): Name of the attribute to average
            
        Returns:
            float: Average value of the attribute, or 0 if no functions
            
        Example:
            avg_complexity = file_info.functions_average('cyclomatic_complexity')
            avg_params = file_info.functions_average('parameter_count')
        """

File Analysis Engine

Main analysis engine that processes individual files and applies extensions.

class FileAnalyzer:
    """
    Main file analysis engine with extension support.
    
    Args:
        extensions (list): List of extension objects to apply during analysis
    """
    
    def __call__(self, filename):
        """
        Analyzes a single file and returns file information.
        
        Args:
            filename (str): Path to file to analyze
            
        Returns:
            FileInformation: Analysis results for the file
            
        Example:
            analyzer = FileAnalyzer([])
            file_info = analyzer('src/app.py')
            print(f"Functions found: {len(file_info.function_list)}")
        """
    
    def analyze_source_code(self, filename, code):
        """
        Analyzes source code string and returns file information.
        
        Args:
            filename (str): Filename for the code (used for language detection)
            code (str): Source code to analyze
            
        Returns:
            FileInformation: Analysis results for the code
            
        Example:
            analyzer = FileAnalyzer([])
            code = "def hello():\\n    print('world')"
            file_info = analyzer.analyze_source_code('test.py', code)
        """

Nesting Classes

Classes representing code nesting levels and namespace structures.

class Nesting:
    """
    Base class representing one level of nesting.
    
    Attributes:
        name_in_space (str): Name within the current namespace
    """

class Namespace(Nesting):
    """
    Represents namespace nesting level.
    
    Args:
        name (str): Name of the namespace
    """
    
    def __init__(self, name):
        """
        Initialize namespace with given name.
        
        Args:
            name (str): Name of the namespace
        """
    
    @property
    def name_in_space(self):
        """
        Returns the namespace name.
        
        Returns:
            str: The namespace name
        """

Helper Classes

Supporting classes for building analysis results and managing nesting state.

class FileInfoBuilder:
    """
    Builder for file and function information (also called "context").
    Manages the construction of FileInformation objects during parsing.
    """

class NestingStack:
    """
    Manages nesting stack for code analysis.
    
    Properties:
        current_nesting_level (int): Current depth of nesting
        last_function (FunctionInfo): Most recently processed function
    """
    
    def add_namespace(self, namespace):
        """Add a namespace to the nesting stack."""
    
    def start_new_function_nesting(self, func):
        """Start tracking a new function's nesting."""
    
    def pop_nesting(self):
        """Remove the top level of nesting."""

class OutputScheme:
    """
    Manages output formatting and column schemas.
    Handles the formatting of analysis results for display.
    """
    
    def function_info_head(self):
        """Returns header string for function information display."""
    
    def function_info(self, func):
        """Formats function information for display."""

class AllResult:
    """
    Aggregates analysis results across all files.
    Provides summary statistics for entire analysis runs.
    """
    
    def function_count(self):
        """Returns total number of functions analyzed."""
    
    def nloc_in_functions(self):
        """Returns total lines of code in all functions."""
    
    def as_fileinfo(self):
        """Returns aggregated data as a FileInformation object."""

Usage Examples

Accessing Function Details

import lizard

results = lizard.analyze(['src/'])
for file_info in results:
    print(f"File: {file_info.filename}")
    print(f"Total NLOC: {file_info.nloc}")
    print(f"Number of functions: {len(file_info.function_list)}")
    
    for func in file_info.function_list:
        print(f"  Function: {func.name}")
        print(f"    Location: {func.location}")
        print(f"    Complexity: {func.cyclomatic_complexity}")
        print(f"    NLOC: {func.nloc}")
        print(f"    Parameters: {func.parameter_count}")
        print(f"    Length: {func.length}")

File-Level Statistics

import lizard

results = lizard.analyze(['src/'])
for file_info in results:
    print(f"File: {file_info.filename}")
    print(f"  Total complexity: {file_info.CCN}")
    print(f"  Max nesting depth: {file_info.ND}")
    print(f"  Average complexity per function: {file_info.average_cyclomatic_complexity:.2f}")
    print(f"  Average NLOC per function: {file_info.average_nloc:.2f}")
    print(f"  Average tokens per function: {file_info.average_token_count:.2f}")

Direct File Analysis

import lizard

# Analyze a single file directly
analyzer = lizard.FileAnalyzer([])
file_info = analyzer('src/complex_module.py')

print(f"Analyzed: {file_info.filename}")
print(f"Functions found: {len(file_info.function_list)}")

# Find most complex function
most_complex = max(file_info.function_list, 
                   key=lambda f: f.cyclomatic_complexity)
print(f"Most complex function: {most_complex.name} (CCN: {most_complex.cyclomatic_complexity})")

Source Code String Analysis

import lizard

code = '''
def calculate_price(base_price, discount, tax_rate):
    if discount > 0:
        if discount > 0.5:
            final_price = base_price * 0.5
        else:
            final_price = base_price * (1 - discount)
    else:
        final_price = base_price
    
    if tax_rate > 0:
        final_price *= (1 + tax_rate)
    
    return final_price
'''

analyzer = lizard.FileAnalyzer([])
file_info = analyzer.analyze_source_code('example.py', code)

func = file_info.function_list[0]
print(f"Function: {func.name}")
print(f"Complexity: {func.cyclomatic_complexity}")
print(f"Parameters: {func.parameter_count}")
print(f"NLOC: {func.nloc}")

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