or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

docs

index.md
tile.json

tessl/pypi-blacken-docs

Run Black on Python code blocks in documentation files.

Workspace
tessl
Visibility
Public
Created
Last updated
Describes
pypipkg:pypi/blacken-docs@1.19.x

To install, run

npx @tessl/cli install tessl/pypi-blacken-docs@1.19.0

index.mddocs/

blacken-docs

A command-line tool that runs Black on Python code blocks in documentation files. It automatically formats Python code examples in Markdown, reStructuredText, and LaTeX files, helping maintain consistent code style across technical documentation, tutorials, and API documentation.

Package Information

  • Package Name: blacken-docs
  • Language: Python
  • Installation: pip install blacken-docs
  • Python Support: 3.9 to 3.13
  • Black Compatibility: 22.1.0+

Core Imports

import blacken_docs

For programmatic use:

from blacken_docs import format_str, format_file, main, CodeBlockError

Basic Usage

Command Line Usage

Process single files:

blacken-docs README.rst
blacken-docs docs/api.md

Process multiple files with glob patterns:

git ls-files -z -- '*.md' | xargs -0 blacken-docs
git ls-files -z -- '*.rst' | xargs -0 blacken-docs

Programmatic Usage

import blacken_docs
import black

# Format code blocks in a string
content = '''
```python
def hello(   ):
    print(  "hello world"  )

'''

Both black.Mode and black.FileMode work (they are equivalent)

black_mode = black.Mode(line_length=88) formatted_content, errors = blacken_docs.format_str(content, black_mode)

Format code blocks in a file

exit_code = blacken_docs.format_file( filename="README.md", black_mode=black_mode, skip_errors=False, rst_literal_blocks=False, check_only=False )

## Capabilities

### String Formatting

Formats Python code blocks within a string using Black formatter.

```python { .api }
def format_str(
    src: str,
    black_mode: black.FileMode,
    *,
    rst_literal_blocks: bool = False
) -> tuple[str, Sequence[CodeBlockError]]:
    """
    Format Python code blocks within documentation text.
    
    Parameters:
    - src: str - Input documentation text containing code blocks
    - black_mode: black.FileMode - Black formatting configuration
    - rst_literal_blocks: bool - Whether to format reStructuredText literal blocks (default: False)
    
    Returns:
    - tuple[str, Sequence[CodeBlockError]] - Formatted text and any parsing errors
    """

File Formatting

Formats Python code blocks in documentation files and writes changes back to disk.

def format_file(
    filename: str,
    black_mode: black.FileMode,
    skip_errors: bool,
    rst_literal_blocks: bool,
    check_only: bool
) -> int:
    """
    Format Python code blocks in a documentation file.
    
    Parameters:
    - filename: str - Path to documentation file to format
    - black_mode: black.FileMode - Black formatting configuration
    - skip_errors: bool - Whether to skip syntax errors and continue processing
    - rst_literal_blocks: bool - Whether to format reStructuredText literal blocks
    - check_only: bool - Whether to only check without modifying the file
    
    Returns:
    - int - Exit code (0=no changes needed, 1=changes made, 2=errors occurred)
    """

Command Line Interface

Main entry point for command-line usage supporting all Black formatting options plus additional features.

def main(argv: Sequence[str] | None = None) -> int:
    """
    Main CLI function that processes files with Python code blocks.
    
    Parameters:
    - argv: Sequence[str] | None - Command line arguments (uses sys.argv if None)
    
    Returns:
    - int - Exit code for the operation
    """

Error Handling

Error class for capturing code block parsing failures with location information.

class CodeBlockError:
    """Error information for code blocks that failed to parse or format."""
    
    def __init__(self, offset: int, exc: Exception) -> None:
        """
        Initialize error with location and exception details.
        
        Parameters:
        - offset: int - Character offset in source where error occurred
        - exc: Exception - The underlying parsing or formatting exception
        """
    
    offset: int  # Character position where error occurred
    exc: Exception  # The underlying exception

Supported Documentation Formats

Markdown

Python code blocks:

```python
def example():
    print("Hello, world!")
Python console blocks:
```markdown
```pycon
>>> def example():
...     print("Hello, world!")
...
>>> example()
Hello, world!
Control formatting with comments:
```markdown
<!-- blacken-docs:off -->
```python
# This code block will not be formatted
def   example( ):
    pass
