CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/pypi-structlog

Structured logging for Python that emphasizes simplicity, power, and performance

Overview
Eval results
Files

development-tools.mddocs/

Development Tools

Rich console output, colored logging, column formatting, and advanced traceback rendering designed for development environments and debugging. These tools provide human-readable output optimized for development workflows.

Capabilities

Console Rendering

Render structured log events as human-readable, colored console output with alignment and customizable formatting.

class ConsoleRenderer:
    """Render event dictionary as aligned, colored console output."""
    
    def __init__(
        self,
        pad_event=30,
        colors=True,
        force_colors=False,
        repr_native_str=False,
        level_styles=None,
        exception_formatter=default_exception_formatter,
        sort_keys=True,
        event_key="event",
        timestamp_key="timestamp",
        columns=None,
        pad_level=True
    ):
        """
        Args:
            pad_event (int): Minimum width for event column
            colors (bool): Enable colored output
            force_colors (bool): Force colors even when not in terminal
            repr_native_str (bool): Use repr() for string values
            level_styles (dict, optional): Custom color styles for log levels
            exception_formatter (callable): Function to format exceptions
            sort_keys (bool): Sort context keys alphabetically
            event_key (str): Key name for main event message
            timestamp_key (str): Key name for timestamp
            columns (list, optional): Custom column configuration
            pad_level (bool): Pad log level names for alignment
        """
    
    def __call__(self, logger, name, event_dict) -> str: ...
    
    @staticmethod
    def get_default_level_styles(colors=True) -> dict[str, str]:
        """
        Get default color styles for log levels.
        
        Args:
            colors (bool): Return colored styles if True, empty styles if False
            
        Returns:
            dict: Mapping of log level names to ANSI color codes
        """

Column Formatting

Flexible column-based formatting system for structured console output.

class Column:
    """Column definition for console rendering."""
    
    key: str  # Key for which this column is responsible
    formatter: ColumnFormatter  # Column formatter instance

class KeyValueColumnFormatter:
    """Format key-value pairs with customizable styling."""
    
    def __init__(
        self,
        key_style,
        value_style,
        reset_style,
        value_repr,
        width=0,
        prefix="",
        postfix=""
    ):
        """
        Args:
            key_style (str): ANSI style code for keys
            value_style (str): ANSI style code for values
            reset_style (str): ANSI reset code
            value_repr (callable): Function to convert values to strings
            width (int): Minimum column width
            prefix (str): Text to prepend to output
            postfix (str): Text to append to output
        """
    
    def __call__(self, key, value) -> str: ...

class LogLevelColumnFormatter:
    """Format log level names with level-specific styling."""
    
    def __init__(self, level_styles, reset_style, width=None):
        """
        Args:
            level_styles (dict): Mapping of level names to style codes
            reset_style (str): ANSI reset code
            width (int, optional): Fixed width for level column
        """
    
    def __call__(self, key, value) -> str: ...

# Protocol for column formatters
class ColumnFormatter(Protocol):
    """Protocol for column formatter functions."""
    
    def __call__(self, key: str, value: object) -> str: ...

Exception Formatting

Advanced exception and traceback formatting with multiple rendering options.

class RichTracebackFormatter:
    """Rich traceback renderer with syntax highlighting and local variables."""
    
    def __init__(
        self,
        color_system="truecolor",
        show_locals=True,
        max_frames=100,
        theme=None,
        word_wrap=False,
        extra_lines=3,
        width=100,
        indent_guides=True,
        locals_max_length=10,
        locals_max_string=80,
        locals_hide_dunder=True,
        locals_hide_sunder=False,
        suppress=()
    ):
        """
        Args:
            color_system (str): Color system ("truecolor", "256", "standard", "windows")
            show_locals (bool): Show local variables in traceback
            max_frames (int): Maximum number of frames to show
            theme (str, optional): Syntax highlighting theme
            word_wrap (bool): Enable word wrapping
            extra_lines (int): Extra lines of context around each frame
            width (int): Console width for formatting
            indent_guides (bool): Show indentation guides
            locals_max_length (int): Maximum number of local variables to show
            locals_max_string (int): Maximum length of local variable strings
            locals_hide_dunder (bool): Hide dunder variables (__var__)
            locals_hide_sunder (bool): Hide sunder variables (_var)
            suppress (tuple): Modules to suppress in traceback
        """
    
    def __call__(self, sio, exc_info) -> None: ...

def plain_traceback(sio, exc_info) -> None:
    """
    Plain traceback formatter function.
    
    Args:
        sio: Text stream to write to
        exc_info: Exception info tuple (type, value, traceback)
    """

def better_traceback(sio, exc_info) -> None:
    """
    Better-exceptions traceback formatter function.
    
    Args:
        sio: Text stream to write to
        exc_info: Exception info tuple (type, value, traceback)
    """

rich_traceback: RichTracebackFormatter
"""Pre-configured RichTracebackFormatter instance."""

Exception Info Processing

Processor for automatically setting exception info in log events.

def set_exc_info(logger, method_name, event_dict) -> EventDict:
    """
    Set exc_info=True for exception-related log methods.
    
    Automatically adds exception information when logging methods
    like 'exception', 'error', etc. are called.
    
    Args:
        logger: Logger instance
        method_name (str): Name of the logger method being called
        event_dict (dict): Event dictionary
        
    Returns:
        dict: Event dictionary with exc_info set if appropriate
    """

Color Constants

ANSI color code constants for custom styling.

RESET_ALL: str  # Reset all formatting
BRIGHT: str     # Bright/bold text
DIM: str        # Dim text

