A Python workflow project contains task classes, a Runner definition, and a tilebox.workflow.toml file. The Tilebox command-line tool uses these files to build a workflow release, discover the tasks it can execute, and make the release available to release runners after deployment.
Keep the project small and importable from its root. Release builds import the configured runner object, check that the Python runtime starts, and package the selected files into an immutable artifact.
Scaffold a workflow project
Section titled “Scaffold a workflow project”For a new Python workflow project, use the CLI to create the Tilebox workflow and scaffold the local files.
tilebox workflow init --name "Scene QA"The --name flag is optional. When omitted, the command derives the local project slug from the current directory name. The command converts the name to a slug, truncates it to at most 40 characters, creates the remote workflow, and writes the API-returned workflow slug to tilebox.workflow.toml.
tilebox workflow init creates tilebox.workflow.toml, pyproject.toml, and runner.py, adds the tilebox Python dependency, and runs uv sync to create the local environment and uv.lock file. It requires uv on PATH and aborts without changing the directory if any of tilebox.workflow.toml, pyproject.toml, runner.py, or uv.lock already exists.
The generated project is intentionally small. Edit runner.py directly for prototypes, or move task code into a package as the workflow grows.
Manual project structure
Section titled “Manual project structure”Use a layout where task code and the runner definition are importable from the project root.
Directorymy-workflow/
- pyproject.toml
- uv.lock
- tilebox.workflow.toml
Directorymy_workflow/
__init__.py- tasks.py
- runner.py
Define the Python project
Section titled “Define the Python project”Use a minimal pyproject.toml with the dependencies your workflow needs. For this example, only the Tilebox Python package is required.
[project]name = "my-workflow"version = "0.1.0"requires-python = ">=3.11"dependencies = [ "tilebox",]Create the package directory and an empty __init__.py file so Python can import my_workflow.runner from the project root.
mkdir -p my_workflowtouch my_workflow/__init__.pyuv lockDefine tasks
Section titled “Define tasks”Put task classes in a module that can be imported during release validation.
# my_workflow/tasks.pyfrom tilebox.workflows import ExecutionContext, Task
class ProcessScene(Task): scene_id: str
@staticmethod def identifier() -> tuple[str, str]: return "tilebox.com/example/ProcessScene", "v1.0"
def execute(self, context: ExecutionContext) -> None: context.current_task.display = f"ProcessScene({self.scene_id})" context.logger.info("Processing scene", scene_id=self.scene_id)Use explicit identifiers for workflow code that will be published. A stable identifier lets existing jobs continue to run after refactors and compatible bug fixes.
Define the runner
Section titled “Define the runner”Create a module that exports a Runner object. This object defines the task registrations for the workflow, and release builds import it during validation.
# my_workflow/runner.pyfrom tilebox.workflows import Runnerfrom tilebox.workflows.cache import LocalFileSystemCache
from my_workflow.tasks import ProcessScene
runner = Runner( tasks=[ProcessScene], cache=LocalFileSystemCache(),)Configure the workflow release
Section titled “Configure the workflow release”Point tilebox.workflow.toml at the exported Runner object and include the files required by the release runner.
[workflow]slug = "my-workflow"root = "."runner = "my_workflow.runner:runner"
[build]include = [ "pyproject.toml", "uv.lock", "my_workflow/**",]exclude = [ ".venv/**", "**/__pycache__/**", "**/*.pyc", ".pytest_cache/**",]use_gitignore = trueThe Tilebox command-line tool imports the runner object during build-release and publish-release, discovers its task identifiers, and records them in the workflow release. A release runner later loads the release artifact and invokes the Python runtime through the command-line tool.
Keep release artifacts small
Section titled “Keep release artifacts small”Include source code, lock files, and small configuration. Exclude local virtual environments, test caches, downloaded provider data, model checkpoints, generated outputs, and other large runtime artifacts.
If a task needs a large model or reference file, fetch it lazily at runtime and cache it in a deterministic runner-local path such as ~/.cache/tilebox/.... The workflow should still work when a release runner starts with an empty cache.