CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/pypi-copier

A library for rendering project templates from Git repositories with Jinja2 templating and interactive questionnaires.

Pending

Quality

Pending

Does it follow best practices?

Impact

Pending

No eval scenarios have been run

Overview
Eval results
Files

advanced-usage.mddocs/

Advanced Usage

Advanced copier functionality using the Worker class for fine-grained control over template processing and the Settings class for user configuration management.

Capabilities

Worker Class

The main copier process state manager that provides full control over template operations.

class Worker:
    """Copier process state manager and context manager."""
    
    def __init__(
        self,
        src_path: str | None = None,
        dst_path: Path = Path(),
        answers_file: RelativePath | None = None,
        vcs_ref: str | VcsRef | None = None,
        data: AnyByStrDict = None,
        settings: Settings = None,
        exclude: Sequence[str] = (),
        use_prereleases: bool = False,
        skip_if_exists: Sequence[str] = (),
        cleanup_on_error: bool = True,
        defaults: bool = False,
        user_defaults: AnyByStrDict = None,
        overwrite: bool = False,
        pretend: bool = False,
        quiet: bool = False,
        conflict: Literal["inline", "rej"] = "inline",
        context_lines: PositiveInt = 3,
        unsafe: bool = False,
        skip_answered: bool = False,
        skip_tasks: bool = False
    ): ...
    
    def run_copy(self) -> None: ...
    def run_update(self) -> None: ...
    def run_recopy(self) -> None: ...
    
    def __enter__(self) -> Worker: ...
    def __exit__(
        self,
        type: type[BaseException] | None,
        value: BaseException | None,
        traceback: TracebackType | None
    ) -> None: ...
    
    # Properties
    answers_relpath: Path
    all_exclusions: Sequence[str]
    jinja_env: YieldEnvironment
    match_exclude: Callable[[Path], bool]
    match_skip: Callable[[Path], bool]
    resolved_vcs_ref: str | None
    subproject: Subproject
    template: Template
    template_copy_root: Path

Worker Configuration Parameters

The Worker class accepts these configuration parameters:

Template and Destination:

  • src_path (str | None): Template source path (local or Git URL)
  • dst_path (Path): Destination path where to render the subproject
  • answers_file (RelativePath | None): Path to answers file relative to dst_path
  • vcs_ref (str | VcsRef | None): VCS tag/commit/branch to use

Data and Settings:

  • data (AnyByStrDict): Answers to the questionnaire
  • settings (Settings): User settings configuration
  • user_defaults (AnyByStrDict): User default overrides for questions

File Processing:

  • exclude (Sequence[str]): File exclusion patterns
  • skip_if_exists (Sequence[str]): File skip patterns
  • use_prereleases (bool): Consider prereleases when detecting latest version

Behavior Control:

  • cleanup_on_error (bool): Delete dst_path if there's an error
  • defaults (bool): Use default answers to questions without prompting
  • overwrite (bool): Overwrite files that already exist without asking
  • pretend (bool): Produce no real rendering (dry run)
  • quiet (bool): Disable all output
  • unsafe (bool): Allow usage of unsafe templates
  • skip_answered (bool): Skip questions that have already been answered
  • skip_tasks (bool): Skip template tasks execution

Update/Conflict Resolution:

  • conflict (Literal["inline", "rej"]): Conflict resolution mode
  • context_lines (PositiveInt): Lines of context for conflict resolution

Usage examples:

from copier import Worker

# Context manager usage (recommended)
with Worker(
    src_path="https://github.com/user/template.git",
    dst_path="./my-project",
    vcs_ref="v2.0.0",
    data={"project_name": "MyApp"},
    overwrite=True,
    quiet=False
) as worker:
    worker.run_copy()
    print(f"Generated from: {worker.template}")

# Direct instantiation
worker = Worker(
    src_path="./template",
    dst_path="./project",
    defaults=True,
    pretend=True  # Dry run
)
result = worker.run_copy()

# Chaining operations
worker = Worker(dst_path="./existing-project")
worker.run_update()
# Later...
worker.run_recopy()

Settings Management

User settings configuration for copier defaults and trusted templates.

class Settings:
    """User settings configuration model."""
    
    defaults: dict[str, Any]
    trust: set[str]
    
    @classmethod
    def from_file(cls, path: StrOrPath | None = None) -> Settings:
        """
        Load settings from a YAML file.
        
        Parameters:
        - path (StrOrPath, optional): Path to settings file
        
        Returns:
        Settings: Loaded settings instance
        """
    
    def is_trusted(self, url: str) -> bool:
        """
        Check if a template URL is trusted.
        
        Parameters:
        - url (str): Template URL to check
        
        Returns:
        bool: True if URL is trusted
        """
    
    def normalize(self) -> dict[str, Any]:
        """
        Normalize settings data for serialization.
        
        Returns:
        dict: Normalized settings data
        """

Settings Configuration

Settings can be loaded from a YAML file (default location determined by COPIER_SETTINGS_PATH environment variable):

# ~/.config/copier/settings.yml
defaults:
  author: "John Doe"
  license: "MIT"
  python_version: "3.9"

trust:
  - "https://github.com/trusted-org/*"
  - "https://gitlab.com/my-company/*"

Usage examples:

from copier import Settings
import os

# Load from default location
settings = Settings.from_file()

# Load from specific file
settings = Settings.from_file("./copier-settings.yml")

# Check if template is trusted
is_safe = settings.is_trusted("https://github.com/trusted-org/template.git")

# Use settings with Worker
os.environ["COPIER_SETTINGS_PATH"] = "./my-settings.yml"
worker = Worker(
    src_path="template/",
    dst_path="project/",
    # Settings will be automatically loaded
)

Advanced Template Processing

Working with template metadata and processing details:

from copier import Worker

# Access template information
with Worker("template/", "project/") as worker:
    worker.run_copy()
    
    # Template metadata
    print(f"Template path: {worker.template.local_abspath}")
    print(f"Template ref: {worker.template.ref}")
    print(f"Template version: {worker.template.version}")
    print(f"Template commit: {worker.template.commit}")
    
    # Processing results
    print(f"Answers used: {worker.answers.combined}")
    print(f"Destination: {worker.subproject.local_abspath}")
    print(f"Answers file: {worker.answers_relpath}")

# Custom conflict resolution
worker = Worker(
    src_path="template/",
    dst_path="existing-project/",
    conflict="rej",  # Create .rej files for conflicts
    context_lines=5  # Show 5 lines of context
)
worker.run_update()

Environment Variable Configuration

Copier respects several environment variables:

  • COPIER_SETTINGS_PATH: Path to settings file
  • GIT_*: Git configuration variables
  • TMPDIR: Temporary directory for processing
import os
from copier import Worker

# Configure via environment
os.environ["COPIER_SETTINGS_PATH"] = "/custom/settings.yml"
os.environ["TMPDIR"] = "/fast/ssd/tmp"

worker = Worker("template/", "project/")
worker.run_copy()

Install with Tessl CLI

npx tessl i tessl/pypi-copier

docs

advanced-usage.md

core-operations.md

error-handling.md

index.md

types-enums.md

tile.json