Add your description here
Project description
bakefile
An OOP task runner in Python. Like a Makefile, but with tasks as Python class methods—so you can inherit, compose, and reuse them across projects.
Why bakefile?
- Reusable - Makefile/Justfile work well, but reusing tasks across projects is hard. bakefile uses OOP class methods—inherit, compose, and share them
- Python - Use Python instead of DSL syntax. Access the full ecosystem with Python's language features, tooling, and type safety (ruff/ty)—with subprocess support for normal CLI commands
- Language-agnostic - Write tasks in Python, run commands for any language (Go, Rust, JS, etc.)
Installation
Install via pip:
pip install bakefile
Or via uv:
uv add bakefile # as a project dependency
uv tool install bakefile # as a global tool
Quick Start
Create a file named bakefile.py:
from bake import Bakebook, command, console
class MyBakebook(Bakebook):
@command()
def build(self) -> None:
console.echo("Building...")
# Use self.ctx to run commands
self.ctx.run("cargo build")
bakebook = MyBakebook()
@bakebook.command()
def hello(name: str = "world"):
console.echo(f"Hello {name}!")
Tip: Or generate a bakefile automatically:
bakefile init # Basic bakefile
bakefile init --inline # With PEP 723 standalone dependencies
Run your tasks:
bake hello # Hello world!
bake hello --name Alice # Hello Alice!
bake build # Building...
Core Concepts
Two CLIs
bakefile provides two command-line tools:
bake- Runs tasks from yourbakefile.pybakefile- Manages yourbakefile.py(init, add-inline, lint, find-python, export, sync, lock, add, pip)
Detailed CLI documentation in Usage.
Bakebook
A class in bakefile.py that holds your tasks:
- Inherit and reuse - Create base classes with common tasks, extend them across projects
- Extends Pydantic's
BaseSettings- Define configuration as class attributes - Uses
@command()decorator - Same syntax as Typer for defining CLI commands - Provides
ctx.run()- Execute CLI commands (built on Python's subprocess) from your tasks
from bake import Bakebook, command, Context, console
from pydantic import Field
from typing import Annotated
import typer
class MyBakebook(Bakebook):
# Pydantic configuration
api_url: str = Field(default="https://api.example.com", env="API_URL")
@command()
def fetch(self) -> None:
# Run CLI commands via self.ctx
self.ctx.run(f"curl {self.api_url}")
bakebook = MyBakebook()
# Standalone functions also work
@bakebook.command()
def test(
verbose: Annotated[bool, typer.Option(False, "--verbose", "-v")] = False,
):
if verbose:
console.echo("Running tests...")
bakebook.ctx.run("pytest")
PEP 723 Support
bakefile supports PEP 723 inline script metadata—your bakefile.py can declare its own dependencies. Add PEP 723 metadata to an existing bakefile with bakefile add-inline:
# /// script
# requires-python = ">=3.14"
# dependencies = [
# "bakefile>=0.0.0",
# ]
# ///
from bake import Bakebook, command, console
bakebook = Bakebook()
@bakebook.command()
def hello():
console.echo("Hello from standalone bakefile!")
Use case: Ideal for non-Python projects without pyproject.toml. For Python projects, add bakefile to your project's dependencies instead.
Usage
Bakebook API
Creating a Bakebook
Tip: Generate a bakefile automatically with bakefile init or bakefile add-inline.
Create a bakebook by inheriting from Bakebook or instantiating it:
from bake import Bakebook
bakebook = Bakebook()
@command Decorator
- Pattern 1: Before instantiating - Use
@command()on class methods - Pattern 2: After instantiating - Use
@bakebook.command()on standalone functions - Accepts all Typer options -
name,help,deprecated, etc.
from bake import Bakebook, command, console
from typing import Annotated
import typer
# Pattern 1: On class (use self.ctx for context access)
class MyBakebook(Bakebook):
@command()
def task1(self) -> None:
console.echo("Task 1")
self.ctx.run("echo 'Task 1 complete'")
bakebook = MyBakebook()
# Pattern 2: On instance (use bakebook.ctx for context access)
@bakebook.command(name="deploy", help="Deploy application")
def deploy(
env: Annotated[str, typer.Option("dev", help="Environment to deploy")],
):
console.echo(f"Deploying to {env}...")
bakebook.ctx.run(f"kubectl apply -f {env}.yaml")
Context API
The Bakebook class provides a .ctx property for accessing CLI context:
class MyBakebook(Bakebook):
@command()
def my_command(self) -> None:
# Run a command
self.ctx.run("echo hello")
# Run with options
self.ctx.run(
"pytest",
capture_output=False, # Stream to terminal
check=True, # Raise on error
cwd="/tmp", # Working directory
env={"KEY": "value"}, # Environment variables
)
# Run a multi-line script
self.ctx.run_script(
title="Setup",
script="""
echo "Step 1"
echo "Step 2"
""",
)
Pydantic Settings
Bakebooks extend Pydantic's BaseSettings for configuration:
from bake import Bakebook
from pydantic import Field
class MyBakebook(Bakebook):
# Defaults
database_url: str = "sqlite:///db.sqlite3"
# With environment variable mapping
api_key: str = Field(default="default-key", env="API_KEY")
# With validation
port: int = Field(default=8000, ge=1, le=65535)
Settings are loaded from environment variables, .env files, or defaults.
bake CLI - Running Tasks
The bake command runs tasks from your bakefile.py. Run bake --help to see all available commands and options.
Basic Execution
bake <command> [args]
bake hello
bake build
bake test --verbose
Dry-Run Mode
Preview what would happen without executing:
bake -n build
bake --dry-run deploy
Verbosity Levels
Control output verbosity:
bake build # Silent (errors only)
bake -v build # Info level
bake -vv build # Debug level
Chaining Commands
Run multiple commands sequentially:
bake -c lint test build
If any command fails, the chain stops.
Options
Override defaults when running bake:
bake -f tasks.py build # Custom filename
bake -b my_bakebook build # Custom bakebook object name
bake -C /path/to/project build # Run from different directory
bakefile CLI - Managing bakefile.py
The bakefile command (short: bf) manages your bakefile.py.
init
Create a new bakefile.py:
bakefile init # Basic bakefile
bakefile init --inline # With PEP 723 inline metadata
bakefile init --force # Force overwrite existing bakefile
add-inline
Add PEP 723 inline metadata to an existing bakefile:
bakefile add-inline
lint
Lint bakefile.py (or entire project) with ruff and ty:
bakefile lint # Lint bakefile.py and all Python files
bakefile lint --only-bakefile # Lint only bakefile.py
bakefile lint --no-ty # Skip type checking
uv-based commands (PEP 723 bakefile.py only)
Convenience wrappers around uv commands with --script bakefile.py added. For PEP 723 bakefile.py files only. For normal Python projects, use your preferred dependency manager (pip, poetry, uv, etc.).
bakefile sync # = uv sync --script bakefile.py
bakefile lock # = uv lock --script bakefile.py
bakefile add requests # = uv add --script bakefile.py requests
bakefile pip install # = uv pip install --python <bakefile-python-path>
find-python
Find the Python interpreter path for the bakefile:
bakefile find-python
export
Export bakebook variables to external formats:
bakefile export # Shell format (default)
bakefile export -f sh # Shell format
bakefile export -f dotenv # .env format
bakefile export -f json # JSON format
bakefile export -f yaml # YAML format
bakefile export -o config.sh # Write to file
# Examples:
bakefile export -f dotenv -o .env # .env file
bakefile export -f json -o config.json # JSON file
bakelib - Optional Helpers
bakelib is an optional collection of opinionated helpers built on top of Bakebook. Includes Spaces (pre-configured tasks) and Environ (multi-environment support).
Install with:
pip install bakefile[lib]
Note: bakelib is optional—you can use bakefile without it. Create your own Bakebook classes if you prefer different conventions.
PythonSpace
PythonSpace provides common tasks for Python projects:
from bakelib import PythonSpace
bakebook = PythonSpace()
Available commands:
bake lint- Run prettier, toml-sort, ruff format, ruff check, ty, deptrybake test- Run pytest with coverage ontests/unit/bake test-integration- Run integration tests fromtests/integration/bake test-all- Run all testsbake clean- Clean gitignored files (with exclusions)bake clean-all- Clean all gitignored filesbake setup-dev- Setup Python development environmentbake tools- List development toolsbake update- Upgrade dependencies (includes uv lock --upgrade)
Creating Custom Spaces
Create custom spaces by inheriting from BaseSpace:
from bakelib import BaseSpace
class MySpace(BaseSpace):
def test(self) -> None:
self.ctx.run("npm test")
bakebook = MySpace()
BaseSpace provides these tasks (override as needed):
lint()- Run prettierclean()/clean_all()- Clean gitignored filessetup_dev()- Setup development environmenttools()- List development toolsupdate()- Upgrade dependencies
Multi-Environment Bakebooks
For projects with multiple environments (dev, staging, prod), use environment bakebooks:
from bakelib.environ import (
DevEnvBakebook,
StagingEnvBakebook,
ProdEnvBakebook,
get_bakebook,
)
bakebook_dev = DevEnvBakebook()
bakebook_staging = StagingEnvBakebook()
bakebook_prod = ProdEnvBakebook()
# Select bakebook based on ENV environment variable
bakebook = get_bakebook([bakebook_dev, bakebook_staging, bakebook_prod])
ENV=prod bake deploy # Uses prod bakebook
ENV=dev bake deploy # Uses dev bakebook
bake deploy # Defaults to dev (lowest priority)
Create custom environments by inheriting from BaseEnv:
from bakelib.environ import BaseEnv, EnvBakebook
class MyEnv(BaseEnv):
ENV_ORDER = ["dev", "sit", "qa", "uat", "prod"]
class MyEnvBakebook(EnvBakebook):
env_: MyEnv = MyEnv("local")
For more details, see the bakelib source.
Development
Environment Setup
Clone and install the project:
git clone https://github.com/wislertt/bakefile.git
cd bakefile
# Install bakefile as a global tool
uv tool install bakefile
# Setup development environment (macOS only)
# Installs brew, bun, uv, and pre-commit hooks
bake setup-dev
# Verify development environment is setup correctly
# Checks tool locations and runs lint + test
bake assert-setup-dev
Note: bake setup-dev only supports macOS. For other platforms, run bake --dry-run setup-dev to see the commands and follow platform-specific alternatives.
The project uses uv for dependency management.
Testing
Run tests using the bake commands:
bake test # Unit tests (fast)
bake test-integration # Integration tests (slow, real subprocess)
bake test-all # All tests with coverage
Code Quality
Run linters and formatters before committing:
bake lint # Run prettier, toml-sort, ruff format, ruff check, ty, deptry
Verification workflow:
- Make changes
- Run
bake lintto check code quality - Run
bake testto verify unit tests pass - Commit when both pass
Contributing
Contributions are welcome! Please see CLAUDE.md for development guidelines, including:
- Project structure and testing conventions
- Code quality standards
- Development workflow
License
Licensed under the Apache License 2.0. See LICENSE for the full text.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file bakefile-0.0.40.tar.gz.
File metadata
- Download URL: bakefile-0.0.40.tar.gz
- Upload date:
- Size: 58.9 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.10.11 {"installer":{"name":"uv","version":"0.10.11","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
6d6ea6b1fefeda88f72514446c0542f1c6ea90485de73cb978cb2bb9fcf9afe9
|
|
| MD5 |
26a0a7f1bf213261500c1b2d22847107
|
|
| BLAKE2b-256 |
2092f7452ba80ae68a42321ac2167b75ee28c7d6c5ceddd4f92e49682feaaeeb
|
File details
Details for the file bakefile-0.0.40-py3-none-any.whl.
File metadata
- Download URL: bakefile-0.0.40-py3-none-any.whl
- Upload date:
- Size: 87.6 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: uv/0.10.11 {"installer":{"name":"uv","version":"0.10.11","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
59d8ceed13b92fc432e223b8dcd1f9b714c12fe9fff1d8f6688e377d9c11810c
|
|
| MD5 |
75c884d32401bd3db4838a35d853685b
|
|
| BLAKE2b-256 |
250e8f453592f17e2d61147faee615ec68575ed5ad265eb41b18ce16b5af6e65
|