# Foreground colors
RED: str
BLUE: str
CYAN: str
MAGENTA: str
YELLOW: str
GREEN: str

# Background colors
RED_BACK: str

Usage Examples

Basic Development Configuration

import structlog
from structlog import dev, processors

structlog.configure(
    processors=[
        processors.TimeStamper(fmt="iso"),
        dev.ConsoleRenderer(
            colors=True,
            exception_formatter=dev.rich_traceback
        )
    ],
    wrapper_class=structlog.BoundLogger,
)

logger = structlog.get_logger()
logger.info("Application started", version="1.0.0", debug=True)

Custom Console Styling

import structlog
from structlog import dev, processors

# Custom level styles
custom_styles = {
    "debug": dev.CYAN,
    "info": dev.GREEN,
    "warning": dev.YELLOW,
    "error": dev.RED,
    "critical": dev.RED_BACK
}

console_renderer = dev.ConsoleRenderer(
    colors=True,
    level_styles=custom_styles,
    pad_event=40,
    sort_keys=False,
    event_key="message",
    timestamp_key="ts"
)

structlog.configure(
    processors=[
        processors.TimeStamper(key="ts"),
        console_renderer
    ],
    wrapper_class=structlog.BoundLogger,
)

logger = structlog.get_logger()
logger.warning("Custom styling", component="auth", user_count=42)

Column-Based Formatting

import structlog
from structlog import dev, processors

# Define custom columns
timestamp_column = dev.Column(
    key="timestamp",
    formatter=dev.KeyValueColumnFormatter(
        key_style="",  # No styling for timestamp key
        value_style=dev.DIM,
        reset_style=dev.RESET_ALL,
        value_repr=str,
        width=25
    )
)

level_column = dev.Column(
    key="level",
    formatter=dev.LogLevelColumnFormatter(
        level_styles=dev.ConsoleRenderer.get_default_level_styles(),
        reset_style=dev.RESET_ALL,
        width=8
    )
)

console_renderer = dev.ConsoleRenderer(
    columns=[timestamp_column, level_column],
    colors=True
)

structlog.configure(
    processors=[
        processors.TimeStamper(),
        processors.add_log_level,
        console_renderer
    ],
    wrapper_class=structlog.BoundLogger,
)

Rich Exception Formatting

import structlog
from structlog import dev, processors

# Configure rich traceback formatter
rich_formatter = dev.RichTracebackFormatter(
    show_locals=True,
    max_frames=20,
    locals_max_length=5,
    locals_max_string=50,
    color_system="truecolor",
    theme="monokai"
)

structlog.configure(
    processors=[
        processors.TimeStamper(),
        dev.set_exc_info,  # Automatically set exc_info for exceptions
        dev.ConsoleRenderer(
            exception_formatter=rich_formatter,
            colors=True
        )
    ],
    wrapper_class=structlog.BoundLogger,
)

logger = structlog.get_logger()

def problematic_function():
    local_var = "important data"
    raise ValueError("Something went wrong")

try:
    problematic_function()
except ValueError:
    logger.exception("Function failed", context="processing_data")
    # Will show rich traceback with local variables

Development vs Production Configuration

import os
import structlog
from structlog import dev, processors

def configure_logging():
    if os.getenv("ENVIRONMENT") == "development":
        # Development: colored console output
        structlog.configure(
            processors=[
                processors.TimeStamper(fmt="%H:%M:%S"),
                processors.add_log_level,
                dev.ConsoleRenderer(
                    colors=True,
                    exception_formatter=dev.rich_traceback,
                    repr_native_str=True
                )
            ],
            wrapper_class=structlog.BoundLogger,
        )
    else:
        # Production: JSON output
        structlog.configure(
            processors=[
                processors.TimeStamper(fmt="iso"),
                processors.add_log_level,
                processors.format_exc_info,
                processors.JSONRenderer()
            ],
            wrapper_class=structlog.BoundLogger,
        )

configure_logging()
logger = structlog.get_logger()

Custom Exception Formatter

import structlog
from structlog import dev, processors
import traceback

def custom_exception_formatter(sio, exc_info):
    """Custom exception formatter that adds extra context."""
    sio.write(f"\n{'='*50}\n")
    sio.write("EXCEPTION OCCURRED:\n")
    sio.write(f"{'='*50}\n")
    
    # Use standard traceback formatting
    traceback.print_exception(*exc_info, file=sio)
    
    sio.write(f"{'='*50}\n")

structlog.configure(
    processors=[
        processors.TimeStamper(),
        dev.ConsoleRenderer(
            exception_formatter=custom_exception_formatter,
            colors=True
        )
    ],
    wrapper_class=structlog.BoundLogger,
)

logger = structlog.get_logger()

try:
    raise RuntimeError("Custom exception handling demo")
except RuntimeError:
    logger.exception("Demonstrating custom formatter")

Conditional Coloring

import sys
import structlog
from structlog import dev, processors

# Enable colors only if stdout is a terminal
use_colors = sys.stdout.isatty()

structlog.configure(
    processors=[
        processors.TimeStamper(),
        processors.add_log_level,
        dev.ConsoleRenderer(
            colors=use_colors,
            force_colors=False  # Respect terminal detection
        )
    ],
    wrapper_class=structlog.BoundLogger,
)

logger = structlog.get_logger()
logger.info("Colors enabled" if use_colors else "No colors", terminal=use_colors)

Install with Tessl CLI

npx tessl i tessl/pypi-structlog

docs

bound-loggers.md

configuration.md

context-management.md

development-tools.md

exception-handling.md

index.md

logger-creation.md

output-loggers.md

processors.md

stdlib-integration.md

testing.md

tile.json