Recipes
Recipes are ordered repair workflows. They group fixes, options, and optional matching rules under a stable id.
Run A Recipe
import woodpecker
recipe = woodpecker.recipe.get("xmip.cmip6_preprocessing")
findings = woodpecker.recipe.check(dataset, recipe)
preview = woodpecker.recipe.apply(dataset, recipe, dry_run=True)
preview.preview
woodpecker check ./data --recipe-id xmip.cmip6_preprocessing
woodpecker apply ./data --recipe-id xmip.cmip6_preprocessing --dry-run
Use Recipe Reference to inspect discovered recipe ids.
Discovery Order
RecipeLoader discovers recipe documents from:
- explicit files or directories passed to catalog-backed APIs
WOODPECKER_RECIPE_PATH- user config, such as
~/.config/woodpecker/recipes - system config, such as
/etc/woodpecker/recipes - core package resources
- installed plugin package
recipes/resources
Inspect the active set:
woodpecker list-recipes
How It Fits
flowchart LR
Dataset["Dataset"] --> Recipe["Recipe"]
Loader["RecipeLoader"] --> Recipe
Core["Core recipes"] --> Loader
Plugins["Plugin recipes"] --> Loader
Local["User/system/explicit recipes"] --> Loader
Recipe --> Fixes["Fixes"]
Fixes --> Result["Checked or repaired dataset"]
Choosing A Source
| Source | Best for |
|---|---|
| Discovered recipe id | Shared core and plugin workflows. |
| Explicit recipe file | Local experiments, tests, and private workflows. |
| Python builder | Authoring JSON or YAML recipe documents from code. |
Explicit file example:
findings = woodpecker.recipe.check(dataset, "my-recipes.yaml")
Python Authoring
from woodpecker.recipes import fix, recipe
cmip6_core = recipe(
"cmip6.core_units",
fix("woodpecker.normalize_tas_units_to_kelvin"),
description="Normalize CMIP6 tas units.",
).match(
dataset_id_patterns=["CMIP6.CMIP.*.Amon.tas.*"],
attrs={"project_id": "CMIP6", "activity_id": "CMIP"},
)
cmip6_core.to_yaml("cmip6_core_recipe.yaml")
cmip6_core.to_json("cmip6_core_recipe.json")
to_model()returns an in-memoryRecipe.to_document()returns a serializableRecipeDocument.
Recipe Phases
Recipe steps can be assigned to prepare, apply, or finalize phases.
Use prepare() for steps that must run before concatenation or aggregation,
apply() for normal adaptation steps, and finalize() for post-processing
steps.
from woodpecker.recipes import apply, finalize, prepare, recipe
c3s_decadal = recipe(
"c3s.cmip6_decadal",
prepare("cmip6_decadal.calendar_normalization"),
apply("cmip6_decadal.time_metadata"),
finalize("cmip6_decadal.publish_metadata"),
)
The lower-level fix() helper also accepts phase=:
from woodpecker.recipes import fix
fix("cmip6_decadal.calendar_normalization", phase="prepare")