Skip to main content

DataFrame utilities for Chalk AI, backed by libchalk

Project description

chalkdf

DataFrame utilities for building fast, portable data pipelines on top of Apache Arrow — powered by Chalk’s libchalk execution engine.

The API centers on two concepts:

  • chalkdf.DataFrame: a lightweight, eager plan that you can materialize to Arrow.
  • chalkdf.LazyFrame: a serializable, chainable description of a plan that can be round-tripped to/from a protobuf and converted to a DataFrame for execution.

You build expressions with Chalk’s Python underscore DSL (from chalk import _) and function registry (import chalk.functions as F). We also ship pragmatic testing helpers (chalkdf.Testing) to make it easy to compare results in your unit tests.

Installation

  • Requires Python 3.10–3.13
  • Works on Linux and macOS 15+

Install from PyPI:

pip install chalkdf chalkpy

Quickstart

Below are minimal, self‑contained examples that mirror the public API used in the tests.

Create from Arrow and select columns

import pyarrow as pa
from chalkdf import DataFrame

tbl = pa.table({"a": [1, 2, 3], "b": [10, 20, 30], "c": [100, 200, 300]})
df = DataFrame.from_arrow(tbl)

out = df.select("c", "a")
print(out.run())
# ┌─────┬─────┐
# │  c  │  a  │
# ├─────┼─────┤
# │ 100 │  1  │
# │ 200 │  2  │
# │ 300 │  3  │
# └─────┴─────┘

Add or replace columns with expressions

import pyarrow as pa
import chalk.functions as F
from chalk import _
from chalkdf import DataFrame

tbl = pa.table({"a": pa.array([1, 2, 3], pa.int64()), "b": pa.array([10, 20, 30], pa.int64())})
df = DataFrame.from_arrow(tbl)

out = df.with_columns(
    {
        "sum": _.a + _.b,
        "flag": F.if_then_else(_.a < 2, "small", "big"),
    }
)
print(out.run())

Filter, slice, and order

import pyarrow as pa
from chalk import _
from chalkdf import DataFrame

tbl = pa.table({"a": pa.array([1, 2, 3, 4, 5], pa.int64()), "b": pa.array([10, 20, 30, 40, 50], pa.int64())})
df = DataFrame.from_arrow(tbl)

out = df.filter(_.a > 2).slice(1, 2).order_by(("b", "descending"))
print(out.run())

Force caching of a reused subcomputation

DataFrame.replay() is an escape hatch for tests and carefully inspected plans where you need to force a subcomputation to be cached behind an explicit replay boundary. Most plans should let the optimizer place replay nodes automatically; use this only when you know a shared subplan is expensive enough to compute once and reuse.

from chalk import _
from chalkdf import DataFrame

df = DataFrame.from_dict({"id": [1, 2, 3], "amount": [10, 20, 30]})
shared = df.with_columns({"amount_cents": _.amount * 100}).replay("shared_amount_cents")

Rename and explode

import pyarrow as pa
from chalkdf import DataFrame

tbl = pa.table({"id": [1, 2], "vals": pa.array([[1, 2], []], type=pa.list_(pa.int64()))})
df = DataFrame.from_arrow(tbl)

renamed = df.rename({"vals": "values"})
exploded = renamed.explode("values")
print(exploded.run())  # (1,1), (1,2)

Group by and aggregate

import pyarrow as pa
from chalk import _
from chalkdf import DataFrame

tbl = pa.table({"g": [1, 1, 2, 2, 2], "v": pa.array([10, 20, 1, 2, 3], pa.int64())})
df = DataFrame.from_arrow(tbl)

out = df.agg(["g"], _.v.sum().alias("v_sum"))
print(out.run())  # rows may be unordered

Joins

Use a list of join keys when both sides share column names. When names differ, pass a mapping of left columns to their right-hand counterparts.

import pyarrow as pa
from chalkdf import DataFrame

left = DataFrame.from_arrow(pa.table({"key": [1, 2, 3], "x": [10, 20, 30]}))
right = DataFrame.from_arrow(pa.table({"key": [2, 3, 4], "y": [200, 300, 400]}))

joined = left.join(right, on=["key"], how="inner").select("key", "x", "y")
print(joined.run())

# Or with an explicit mapping of left->right keys
joined2 = left.join(right, on={"key": "key"}, how="inner")

