Format- and source-agnostic ingestion framework: a common execution runtime for turning record-oriented data sources into typed columnar data. Rust core, Python bindings; adapters live in separate packages.
See the code
rypipe
Format-agnostic columnar ingestion engine. Rust core, Python bindings.
Parse row-oriented byte streams into Apache Arrow tables with parallel scheduling, memory-bounded execution, query pushdown, and a chainable pipeline API. Format adapters live in separate packages.
rypipe is a format- and source-agnostic ingestion framework that provides a
common execution runtime for turning arbitrary record-oriented data sources
into typed columnar data. It separates format-specific parsing from
format-agnostic execution, so the same engine can parse XML, JSON, CSV, HTML,
or any other row-oriented format once you provide a small adapter.
Add a new format by implementing two small traits: Splitter and
RecordParser.
rypipe was originally developed as the ingestion engine for crxml, a Crystal Reports XML parser, and was later extracted and abstracted. The engine's design, performance characteristics, and API were shaped by real-world production use with crxml. We use crxml as the primary example throughout the documentation because it demonstrates the full power of the framework: complex nested schemas, large files, parallel processing, and advanced filtering.
Any parser you build on rypipe (or any adapter package you install) gets this same API: a small Rust crate behind a clean, chainable Python interface with fused filtering, parallel parsing, and bounded-memory streaming. The quick start below shows crxml as a concrete example; your format's adapter would look and behave the same.
pip install crxml
import crxml
from crxml import CrystalXMLSource, CastTypes, FilterRows, col
source = CrystalXMLSource("report.xml", row_tag="Details")
# Simple read
table = source.to_arrow()
# Pipeline with stages
result = (
source
| CastTypes({"Amount": float})
| FilterRows(field="Status", op="==", value="Active")
| crxml.to_arrow()
)
# Expression predicates fuse into the Rust parse loop too
result = (
source
| FilterRows((col("Amount") > 100) & (col("Status") == "Active"))
| crxml.to_arrow()
)
# Convert to DataFrame
df = source.to_pandas()
# Constant-memory streaming
for batch in source.iter_record_batches(memory="64MiB"):
writer.write_batch(batch)
One runtime, many formats. XML, JSON, CSV, HTML, TSV, and any future format share the same parallel scheduler, memory-bounded executor, and pushdown infrastructure. An adapter is two small traits, not a full engine. crxml (Crystal Reports XML) is the reference adapter that proved this model.
Measured performance. On the documented 533 MB crxml workload, ~4.2 GB/s parallel and ~950 MB/s single-threaded (Ryzen 7 5800X). Arrow export moves string/dictionary buffers without copying; primitive arrays are copied. Predicate-first evaluation. Layout prediction via memcmp.
Correctness by construction. Differential testing, fuzz targets, property tests, and a tier-ladder profiler.
Python-native ergonomics. Chainable pipeline API with automatic fusion of rename/drop/cast/filter into the Rust parse loop. Streaming with bounded memory. Schema discovery. DataFrame and Parquet sinks.
rayon scales to many cores.iter_record_batches
and a configurable budget.col(...) predicates that fuse into the
parse loop, composable with &, |, ~.RecordBatch and exports via the C Data Interface.| Crate | Purpose |
|---|---|
rypipe-core | Pure Rust engine: Value, ExecutionPlan, TableBuilder, Pipeline, parallel/bounded drivers, Arrow export |
rypipe-python | PyO3 bindings for adapter packages; exposes the rypipe package |
rypipe-test | Property-based testing helpers and fixtures for adapter development |
# Rust only
cargo build --workspace --release
# Python extension
maturin develop --release
# Rust
cargo test --workspace --all-features
# Python
pip install -e ".[dev]"
pytest crates/rypipe-python/tests/
MIT
Rust
81.8%
Python
18.2%
Format- and source-agnostic ingestion framework: a common execution runtime for turning record-oriented data sources into typed columnar data. Rust core, Python bindings; adapters live in separate packages.
See the code
rypipe
Format-agnostic columnar ingestion engine. Rust core, Python bindings.
Parse row-oriented byte streams into Apache Arrow tables with parallel scheduling, memory-bounded execution, query pushdown, and a chainable pipeline API. Format adapters live in separate packages.
rypipe is a format- and source-agnostic ingestion framework that provides a
common execution runtime for turning arbitrary record-oriented data sources
into typed columnar data. It separates format-specific parsing from
format-agnostic execution, so the same engine can parse XML, JSON, CSV, HTML,
or any other row-oriented format once you provide a small adapter.
Add a new format by implementing two small traits: Splitter and
RecordParser.
rypipe was originally developed as the ingestion engine for crxml, a Crystal Reports XML parser, and was later extracted and abstracted. The engine's design, performance characteristics, and API were shaped by real-world production use with crxml. We use crxml as the primary example throughout the documentation because it demonstrates the full power of the framework: complex nested schemas, large files, parallel processing, and advanced filtering.
Any parser you build on rypipe (or any adapter package you install) gets this same API: a small Rust crate behind a clean, chainable Python interface with fused filtering, parallel parsing, and bounded-memory streaming. The quick start below shows crxml as a concrete example; your format's adapter would look and behave the same.
pip install crxml
import crxml
from crxml import CrystalXMLSource, CastTypes, FilterRows, col
source = CrystalXMLSource("report.xml", row_tag="Details")
# Simple read
table = source.to_arrow()
# Pipeline with stages
result = (
source
| CastTypes({"Amount": float})
| FilterRows(field="Status", op="==", value="Active")
| crxml.to_arrow()
)
# Expression predicates fuse into the Rust parse loop too
result = (
source
| FilterRows((col("Amount") > 100) & (col("Status") == "Active"))
| crxml.to_arrow()
)
# Convert to DataFrame
df = source.to_pandas()
# Constant-memory streaming
for batch in source.iter_record_batches(memory="64MiB"):
writer.write_batch(batch)
One runtime, many formats. XML, JSON, CSV, HTML, TSV, and any future format share the same parallel scheduler, memory-bounded executor, and pushdown infrastructure. An adapter is two small traits, not a full engine. crxml (Crystal Reports XML) is the reference adapter that proved this model.
Measured performance. On the documented 533 MB crxml workload, ~4.2 GB/s parallel and ~950 MB/s single-threaded (Ryzen 7 5800X). Arrow export moves string/dictionary buffers without copying; primitive arrays are copied. Predicate-first evaluation. Layout prediction via memcmp.
Correctness by construction. Differential testing, fuzz targets, property tests, and a tier-ladder profiler.
Python-native ergonomics. Chainable pipeline API with automatic fusion of rename/drop/cast/filter into the Rust parse loop. Streaming with bounded memory. Schema discovery. DataFrame and Parquet sinks.
rayon scales to many cores.iter_record_batches
and a configurable budget.col(...) predicates that fuse into the
parse loop, composable with &, |, ~.RecordBatch and exports via the C Data Interface.| Crate | Purpose |
|---|---|
rypipe-core | Pure Rust engine: Value, ExecutionPlan, TableBuilder, Pipeline, parallel/bounded drivers, Arrow export |
rypipe-python | PyO3 bindings for adapter packages; exposes the rypipe package |
rypipe-test | Property-based testing helpers and fixtures for adapter development |
# Rust only
cargo build --workspace --release
# Python extension
maturin develop --release
# Rust
cargo test --workspace --all-features
# Python
pip install -e ".[dev]"
pytest crates/rypipe-python/tests/
MIT
Rust
81.8%
Python
18.2%