Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 35 additions & 0 deletions examples/supported/01_hello_filesystem.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
# Supported example 01: the smallest complete pipeline.
#
# Typed parameter -> write a file -> read it back -> declared output.
# Everything here is deterministic: no model, no network, no credentials.
id: hello_filesystem
name: Hello Filesystem
description: Write a file from a typed parameter, read it back, declare an output
version: "1.0.0"

parameters:
greeting:
type: string
default: "hello"
out_dir:
type: string
default: "./output"

steps:
- id: write_greeting
tool: filesystem
action: write
parameters:
path: "{{ out_dir }}/greeting.txt"
content: "{{ greeting }}, world"

- id: read_back
tool: filesystem
action: read
parameters:
path: "{{ out_dir }}/greeting.txt"
dependencies:
- write_greeting

outputs:
greeting_text: "{{ read_back.result.content }}"
58 changes: 58 additions & 0 deletions examples/supported/02_parallel_fanout_fanin.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
# Supported example 02: parallel fan-out with a dependent join.
#
# `alpha` and `beta` do not depend on each other, so they share an execution
# level and may run concurrently. `join` depends on both and must run strictly
# after them, interpolating both of their results.
id: parallel_fanout_fanin
name: Parallel Fan-out and Fan-in
description: Two independent branches joined by a dependent step
version: "1.0.0"

parameters:
out_dir:
type: string
default: "./output"

steps:
- id: alpha
tool: filesystem
action: write
parameters:
path: "{{ out_dir }}/alpha.txt"
content: "alpha-value"

- id: beta
tool: filesystem
action: write
parameters:
path: "{{ out_dir }}/beta.txt"
content: "beta-value"

- id: read_alpha
tool: filesystem
action: read
parameters:
path: "{{ out_dir }}/alpha.txt"
dependencies:
- alpha

- id: read_beta
tool: filesystem
action: read
parameters:
path: "{{ out_dir }}/beta.txt"
dependencies:
- beta

- id: join
tool: filesystem
action: write
parameters:
path: "{{ out_dir }}/joined.txt"
content: "{{ read_alpha.result.content }}+{{ read_beta.result.content }}"
dependencies:
- read_alpha
- read_beta

outputs:
joined: "{{ join.result.path }}"
48 changes: 48 additions & 0 deletions examples/supported/04_conditions.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
# Supported example 04: conditional execution and control-flow routing.
#
# `check_size` runs only when its `condition:` holds. When the condition is
# false the step is skipped and `on_false` routes execution to the recovery
# branch, marking the steps in between as skipped. Skipping is not failing:
# this pipeline succeeds either way.
id: conditions
name: Conditions and Routing
description: Conditional execution with on_false routing and skipped steps
version: "1.0.0"

parameters:
content:
type: string
default: "a reasonably long piece of text"
out_dir:
type: string
default: "./output"

steps:
- id: check_size
tool: filesystem
action: write
condition: "{{ content | length > 10 }}"
on_false: handle_short
parameters:
path: "{{ out_dir }}/long.txt"
content: "long: {{ content }}"

- id: handle_long
tool: filesystem
action: read
parameters:
path: "{{ out_dir }}/long.txt"
dependencies:
- check_size

- id: handle_short
tool: filesystem
action: write
parameters:
path: "{{ out_dir }}/short.txt"
content: "short: {{ content }}"
dependencies:
- handle_long

outputs:
taken_branch: "{{ out_dir }}"
47 changes: 47 additions & 0 deletions examples/supported/06_failure_policy.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
# Supported example 06: failure policy, timeout and retry.
#
# `flaky` cannot finish inside its timeout, so it fails with a TimeoutError.
# A timeout is retried like any other failure, so `max_retries: 2` means two
# attempts and therefore one retry -- max_retries bounds ATTEMPTS, not retries
# beyond the first.
#
# `on_failure: continue` lets the run finish. The failure is not swallowed:
# the step reports success=false with its error, the run reports success=false,
# and the CLI exits 1.
id: failure_policy
name: Failure Policy
description: Timeout, bounded retry, and continuing past a failed step
version: "1.0.0"