# When column names differ, map each left column to its right counterpart
joined3 = left.join(right, on={"key": "lookup_key"}, how="left")

Scan Parquet files

You can construct a DataFrame that scans one or more Parquet files without loading them eagerly. Use local file:// URIs (or remote URIs when running in an environment with appropriate access):

from chalkdf import DataFrame

df = DataFrame.scan(
    ["file:///path/to/data.parquet"],
    name="my_table",
)

print(df.run())  # materializes and prints a preview

Lazy plans (experimental)

LazyFrame records a chain of operations and can round‑trip to a protobuf for transport or persistence. You can reconstruct the same lazy plan later and convert it to a DataFrame to execute.

from chalk import _
from chalkdf import LazyFrame

lf = (
    LazyFrame.from_dict({"c1": [1, 2, 3], "c2": [4, 5, 6]})
    .select("c1", "c2")
    .slice(0, length=10)
    .filter(_.c1 > 0)
)

proto = lf.to_proto()
lf2 = LazyFrame.from_proto(proto)
assert lf == lf2  # structural equality of the recorded plan

df = lf2._convert_to_df()  # convert to a DataFrame for execution
print(df.run())

Notes:

  • LazyFrame._convert_to_df() is currently a private/experimental helper.
  • For named tables, use LazyFrame.named_table("table_name", schema) as a root.

Testing helpers

Use chalkdf.Testing.assert_frame_equal to compare DataFrame results in unit tests. It materializes both frames to Arrow and supports relaxed comparisons.

import pyarrow as pa
from chalkdf import Testing, DataFrame

left = DataFrame.from_arrow(pa.table({"a": [1.000001], "b": [2.0]}))
right = DataFrame.from_arrow(pa.table({"a": [1.0], "b": [2.0]}))

Testing.assert_frame_equal(left, right, atol=1e-5, rtol=0.0)

# Ignore row or column order when needed
Testing.assert_frame_equal(left, right, check_row_order=False, check_column_order=False)

Why chalkdf?

  • Built on Apache Arrow memory formats for zero‑copy interop.
  • Runs on Chalk’s native engine for performance and portability.
  • Small, predictable API surface suited for services and batch jobs.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distributions

No source distribution files available for this release.See tutorial on generating distribution archives.

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

chalkdf-3.39.5-cp313-cp313-manylinux_2_36_x86_64.whl (207.4 MB view details)

Uploaded CPython 3.13manylinux: glibc 2.36+ x86-64

chalkdf-3.39.5-cp313-cp313-macosx_15_0_arm64.whl (165.1 MB view details)

Uploaded CPython 3.13macOS 15.0+ ARM64

chalkdf-3.39.5-cp312-cp312-manylinux_2_36_x86_64.whl (207.4 MB view details)

Uploaded CPython 3.12manylinux: glibc 2.36+ x86-64

chalkdf-3.39.5-cp312-cp312-macosx_15_0_arm64.whl (165.1 MB view details)

Uploaded CPython 3.12macOS 15.0+ ARM64

chalkdf-3.39.5-cp311-cp311-manylinux_2_36_x86_64.whl (207.4 MB view details)

Uploaded CPython 3.11manylinux: glibc 2.36+ x86-64

chalkdf-3.39.5-cp311-cp311-macosx_15_0_arm64.whl (165.0 MB view details)

Uploaded CPython 3.11macOS 15.0+ ARM64

chalkdf-3.39.5-cp310-cp310-manylinux_2_36_x86_64.whl (207.4 MB view details)

Uploaded CPython 3.10manylinux: glibc 2.36+ x86-64

chalkdf-3.39.5-cp310-cp310-macosx_15_0_arm64.whl (165.0 MB view details)

Uploaded CPython 3.10macOS 15.0+ ARM64

File details

Details for the file chalkdf-3.39.5-cp313-cp313-manylinux_2_36_x86_64.whl.

File metadata

File hashes

Hashes for chalkdf-3.39.5-cp313-cp313-manylinux_2_36_x86_64.whl
Algorithm Hash digest
SHA256 d9dd5f0c278358af060ae39d3aebc6560ebf54765b1036d4ede19dd0c8ce14b2
MD5 e35fbba0fd0ffb020fff6427203521be
BLAKE2b-256 f1b4894ebc74361d279f9a88884310bc67b844b1cbaec6cae2bde2cb267ccbc6

