Quick Start#
Get from zero to a running pipeline in under five minutes. This tutorial assumes you have already installed oxo-flow.
1. Initialize a project#
This creates:
my-pipeline/
├── my-pipeline.oxoflow # Workflow definition
├── data/input.txt # Starting input data
├── envs/ # Environment specs
├── results/ # Output directory (created by init)
├── scripts/ # Helper scripts
└── .gitignore # Bioinformatics-aware ignore file
2. Define a simple workflow#
Open my-pipeline.oxoflow and replace its contents:
[workflow]
name = "my-pipeline"
version = "0.1.0"
description = "A simple two-step demo"
[defaults]
threads = 2
[[rules]]
name = "create_data"
input = []
output = ["data/greeting.txt"]
shell = "echo 'Hello from oxo-flow!' > data/greeting.txt"
[[rules]]
name = "transform"
input = ["data/greeting.txt"]
output = ["results/uppercase.txt"]
shell = "tr '[:lower:]' '[:upper:]' < data/greeting.txt > results/uppercase.txt"
This workflow has two rules:
- create_data — writes a text file (no input files required)
- transform — converts the file to uppercase (depends on
create_data's output)
oxo-flow infers the dependency automatically because transform's input matches create_data's output.
Output directories are created automatically
oxo-flow creates parent directories for every declared output before running the rule — no mkdir -p needed in your shell commands. The data/ and results/ directories above are created by the engine.
3. Validate#
Warnings are the signal — the exit code is not
validate exits 0 even when it warns. A missing input file, a
sample_pattern that matches no files, or a {sample} wildcard with no
sample source declared (no sample_pattern, [[sample_groups]], or
[[pairs]]) — all are warnings under the ✓ line, not errors:
✓ my-pipeline.oxoflow — 2 rules, 1 dependency
⚠ Warning: The following input files do not exist:
- raw/sample1_R1.fastq.gz
The ✓ ... — N rules, M dependencies line only says the workflow
parsed. Read the warnings, and let run be the gate: it exits non-zero
when a rule's input is absent or its wildcards cannot be bound.
4. Dry-run#
Preview the execution plan without running anything:
oxo-flow v0.23.2 — Rust-native bioinformatics pipeline engine
Plan: would run: 2 | skip: 0 | completed: 0 (DAG size: 2)
1. create_data
threads=2
outputs: ["data/greeting.txt"]
command: echo 'Hello from oxo-flow!' > data/greeting.txt
2. transform
threads=2
outputs: ["results/uppercase.txt"]
command: tr '[:lower:]' '[:upper:]' < data/greeting.txt > results/uppercase.txt
input ✗: data/greeting.txt
Summary: 2 rules, total 4 threads declared, max 2 threads/rule
To execute: oxo-flow run my-pipeline.oxoflow -j 1
The banner is TTY-gated
The oxo-flow v0.23.2 — … line at the top only prints when stderr is an
interactive terminal. In nohup/CI/log-capture runs it is suppressed (the
run log header and --version still carry version provenance), so
transcripts copied from redirected output will not show it.
5. Execute#
oxo-flow v0.23.2 — Rust-native bioinformatics pipeline engine
DAG: 2 rules in execution order
1. create_data
2. transform
Running: create_data
✓ create_data (0.0s)
Running: transform
✓ transform (0.0s)
Done: 2 succeeded, 0 skipped, 0 failed
✓ Report snapshot: …/.oxo-flow/reports/report-20261001-093232.json
✓ 2 output files verified (42B total)
Progress lines depend on the output stream
Running: / ✓ progress lines print when stderr is not an
interactive terminal (in a TTY the animated progress bar replaces
them); the ✓ Report snapshot: line after Done: prints on every
run and names the JSON snapshot written under
.oxo-flow/reports/ (see Run output & logs).
INFO-level tracing lines (workflow start, JSON events) are elided
here for readability.
6. Check the results#
You are already inside my-pipeline/ (step 1 changed into it), so read the
output directly:
What to verify
After running your first workflow, check these to confirm success:
- Output files exist:
ls results/showsuppercase.txt - Content is correct: The file contains the expected uppercase text
- No error files: Check
.oxo-flow/for any error logs
If the output doesn't match expectations, see the Troubleshooting Guide.
7. Visualize the DAG#
oxo-flow provides multiple ways to visualize your workflow's structure.
Terminal View (Default)#
The default graph command prints a stylized ASCII or tree representation directly to your terminal:
oxo-flow v0.23.2 — Rust-native bioinformatics pipeline engine
┌──────────────────────────────────────────────┐
│ Workflow DAG: 2 rules, 1 dependencies │
│ Depth: 2, Width: 1, Critical path: 2 steps │
└──────────────────────────────────────────────┘
Level 0 (sequential)
create_data
│
▼
Level 1 (sequential)
transform [depends: create_data]
Critical path: create_data → transform
Graphviz (DOT) Export#
For complex pipelines, you can export to Graphviz DOT format for high-resolution rendering:
If you have Graphviz installed, render it (macOS: brew install graphviz):
What Just Happened?#
- oxo-flow parsed the
.oxoflowTOML file into aWorkflowConfig - The DAG engine analyzed input/output dependencies and built a directed acyclic graph
- Topological sorting determined that
create_datamust run beforetransform - The local executor ran each rule's shell command in order
- Success/failure was reported for each step
Web Interface#
Start the web server for a browser-based workflow experience:
# Personal mode (localhost, no auth)
oxo-flow serve
# Team mode (multi-user, OAuth2)
oxo-flow serve --mode team
# HPC mode (cluster submit panel, scheduler auto-detected)
oxo-flow serve --mode hpc
Open http://localhost:8080 to access the web UI with:
- DAG visualization with live status
- Pipeline validation and execution monitoring
- AI-powered pipeline generation from natural language
- Real-time resource metrics and diagnostics
See Deployment Modes for detailed configuration.
Next Steps#
- Run a pilot first: on a workflow that has a sample dimension
(
sample_pattern,[[sample_groups]], or[[pairs]]), tryoxo-flow run pipeline.oxoflow --samples first:2— the engine runs the full pipeline on two samples, reports a projected full-run time, and skips them automatically when you scale up. The two-rule demo above has no samples, so a sample filter there — e.g.--samples first:2or--samples ready— would exit with--samples matched no samples in this workflow(a bare sample name like--samples S9instead declares it for later use and exits successfully). See Pilot runs and Parallel Samples for a sample-driven workflow to try it on. - Your First Workflow — build a real bioinformatics pipeline with environments
- Variant Calling Pipeline — complete NGS analysis tutorial
- Create a Workflow — reference guide for
.oxoflowauthoring - Command Reference — explore all CLI options