uv-build (Python)

The host owns pyproject.toml and points uv's own build backend at the generated package with module-root and module-name.

Language Python
Build system uv-build
Idiom B -- your project owns the manifest
Regeneration None -- regeneration is an explicit step

Notes

uv_build wants the package's parent directory as module-root and the package name as module-name, rather than a path to the package itself. Otherwise this is the hatchling recipe with a different backend block.

Every Python recipe builds its own virtual environment and lets pip fetch the build backend into it. That is correct isolation regardless, and on a distribution that marks its interpreter externally managed (PEP 668) -- which the toolshed image does -- nothing else works.

Prerequisites

Tool Why
python3 creates the virtual environment the backend installs into

Commands

Run these from the recipe directory, with dsdl/ and src/ copied alongside it. This is the exact sequence CI runs.

# generate
dsdlc --target-language python --versioned-type-names dsdl/lanyard --py-package lanyard --outdir generated
# virtual environment
python3 -m venv .venv
# install
.venv/bin/pip install -q .
# round-trip
.venv/bin/python src/python/test_roundtrip.py

The types this builds

The whole lanyard namespace -- twenty-four definitions, browsable from the showroom overview, where each one is paired with its wire-layout facts and a declaration excerpt in every language.

The build files

pyproject.toml

# The host owns this file. dsdlc also wrote a pyproject.toml into generated/, declaring setuptools;
# it is inert here; only the setuptools recipe uses it.
[build-system]
requires = ["uv_build>=0.9,<0.10"]
build-backend = "uv_build"

[project]
name = "lanyard"
version = "0.1.0"
description = "Host project consuming generated DSDL types"
requires-python = ">=3.10"

# Point the backend at the package dsdlc generated. Everything under it -- the namespace packages,
# the runtime, py.typed -- comes along.
[tool.uv.build-backend]
module-root = "generated"
module-name = "lanyard"