py2xzz is a Rust-based CLI tool that converts data and deep learning pipelines
written in Python (Pandas / PyTorch) into .xzz scripts — the declarative DSL of
Xazz.
Hand-porting Pandas preprocessing code and PyTorch training loops is repetitive and error-prone. py2xzz does it for you, with the following guarantees:
- Automatic conversion — from
read_csvall the way to training loops (backward/step), rewritten into the declarative DSL - Static diagnostics — non-convertible constructs are reported with exact line/column locations
- Standard DSL compliance — output maps 1:1 to the xazz-core AST and passes
xazz check
Docs in other languages: 한국어
input.py ──▶ Python Parser ──▶ Mapper ──▶ Emitter ──▶ output.xzz
(Python AST) (Xazz AST) + diagnostics
The whole flow consists of four stages:
- Python Parser (
src/python/) — a self-contained lexer/parser that turns Python source into an AST using Rust nodes mirroring the Python 3astmodule specification. - Mapper (
src/mapper/) — maps the Python AST to the xazz-core AST. Pandas chains becomePipelineOpchains,nn.Moduleclasses becomeModelDecl/LayerKind, and CSV headers are read to infer the schema (typedeclaration). - SpanMap (
src/span_map.rs) — records the correspondence between original Python line/column positions and emitted statements, to support diagnostic tracing. - Emitter (
src/emitter.rs) — renders the Xazz AST back to.xzzsource text.
Diagnostics are collected at every stage (src/diagnostics.rs) and printed as
text or a structured report via --json.
Prerequisites:
- A toolchain supporting Rust 2024 edition (
rustup update stable) - The
xazz-corecrate — it must be cloned into a sibling directory (../Xazz) next to this repository.
git clone https://github.com/xazzdev/Xazz.git ../Xazz # right after cloning py2xzz
cargo build --releaseOnce built, the binary is available at target/release/py2xzz.
# Convert — writes a .xzz artifact
py2xzz convert <input.py> -o <output.xzz>
# Diagnose — checks convertibility without writing any file
py2xzz check <input.py>convert fails without writing any output when there is at least one error
(exit code 1). Add --verify to run xazz check on the artifact right after
writing it, for double validation.
| Option | Description |
|---|---|
-o, --output <path> |
convert only. Path of the output .xzz file |
--json |
Print the diagnostic report as structured JSON |
--verbose |
Dump intermediate ASTs for every mapping stage (debugging) |
--schema <name> |
Override the automatically inferred schema name |
--verify |
Run xazz check after convert (when the xazz binary is on PATH) |
py2xzz convert examples/preprocessing.py -o output.xzzPyTorch training code is consolidated into a single run ... |> train(...)
statement, combining the model definition and the training loop.
Non-convertible constructs are reported along with their original location, and
--json yields structured results. Diagnostic categories are parse,
unsupported, mapping, schema, io, and other.
| Python (Pandas) | .xzz |
|---|---|
df = pd.read_csv("f.csv") |
type <Schema> = { ... } + v df = load("f.csv") :: <Schema> |
df.dropna(subset=["c"]) |
|> dropNull("c") |
df.fillna(0) |
|> fillNull("c", 0) |
df["c"].fillna(df["c"].mean()) |
|> fillNull("c", strategy: "mean") |
df.groupby("k").agg({"v": "sum"}) |
|> groupBy("k") |> sum("v") |
df.sort_values("c", ascending=False) |
|> orderBy("c", desc: true) |
df.head(n) |
|> take(n) |
df[df["c"] > 10] |
|> filter(col("c") > 10) |
df[["a", "b"]] |
|> select([a, b]) |
df["n"] = df["a"] + df["b"] |
|> withColumn("n", col("a") + col("b")) |
Column types (string / int / float / bool, wrapped in Option<...> when
nulls are present) are inferred from CSV headers and sample values.
| Python (PyTorch) | .xzz |
|---|---|
nn.Linear(in, out) |
Dense(out) (the in dimension is derived from the schema) |
nn.ReLU() · nn.Sigmoid() · nn.Tanh() · nn.Softmax() |
ReLU() · Sigmoid() · Tanh() · Softmax() |
nn.Dropout(p) |
Dropout(p) |
nn.BatchNorm1d(n) |
BatchNorm() |
class Net(nn.Module): ... |
model Net { Dense(...) -> ReLU() -> ... } |
Training loop (zero_grad / backward / step) |
run df |> train(Net, target: "c", epochs: N, lr: X) |
The optimizer mechanics inside the training loop are collapsed into a single
train(...) operator. A target column missing from the schema or an undeclared
model is reported as a conversion error.
AGENT.md is the single source of truth for the full rule set.
Everything in examples/ can be run as is:
examples/preprocessing.py— a Pandas preprocessing pipelineexamples/deep_learning.py— a Pandas + PyTorch model definition and training
cargo build # build
cargo test # unit + integration tests (output must pass xazz check)
cargo clippy --all-targets
cargo fmt --checkContributions are always welcome. See CONTRIBUTING.md (한국어) for details.
Apache License 2.0 — see LICENSE.