Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
name: CI

on:
push:
branches: [main]
pull_request:
branches: [main]

jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4

- name: Install uv
uses: astral-sh/setup-uv@v5

- name: Run template tests
run: make test
5 changes: 5 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
.claude/
.venv/
.pytest_cache/
__pycache__/
*.pyc
28 changes: 28 additions & 0 deletions AGENTS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
# Agent guide for copier-minimal-python

This is a copier template for Python projects. It generates new Python projects with uv, pytest, ruff, and optional CLI support.

## Repository structure

- `copier.yml` - Template configuration and questions
- `template/` - Template files that get copied to new projects (uses Jinja2 templating)
- `tests/` - Integration tests for the template itself
- `Makefile` - Development commands for the template repo

## Development

- Run `make test` to verify the template generates correctly
- The test creates a temporary project using copier with default values and checks basic structure

## How the template works

- `_subdirectory: template` in copier.yml tells copier to source files from `template/`
- `_templates_suffix: ""` means all files are templates (no `.jinja` extension needed)
- Template variables like `{{ project_name }}` are replaced during generation
- Conditional blocks like `{% if has_cli %}` control optional features

## Making changes

1. Edit files in `template/` to change what gets generated
2. Edit `copier.yml` to add/modify template questions
3. Run `make test` to verify changes work
4 changes: 4 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
.PHONY: test

test:
uv run pytest tests/ -v
2 changes: 2 additions & 0 deletions copier.yml
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
_min_copier_version: "9.0.0"

_subdirectory: template

_answers_file: .copier-answers.yml

_templates_suffix: ""
Expand Down
12 changes: 12 additions & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
[project]
name = "copier-minimal-python"
version = "0.1.0"
description = "A minimal copier template for Python projects"
requires-python = ">=3.12"

[dependency-groups]
dev = [
"copier>=9.0.0",
"jinja2-time>=0.2.0",
"pytest>=8.0.0",
]
41 changes: 41 additions & 0 deletions tests/test_template.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
"""Integration tests for the copier template."""

import subprocess
import tempfile
from pathlib import Path


def test_template_generates_with_defaults():
"""Test that the template generates successfully with default values."""
template_dir = Path(__file__).parent.parent

with tempfile.TemporaryDirectory() as tmpdir:
dest = Path(tmpdir) / "test-project"

result = subprocess.run(
[
"uv",
"run",
"copier",
"copy",
"--defaults",
"--trust",
"--data",
"project_name=test-project",
"--data",
"description=A test project",
"--data",
"author_name=Test Author",
"--data",
"repo_owner=test-owner",
str(template_dir),
str(dest),
],
capture_output=True,
text=True,
)

assert result.returncode == 0, f"copier failed: {result.stderr}"
assert dest.exists(), "Destination directory was not created"
assert (dest / "pyproject.toml").exists(), "pyproject.toml was not generated"
assert (dest / "src" / "test_project").exists(), "Package directory was not created"
515 changes: 515 additions & 0 deletions uv.lock

Large diffs are not rendered by default.