Template System Reference¶
This page documents the template YAML format and resolution mechanics. For browsing available templates and quick start guides, see the Template Catalog.
What is a Template?¶
A template is a template.yaml file that ships inside Depictio under depictio/projects/<pipeline>/<version>/. It extends a standard project YAML with:
- A
template:metadata block — variable declarations, conditionals, dashboard references {VAR_NAME}placeholders throughout the project config — resolved at runtime- References to bundled dashboard YAML files — imported automatically
- References to recipes for transformed data collections
Template Variables¶
Every template declares its own variables. Variable names are template-specific — each pipeline decides what it needs.
DATA_ROOT is the usual root variable: the results directory given to depictio ingest (formerly --data-root), a local folder or an s3:// prefix. A manifest-driven template declares MANIFEST_URL instead, set with --manifest. All others are passed via --var KEY=VALUE. --bind TAG=LOCATION can stand in for either root variable by pointing each data collection at its own location; see Instantiating with --manifest or --bind.
Auto-detected variables: When a metadata file is provided, the system reads its headers and auto-populates:
GROUP_COL— first non-ID annotation column (overridable)GROUP_COL_DISPLAY— title-cased version for chart labelsANNOTATION_COLS— comma-separated list of all annotation columns
Template YAML Structure¶
template:
template_id: "org/pipeline/version"
description: "Human-readable description"
version: "1.0.0"
variables:
- name: "DATA_ROOT"
description: "Pipeline output root directory"
required: true
- name: "OPTIONAL_VAR"
description: "An optional variable"
required: false
- name: "GENOME"
description: "Assembly the run was aligned to"
required: false
default: "hg38" # v1.13.0+: used when the run does not set it
dashboards:
- "dashboards/base.yaml"
conditional:
- if_var_absent: "OPTIONAL_VAR"
remove_dc_tags: ["optional_dc"]
dashboards: ["dashboards/base.yaml"]
- if_var_present: "OPTIONAL_VAR"
dashboards: ["dashboards/base.yaml", "dashboards/extended.yaml"]
Below the template: block is a standard project configuration with {VAR_NAME} placeholders.
Variable defaults (v1.13.0+)¶
A variable can declare a default, the value used when the run leaves it unset. A value
passed with --var, read from the run's params.json or detected from the metadata file
always wins over it. A defaulted variable fills {NAME} in template.yaml and in the
dashboard YAMLs and satisfies required, but it does not count as provided: an
if_var_present conditional does not fire on a default. A default may contain
{DATA_ROOT}, as in default: "{DATA_ROOT}/input/samplesheet.csv". The nf-core templates use
defaults for GENOME (hg38), the axis of their genome tracks, for GROUP_COL where the
samplesheet has a usual grouping column, and for cut-offs such as SPLICING_FDR in
nf-core/rnasplice.
Conditionals¶
Conditionals adapt the project based on which optional variables the user provides. Each rule can:
- Remove data collections (
remove_dc_tags) — and automatically prune any links referencing them - Override the dashboard list (
dashboards) — select different dashboard variants
Rules fire on if_var_absent (variable not provided) or if_var_present (variable provided).
Source Overrides¶
When a recipe's source paths depend on a template variable, use source_overrides:
transform:
recipe: "org/pipeline/my_recipe.py"
source_overrides:
input_file:
path: "results/Category-{GROUP_COL}-level-2/data.csv"
The recipe Python code stays generic — path resolution happens via variable substitution in the YAML.
When the variable changes what the recipe computes rather than where it reads (a grouping
column, an identifier column, a cutoff), pass it under transform.params instead. Unset
variables are dropped before the call, so the recipe falls back to its own default. See
Passing template parameters to a recipe.
CLI Flags¶
| Flag | Type | Required | Description |
|---|---|---|---|
--template |
string |
one of | Template ID. Pin a version (nf-core/ampliseq/2.16.0), or use nf-core/ampliseq/latest, or just nf-core/ampliseq, to resolve the newest shipped version (v1.5.2+). On the CLI, also a path to an exported bundle (v1.16.0+) |
DATA_DIR (argument) |
path |
one of the three | The results directory, a local folder or, from v1.16.0, an s3:// prefix, substituted for {DATA_ROOT}. Formerly --data-root |
--manifest |
url or path |
one of the three | Data manifest substituted for {MANIFEST_URL}. Not with DATA_DIR (v1.16.0+) |
--bind |
TAG=LOCATION |
one of the three | Point one data collection at a location; the scan mode is inferred from its shape. Repeatable (v1.16.0+) |
--var |
KEY=VALUE |
depends on template | Pass template-specific variables; repeatable |
--dashboard |
path |
no | Override default dashboard(s); repeatable |
--skip dashboards |
flag |
no | Skip automatic dashboard import. Formerly --skip-dashboard-import |
--project |
string |
no | Custom project name. Formerly --project-name |
Here an nf-core/rnaseq run is ingested with its template named, as the Template Catalog lists it, and its samplesheet passed as a variable:
Which template a run uses¶
depictio ingest takes the project from the first of these that applies:
--template nf-core/ampliseq/2.16.0, for a pipeline Depictio ships a template for, or--project-config-path my_project.yaml, for a pipeline of your own;--pipeline-id nf-core/ampliseq/2.16.0, which the Nextflow trigger passes for you since v1.10.0, read from themanifestblock of itsnextflow.config. Its version must match a shipped template, or the run stops with an error;- the results directory itself, local or an
s3://prefix: the run information an nf-core pipeline writes underpipeline_info/names the pipeline and its version, and the matching template is used. When no shipped version matches, the closest version that is not newer is used, with a warning; - since v1.16.0, a template composed from what the
tools catalog recognises in a local results
directory, when no bundled template fits it.
--composecomposes even when one does. See Composed dashboards.
The web UI's From a run folder tab detects the template the same way and shows the comparison before anything is created; see From a run folder.
When none applies, as for an s3:// prefix no template reads, the command
stops and asks for --template or --project-config-path.
Instantiating with --manifest or --bind (v1.16.0+)¶
DATA_DIR, --manifest and --bind all answer the same question, where
the data is, and a template run needs at least one of them:
# A manifest-driven template: no results directory at all
depictio ingest --template generic/manifest-tables/1 \
--manifest https://data.example.org/run42/manifest.json
# Any template, each data collection pointed at its own location
depictio ingest --template my-lab/rnaseq-qc/1 \
--bind metadata=/data/run42/metadata.tsv \
--bind samples=s3://my-bucket/run42/*.samples.csv
--manifest takes a URL or a local file path and becomes the MANIFEST_URL
variable. --bind is applied after resolution, so it wins over whatever
{DATA_ROOT} or {MANIFEST_URL} resolved to for that collection, and a
required variable that no collection uses any more is not asked for. A
--bind naming a tag the template does not declare is an error, listing the
tags that exist. The location shapes and the mode each one implies are on
Remote data and manifests.
Running an exported bundle (v1.16.0+)¶
On the CLI, --template also accepts a path: a directory holding a
template.yaml (or project.yaml), or a YAML file. That is what makes an
exported bundle usable by whoever receives
it, without copying it into an installation first:
depictio ingest --template ./my-lab/rnaseq-qc/1 \
--bind samples=s3://their-bucket/run7/*.samples.csv
An existing path wins over an installed template of the same name. The server never accepts the path form: it resolves ids on behalf of remote callers, and ids are confined to the templates directory in both contexts.
Resolution Workflow¶
When a template is used, depictio ingest inserts Step 0: Template resolution before the standard pipeline:
| Step | Name | Description |
|---|---|---|
| 0 | Template resolution | Load YAML, substitute variables, auto-detect metadata columns, apply conditionals, then materialise recipe seeds |
| 1 | Server check | Check that the server answers |
| 2 | S3 check | Check the S3 storage configuration |
| 3 | Config validation | Pydantic validation of the resolved project config |
| 4 | Project sync | Create or update project on server |
| 5 | File scan | Discover data collection files |
| 6 | Data process | Execute recipes, write to Delta Lake |
| 7 | Join computation | Compute cross-DC joins |
| 8 | Dashboard import | Import the bundled dashboard YAML the project lacks (with variable substitution). On a refresh, the dashboards it has are kept as edited in the viewer, unless --reset-dashboards |
Dashboard YAML files also undergo variable substitution (e.g. {GROUP_COL} in filter columns, chart titles).
Recipe seeds (v1.6.0+)¶
A reference template ships each recipe's output as a committed
{DATA_ROOT}/{dc_tag}.tsv, so the bundled projects can be explored without the
pipeline run behind them. Since v1.6.0 --template reads those seeds, the way
first-boot seeding always did: where a seed exists for a source: transformed
data collection, the recipe is replaced by a plain scan of that file. The
collection keeps source: transformed, so the viewer still shows its lineage.
A data collection with no seed is left alone and its recipe runs as before. Seed
coverage is uneven: nf-core/viralrecon/3.0.0 ships one for all ten of its
recipe collections, nf-core/ampliseq/2.16.0 for sixteen of nineteen.
This runs after conditionals, so a collection a conditional gated out stays gated out even with a seed sitting beside it.
A seed is matched by name, not assumed
Only a source: transformed collection is redirected. A {dc_tag}.tsv next
to a source: native collection of the same tag is that collection's own
input, and is scanned normally.
Template Origin¶
Once a project is created from a template, the UI shows a template badge on dashboard cards and in the project data manager. This provenance is stored in the template_origin field:
template_id— e.g."nf-core/ampliseq/2.16.0"template_version— schema versiondata_root— the resolved pathvariables— all resolved variable valuesapplied_at— timestampconfig_snapshot— frozen copy of the resolved configrun_provenance: the pipeline's own run parameters, see below (v1.8.3+)unrecognised_files: for a composed template, the tabular files of the run the catalog did not recognise and that were left out, each with what it would show; the project page lists them (v1.16.0+)
Run provenance (v1.8.3+)¶
template_origin records how Depictio was invoked. Run provenance records
how the pipeline was, by reading the run's own parameter, version and recap
files and storing them as ordered entries on template_origin.run_provenance.
Three different things are called provenance
This section is about pipeline run parameters. The ingestion run provenance is about how the CLI was invoked (host, CLI version, command line), and Template Origin above is about which template produced the project.
A template declares the recipe under template.provenance:
template:
provenance:
sources:
- name: "params"
glob: "pipeline_info/params*.json"
format: "json"
pick: "latest"
exclude_keys:
- "*_ref_databases*" # bulky reference-DB catalogs
- name: "software_versions"
glob: "pipeline_info/*software*versions.yml"
format: "yaml"
group: "Software versions"
groups:
- group: "Cutadapt (primer trimming)"
key_patterns: ["FW_primer", "RV_primer", "cutadapt_*", "skip_cutadapt"]
- group: "DADA2 (denoising & filtering)"
key_patterns: ["trunclenf", "trunclenr", "trunc_qmin", "max_ee", "dada_*"]
highlight:
- "FW_primer"
- "RV_primer"
- "diversity_rarefaction_depth"
sources¶
One entry per file, or file family, to read.
| Field | Default | Description |
|---|---|---|
name |
required | Label shown next to each entry |
glob |
required | Glob relative to DATA_ROOT, so one spec fits every run |
format |
auto |
json, yaml, tsv (two-column key/value) or auto, by suffix |
pick |
latest |
When the glob matches several files: latest (last in sorted order, which is chronological for nf-core timestamps), first, or all (merged in order, later wins) |
exclude_keys |
[] |
fnmatch globs of keys to drop |
group |
unset | Put every key of this source in one group, bypassing the group rules |
Nested files are flattened to dotted keys.
groups¶
Each rule assigns keys matching any of its key_patterns (fnmatch globs against
the flattened key) to a named group, in declaration order, first match winning.
highlight¶
Keys surfaced inline in the dashboard's Settings. The full listing always stays in the ingestion report.
Complete by construction
exclude_keys is the only way a key is omitted. Everything else is kept, and
keys no group rule matches land in a catch-all Other group rather than
being dropped.
A template with no provenance: block gets a default spec: the latest
pipeline_info/params*.json, everything in one Parameters group.
Files with no template¶
--provenance-file takes an arbitrary recap file, JSON, YAML or two-column TSV,
and lists its entries under a User provided group. The flag is repeatable.
depictio ingest /path/to/results --provenance-file run_summary.yaml --provenance-file thresholds.tsv
Where it surfaces¶
- Ingestion report: a Run provenance card, one accordion per group, with per-row copy, full-text search across keys and values, and the source files listed. See Ingestion Report & Health.
- Dashboard settings: a Run parameters row showing the highlighted keys inline, linking to the full report. See Using the dashboard.
The bundled nf-core/ampliseq template ships a spec covering Cutadapt, DADA2,
taxonomy, QIIME2 filtering, diversity and rarefaction, differential abundance,
skipped steps and software versions.
Cross-DC Links¶
Templates define links between data collections using tags (not IDs):
links:
- source_dc_tag: "metadata"
source_column: "ID"
target_dc_tag: "alpha_diversity"
target_type: "table"
link_config:
resolver: "direct"
target_field: "sample"
Tags are resolved to MongoDB ObjectIds after the project is synced to the server. Links referencing removed DCs (via conditionals) are auto-pruned.
Export a project as a template (v1.16.0+)¶
The inverse of instantiation: freeze a live project and its dashboards into a template bundle. Build one good project interactively, export it, and the next run of the same pipeline is one command.
The bundle is unpacked into <output-dir>/<template-id>/. --server,
--version, --description and --data-dir are optional; see the
CLI reference.
On the project page, Project settings, then Export: a
Template ID, a Version, a Description (optional) and a
Data root (optional), left empty for the default below. Export
downloads the bundle as a zip named after the template ID, / becoming
_. Owners, editors and administrators can export; on a public
instance, administrators only.
POST /projects/{project_id}/export_template with
{"template_id", "version", "description", "data_root"} returns the zip.
What the bundle contains¶
| Path | Content |
|---|---|
template.yaml |
A synthesised template: block (id, description, version, variables, dashboard list) followed by the project configuration |
dashboards/*.yaml |
One file per main dashboard tab, child tabs included, referencing data collections by tag |
Runtime state is stripped: ids, permissions, file hashes, runs, registration
and modification timestamps, template_origin, yaml_config_path, the
generated workflow_tag, and the per-collection size metadata that ingestion
keeps on each data collection. Per-project storage credentials are never
exported.
Data bindings are re-parameterised. Stored manifest URLs become
{MANIFEST_URL}, declared as a required variable. A data root, a local path
or an s3:// prefix, becomes {DATA_ROOT} when --data-dir is given, or when
the project itself came from a template that recorded one. Only locations
below the data root are rewritten: a URL or an s3:// location elsewhere is
kept as it is. A template binds one manifest, so distinct stored manifest URLs
all collapse onto the same placeholder; only the server log notes it.
Round-trip guarantee¶
Before the bundle is returned it is checked against the same models
instantiation uses: the template: block must validate as template metadata,
and the configuration with placeholders substituted must validate as a
project. If either fails the request is rejected with a 422 and nothing is
emitted, so an exported bundle always re-instantiates through the resolver.
A project read from an s3:// folder
The check gives {DATA_ROOT} a local test path, which an s3_prefix or
url collection does not accept. With an s3:// data root, the default
for a project made from a run folder on S3, the export therefore stops
with Exported config does not round-trip through Project validation.
From the CLI, --data-dir "" exports without a data root and keeps the
s3:// locations as they are. In the web form, an empty Data root
means the default.
Unpacked in the server's depictio/projects/ folder, which an installed
package keeps as depictio/cli/projects/, the bundle is found by the resolver
and offered in the picker. Anywhere else, run it by path with
--template ./folder.
Additional Resources¶
- Template Catalog: browse and use available templates
- Remote data and manifests: run folders on S3, URL, prefix and manifest scan modes,
--bind, creating a project in the web UI, sharing a project - Recipes: how to write and test data transformation recipes
- Contributing Templates: add a new template
- CLI Usage: full
depictio ingestreference