CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/pypi-commitizen

Python commitizen client tool for standardized commit conventions and automated version management

Pending

Quality

Pending

Does it follow best practices?

Impact

Pending

No eval scenarios have been run

Overview
Eval results
Files

git-operations.mddocs/

Git Operations

Extensive git integration including commit creation, tag management, branch operations, repository status checking, and smart file handling with EOL support. Commitizen provides comprehensive git operations that handle edge cases and provide robust integration with git workflows.

Capabilities

Git Object Types

Core data structures representing git objects with metadata.

class GitObject:
    """Base class for git objects."""
    
    def __init__(self, rev: str):
        """
        Initialize git object.
        
        Parameters:
        - rev: Git revision identifier
        """

class GitCommit(NamedTuple):
    """Git commit representation with metadata."""
    rev: str           # Commit SHA hash
    title: str         # Commit title (first line)
    body: str          # Commit body (remaining lines)
    author: str        # Author name
    author_email: str  # Author email
    date: str          # Commit date (ISO format)

class GitTag(NamedTuple):
    """Git tag representation with metadata."""
    name: str          # Tag name
    rev: str           # Tagged commit SHA
    date: str          # Tag creation date

End-of-Line Handling

Support for different end-of-line formats in text files.

class EOLTypes(Enum):
    """End-of-line type enumeration."""
    LF = "lf"         # Unix line endings (\n)
    CRLF = "crlf"     # Windows line endings (\r\n)  
    NATIVE = "native" # Platform-specific line endings

Repository Operations

Repository Status and Validation

Check repository state and validate git project status.

def is_git_project(path: str = ".") -> bool:
    """
    Check if directory is a git repository.
    
    Parameters:
    - path: Directory path to check
    
    Returns:
    True if directory contains a git repository
    """

def find_git_project_root(path: str = ".") -> Path:
    """
    Find the root directory of the git repository.
    
    Searches upward from the given path to find .git directory.
    
    Parameters:
    - path: Starting directory path
    
    Returns:
    Path to git repository root
    
    Raises:
    NotAGitProjectError: If not in a git repository
    """

def is_staging_clean(check_untracked_files: bool = False) -> bool:
    """
    Check if git staging area is clean.
    
    Parameters:
    - check_untracked_files: Include untracked files in check
    
    Returns:
    True if staging area has no changes
    """

Basic Git Commands

File Operations

Add files to staging area and manage working directory.

def add(pathspecs: list[str]) -> Command:
    """
    Add files to git staging area.
    
    Parameters:
    - pathspecs: List of file paths or patterns to add
    
    Returns:
    Command execution result
    
    Raises:
    GitCommandError: If git add command fails
    """

Commit Operations

Create git commits with various options and validation.

def commit(message: str, args: str = "") -> Command:
    """
    Create git commit with message.
    
    Parameters:
    - message: Commit message text
    - args: Additional git commit arguments
    
    Returns:
    Command execution result
    
    Raises:
    GitCommandError: If commit creation fails
    CommitMessageLengthError: If message exceeds limits
    """

Command Execution

Execute shell commands with proper error handling and result capture.

def run(cmd: str, env: dict[str, str] | None = None) -> Command:
    """
    Execute shell command and return result.
    
    Parameters:
    - cmd: Shell command to execute
    - env: Environment variables for command execution
    
    Returns:
    Command object with return_code, stdout, and stderr
    
    Raises:
    CommandExecutionError: If command execution fails
    """

Tag Operations

Create and manage git tags with signing support.

def tag(
    name: str,
    message: str = "",
    signed: bool = False,
    annotated: bool = True
) -> Command:
    """
    Create git tag.
    
    Parameters:
    - name: Tag name
    - message: Tag message (for annotated tags)
    - signed: Create GPG signed tag
    - annotated: Create annotated tag (default)
    
    Returns:
    Command execution result
    
    Raises:
    GitCommandError: If tag creation fails
    """

def tag_exist(tag: str) -> bool:
    """
    Check if git tag exists.
    
    Parameters:
    - tag: Tag name to check
    
    Returns:
    True if tag exists in repository
    """

def is_signed_tag(tag_name: str) -> bool:
    """
    Check if tag is GPG signed.
    
    Parameters:
    - tag_name: Name of tag to check
    
    Returns:
    True if tag has valid GPG signature
    """

def get_latest_tag_name(pattern: str = "*") -> str | None:
    """
    Get the most recent tag name.
    
    Parameters:
    - pattern: Tag name pattern filter
    
    Returns:
    Latest tag name or None if no tags exist
    """

Information Retrieval

Commit History

Retrieve and analyze commit history with filtering options.

def get_commits(
    start: str = "",
    end: str = "",
    rev: str = "",
    paths: list[str] = []
) -> list[GitCommit]:
    """
    Get git commit history.
    
    Parameters:
    - start: Starting revision (exclusive)
    - end: Ending revision (inclusive)  
    - rev: Specific revision or range
    - paths: Limit to changes in specific paths
    
    Returns:
    List of GitCommit objects in chronological order
    
    Raises:
    GitCommandError: If git log command fails
    """

def get_filenames_in_commit(rev: str) -> list[str]:
    """
    Get list of files changed in specific commit.
    
    Parameters:
    - rev: Commit revision identifier
    
    Returns:
    List of file paths modified in the commit
    """

Tag Information

Retrieve tag information and metadata.

def get_tags() -> list[GitTag]:
    """
    Get all git tags in repository.
    
    Returns:
    List of GitTag objects sorted by creation date
    
    Raises:
    GitCommandError: If git tag command fails
    """

File Handling

Smart File Operations

Intelligent file handling with git configuration awareness.