parameters:
out_dir:
type: string
default: "./output"

steps:
- id: before
tool: filesystem
action: write
parameters:
path: "{{ out_dir }}/before.txt"
content: "this step succeeds"

- id: flaky
tool: terminal
action: execute
timeout: 1
max_retries: 2
on_failure: continue
parameters:
command: "sleep 5"
dependencies:
- before

- id: after
tool: filesystem
action: write
parameters:
path: "{{ out_dir }}/after.txt"
content: "the run continued"
dependencies:
- flaky
49 changes: 49 additions & 0 deletions examples/supported/07_templates_and_outputs.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
# Supported example 07: templates, step-result references and declared outputs.
#
# A step's result is referenced by `{{ step_id.result.field }}`. Any reference
# that does not resolve fails the step before it can write anything, so an
# unresolved `{{ }}` never reaches a file.
id: templates_and_outputs
name: Templates and Outputs
description: Nested parameters, step-result references and declared outputs
version: "1.0.0"

parameters:
title:
type: string
default: "Quarterly Report"
author:
type: string
default: "Orchestrator"
out_dir:
type: string
default: "./output"

steps:
- id: write_header
tool: filesystem
action: write
parameters:
path: "{{ out_dir }}/header.md"
content: "# {{ title }}\n\nBy {{ author }}\n"

- id: read_header
tool: filesystem
action: read
parameters:
path: "{{ out_dir }}/header.md"
dependencies:
- write_header

- id: write_report
tool: filesystem
action: write
parameters:
path: "{{ out_dir }}/report.md"
content: "{{ read_header.result.content }}\nBody of the report.\n"
dependencies:
- read_header

outputs:
report_path: "{{ write_report.result.path }}"
header_text: "{{ read_header.result.content }}"
50 changes: 50 additions & 0 deletions examples/supported/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
# Supported examples

Every pipeline in this directory is **tested as product behaviour**. Each one:

1. compiles under `orchestrator validate`;
2. executes through the CLI;
3. executes through the Python API;
4. produces the same normalised result document from both surfaces;
5. produces the artifacts and declared outputs its expectations record.

`tests/test_supported_examples.py` enforces all five, and fails if a file is
added here without an entry declaring what it should do — so the set cannot
grow past its coverage.

| Example | Demonstrates |
|-|-|
| `01_hello_filesystem.yaml` | typed parameters, templating, dependencies, declared outputs |
| `02_parallel_fanout_fanin.yaml` | independent steps sharing an execution level, joined by a dependent step |
| `04_conditions.yaml` | `condition:`, `on_false` routing, skipped steps |
| `06_failure_policy.yaml` | `timeout`, bounded retry, `on_failure: continue`, honest exit code |
| `07_templates_and_outputs.yaml` | step-result references and declared outputs |

Everything else under `examples/` is **not** in this set. Those pipelines
predate the current contract and most of them do not compile — 108 of 111 at
the time of writing (#104). Treat them as historical until each is proven and
moved here.

## Running one

```bash
orchestrator validate examples/supported/01_hello_filesystem.yaml
orchestrator run examples/supported/01_hello_filesystem.yaml
```

`06_failure_policy.yaml` exits **1** on purpose: it contains a step that
fails, and the run reports that rather than hiding it.

## Not here yet

Numbering follows the planned set, so gaps are deliberate rather than lost:

- `03_data_etl` — needs the data-processing tool under the same contract.
- `05_loop` — `for_each`/`while` exist but are not yet pinned by contract tests.
- `08`–`09`, `11` — model pipelines. They cannot run hermetically in the
blocking layer; they belong in the live job.
- `10_model_fallback` — **deliberately absent.** There is no model fallback:
`select_model` raises rather than substituting a model the pipeline did not
ask for. An example must not be written for behaviour that does not exist.
- `12`–`14` — checkpoint/resume, sub-pipelines and web research, each of which
needs its own acceptance job first.
Loading
Loading