<!-- blacken-docs:on -->
### reStructuredText

Python code blocks:
```rst
.. code-block:: python

    def example():
        print("Hello, world!")

Python console blocks:

.. code-block:: pycon

    >>> def example():
    ...     print("Hello, world!")
    ...

Literal blocks (with --rst-literal-blocks flag):

An example::

    def example():
        print("Hello, world!")

Control formatting with comments:

.. blacken-docs:off

.. code-block:: python

    # This code block will not be formatted
    def   example( ):
        pass

.. blacken-docs:on

LaTeX

Minted Python blocks:

\begin{minted}{python}
def example():
    print("Hello, world!")
\end{minted}

Minted Python console blocks:

\begin{minted}{pycon}
>>> def example():
...     print("Hello, world!")
...
\end{minted}

PythonTeX blocks:

\begin{pycode}
def example():
    print("Hello, world!")
\end{pycode}

Control formatting with comments:

% blacken-docs:off
\begin{minted}{python}
# This code block will not be formatted
def   example( ):
    pass
\end{minted}
% blacken-docs:on

Command Line Options

Black Pass-through Options

These options are passed directly to Black for code formatting:

  • -l, --line-length INT - Set maximum line length (default: 88)
  • --preview - Enable Black's preview features
  • -S, --skip-string-normalization - Skip string quote normalization
  • -t, --target-version {py39,py310,py311,py312,py313} - Set Python target version
  • --pyi - Format as Python stub (.pyi) file

blacken-docs Specific Options

  • --check - Check-only mode: don't modify files, just report if changes needed
  • -E, --skip-errors - Skip syntax errors from Black and continue processing
  • --rst-literal-blocks - Also format literal blocks in reStructuredText files

Examples

Format with custom line length:

blacken-docs -l 120 README.md

Check mode (don't modify files):

blacken-docs --check docs/*.rst

Skip errors and format literal blocks:

blacken-docs -E --rst-literal-blocks documentation.rst

Target specific Python version:

blacken-docs -t py311 examples.md

Integration Patterns

Pre-commit Hook

Add to .pre-commit-config.yaml:

repos:
  - repo: https://github.com/adamchainz/blacken-docs
    rev: "1.19.1"  # Use the latest version
    hooks:
      - id: blacken-docs
        additional_dependencies:
          - black==24.8.0  # Pin Black version

Programmatic Integration

import blacken_docs
import black
from pathlib import Path

def format_documentation_files(file_paths, line_length=88):
    """Format Python code blocks in multiple documentation files."""
    # Note: black.Mode is used internally by blacken-docs
    black_mode = black.Mode(line_length=line_length)
    results = {}
    
    for file_path in file_paths:
        try:
            exit_code = blacken_docs.format_file(
                filename=str(file_path),
                black_mode=black_mode,
                skip_errors=False,
                rst_literal_blocks=True,
                check_only=False
            )
            results[file_path] = {
                'success': exit_code != 2,
                'modified': exit_code == 1
            }
        except Exception as e:
            results[file_path] = {'success': False, 'error': str(e)}
    
    return results

# Usage
doc_files = Path('docs').glob('*.md')
results = format_documentation_files(doc_files)

Types

# From black module (external dependency)
class black.FileMode:
    """Black formatting configuration."""
    def __init__(
        self,
        target_versions: set[TargetVersion] = ...,
        line_length: int = 88,
        string_normalization: bool = True,
        is_pyi: bool = False,
        preview: bool = False
    ): ...

# Note: black.Mode is an alias for black.FileMode used in implementation
black.Mode = black.FileMode

class black.TargetVersion:
    """Python version targets for Black formatting."""
    PY39: TargetVersion
    PY310: TargetVersion  
    PY311: TargetVersion
    PY312: TargetVersion
    PY313: TargetVersion

# Standard library types used
from collections.abc import Sequence

Error Cases

Common error scenarios and handling:

  • Syntax Errors: Invalid Python code in blocks raises exceptions, captured in CodeBlockError objects
  • File Not Found: format_file raises standard Python file exceptions
  • Permission Errors: File write permissions cause standard I/O exceptions
  • Black Formatting Errors: Internal Black errors are captured and reported with line numbers

Use skip_errors=True in format_file or -E flag to continue processing despite syntax errors in code blocks.