def smart_open(
    filename: str,
    encoding: str = "utf-8",
    eol: str = ""
) -> TextIOWrapper:
    """
    Open file with git-aware line ending handling.
    
    Respects git configuration for core.autocrlf and core.eol settings.
    Handles different line ending conventions appropriately.
    
    Parameters:
    - filename: Path to file
    - encoding: Text encoding (default: utf-8)
    - eol: End-of-line format override
    
    Returns:
    Text file handle with appropriate line ending handling
    
    Raises:
    FileNotFoundError: If file doesn't exist
    UnicodeDecodeError: If encoding is incorrect
    """

Usage Examples

Basic Git Operations

from commitizen import git

# Check if in git repository
if git.is_git_project():
    print("In git repository")
    root = git.find_git_project_root()
    print(f"Repository root: {root}")

# Check staging area status
if git.is_staging_clean():
    print("No staged changes")

# Add files and commit
git.add(["src/", "tests/"])
result = git.commit("feat: add new feature")
print(f"Commit created: {result.return_code == 0}")

# Create signed tag
git.tag("v1.0.0", "Release version 1.0.0", signed=True)

Working with Commit History

from commitizen import git

# Get all commits since last tag
commits = git.get_commits(start="v0.9.0", end="HEAD")

for commit in commits:
    print(f"{commit.rev[:8]}: {commit.title}")
    print(f"Author: {commit.author} <{commit.author_email}>")
    print(f"Date: {commit.date}")
    
    # Get files changed in commit
    files = git.get_filenames_in_commit(commit.rev)
    print(f"Files: {', '.join(files)}")
    print()

# Get commits in specific path
src_commits = git.get_commits(
    start="v0.9.0",
    end="HEAD", 
    paths=["src/"]
)
print(f"Commits affecting src/: {len(src_commits)}")

Tag Management

from commitizen import git

# Get all tags
tags = git.get_tags()
for tag in tags:
    print(f"{tag.name} -> {tag.rev[:8]} ({tag.date})")

# Check if tag exists
if git.tag_exist("v1.0.0"):
    print("Tag v1.0.0 exists")
    
    # Check if signed
    if git.is_signed_tag("v1.0.0"):
        print("Tag is GPG signed")

# Get latest tag
latest = git.get_latest_tag_name()
print(f"Latest tag: {latest}")

# Get latest tag matching pattern
latest_stable = git.get_latest_tag_name("v*.*.*")
print(f"Latest stable: {latest_stable}")

File Operations with EOL Handling

from commitizen import git

# Open file with git-aware line ending handling
with git.smart_open("CHANGELOG.md", encoding="utf-8") as f:
    content = f.read()

# The file is opened with appropriate line endings based on:
# - Git configuration (core.autocrlf, core.eol)
# - Platform defaults
# - Repository .gitattributes settings

# Write file with consistent line endings
with git.smart_open("VERSION", encoding="utf-8", eol="lf") as f:
    f.write("1.0.0\n")

Error Handling

from commitizen import git
from commitizen.exceptions import (
    NotAGitProjectError,
    GitCommandError, 
    CommitMessageLengthError
)

try:
    # Check repository status
    if not git.is_git_project():
        raise NotAGitProjectError("Not in git repository")
    
    # Attempt to commit
    result = git.commit("Very long commit message that exceeds the recommended length...")
    
except NotAGitProjectError as e:
    print(f"Git error: {e}")
    
except CommitMessageLengthError as e:
    print(f"Commit message too long: {e}")
    
except GitCommandError as e:
    print(f"Git command failed: {e}")
    print(f"Return code: {e.return_code}")
    print(f"Error output: {e.stderr}")

Advanced Git Integration

from commitizen import git
from commitizen.cmd import run

# Custom git operations using command runner
def get_current_branch() -> str:
    """Get current git branch name."""
    result = run("git branch --show-current")
    if result.return_code != 0:
        raise GitCommandError("Failed to get current branch")
    return result.out.strip()

def get_remote_url() -> str:
    """Get remote origin URL."""
    result = run("git remote get-url origin")
    if result.return_code != 0:
        raise GitCommandError("Failed to get remote URL")
    return result.out.strip()

# Repository information
try:
    branch = get_current_branch()
    remote = get_remote_url()
    
    print(f"Current branch: {branch}")
    print(f"Remote URL: {remote}")
    
    # Check if branch is up to date
    if git.is_staging_clean():
        print("Working directory is clean")
    
    # Get commits on current branch
    commits = git.get_commits(rev=f"origin/{branch}..HEAD")
    print(f"Commits ahead: {len(commits)}")
    
except GitCommandError as e:
    print(f"Git operation failed: {e}")

Git Hook Integration

from commitizen import git
from pathlib import Path

def install_commit_msg_hook():
    """Install commit message validation hook."""
    hooks_dir = git.find_git_project_root() / ".git" / "hooks"
    hook_file = hooks_dir / "commit-msg"
    
    hook_content = """#!/bin/sh
# Commitizen commit message validation
exec commitizen check --commit-msg-file $1
"""
    
    hook_file.write_text(hook_content)
    hook_file.chmod(0o755)
    
    print("Commit message hook installed")

def install_pre_push_hook():
    """Install pre-push validation hook."""
    hooks_dir = git.find_git_project_root() / ".git" / "hooks"  
    hook_file = hooks_dir / "pre-push"
    
    hook_content = """#!/bin/sh
# Commitizen branch validation
exec commitizen check --rev-range origin/main..HEAD
"""
    
    hook_file.write_text(hook_content)
    hook_file.chmod(0o755)
    
    print("Pre-push hook installed")

Install with Tessl CLI

npx tessl i tessl/pypi-commitizen

docs

commands.md

configuration.md

git-operations.md

index.md

plugins.md

version-management.md

tile.json