See more details on using hashes here.

File details

Details for the file chalkdf-3.39.5-cp313-cp313-macosx_15_0_arm64.whl.

File metadata

File hashes

Hashes for chalkdf-3.39.5-cp313-cp313-macosx_15_0_arm64.whl
Algorithm Hash digest
SHA256 14a27e1596844df56f1b0eec912778c5595f4d6b042aff87cfb23839eaeaeb4b
MD5 74a39d6557686f2bfacb91325a719ab8
BLAKE2b-256 150db5260b51d4fb2ff1cbc9d27c8b4b27bb5f25a8c51abd55320aca4cf7aef8

See more details on using hashes here.

File details

Details for the file chalkdf-3.39.5-cp312-cp312-manylinux_2_36_x86_64.whl.

File metadata

File hashes

Hashes for chalkdf-3.39.5-cp312-cp312-manylinux_2_36_x86_64.whl
Algorithm Hash digest
SHA256 5d9c1ec663cb5d768de5b9cd773159dc48dae442f5326148edecee6cf0f5946b
MD5 5763a037035088191c3017a6e753642c
BLAKE2b-256 23c065291f2a7437a4df641d33a76d4940ff925c8dbeccccd4af8160c1c554f4

See more details on using hashes here.

File details

Details for the file chalkdf-3.39.5-cp312-cp312-macosx_15_0_arm64.whl.

File metadata

File hashes

Hashes for chalkdf-3.39.5-cp312-cp312-macosx_15_0_arm64.whl
Algorithm Hash digest
SHA256 3dc287a669972fd5e3db8ca5f1f492f82d946ac1b1d56af24cd0b078067cd82d
MD5 059da0d5e8694112f1a47715e2d5049b
BLAKE2b-256 639d0d442f403d7cfcbb659642e30d16a072ce21e66adfb2c4419c4bc0a0df17

See more details on using hashes here.

File details

Details for the file chalkdf-3.39.5-cp311-cp311-manylinux_2_36_x86_64.whl.

File metadata

File hashes

Hashes for chalkdf-3.39.5-cp311-cp311-manylinux_2_36_x86_64.whl
Algorithm Hash digest
SHA256 ca5784244d6bf907674fd15cce257d3f27f5971d6d03d09e641df22d1521b9f1
MD5 acf22f053d1e45b814c7d467b293742d
BLAKE2b-256 bc88d81f621b46e5007f66e295b05aa170a6d8db7c870eb8e2363b35283fc05d

See more details on using hashes here.

File details

Details for the file chalkdf-3.39.5-cp311-cp311-macosx_15_0_arm64.whl.

File metadata

File hashes

Hashes for chalkdf-3.39.5-cp311-cp311-macosx_15_0_arm64.whl
Algorithm Hash digest
SHA256 0895e7ce03727468d6c6724df2ec49ee95948b5fc02a47096579fd909f921ba7
MD5 f81e0b25fe4395e92165fe9e9530e4b4
BLAKE2b-256 97f327be3f34d418f462b6ec3a40c5c1c499ff5437dacf9cec128183b892b91b

See more details on using hashes here.

File details

Details for the file chalkdf-3.39.5-cp310-cp310-manylinux_2_36_x86_64.whl.

File metadata

File hashes

Hashes for chalkdf-3.39.5-cp310-cp310-manylinux_2_36_x86_64.whl
Algorithm Hash digest
SHA256 ac99ad08e75ea4065ebea7464f795c2bdd7b0e8ee417bfd4b88d92c43d463361
MD5 1ebc531b625f4b955df74b5598278192
BLAKE2b-256 73a551007b61a6af8a5fd37707ff93c439ee5584abff066d6bf5ad079ed54288

See more details on using hashes here.

File details

Details for the file chalkdf-3.39.5-cp310-cp310-macosx_15_0_arm64.whl.

File metadata

File hashes

Hashes for chalkdf-3.39.5-cp310-cp310-macosx_15_0_arm64.whl
Algorithm Hash digest
SHA256 cfa594477412d037c38810430601b383bc9a634fc19ce59d818d174cc31abcbe
MD5 21ac094bc3b0ffd1754a86f4dab76d3e
BLAKE2b-256 373ec54123e52089f9ab696e6b8caff55b38ba17f9d7a4db56ed13a35ed0ecb0

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page