Skip to content

Catch DataFrame bugs
before your code runs

Define your schema once. Reference columns as attributes.
Your type checker catches the rest.

Works with ty, mypy, and pyright. Supports Polars, Pandas, and Dask. No plugins. No codegen.

Home

Without type safety

import polars as pl

df = pl.read_parquet("users.parquet")

# Typo — crashes at runtime
df.filter(pl.col("naem") == "Alice")

# Wrong method — crashes at runtime
df.select(pl.col("name").sum())

With Colnade

from colnade_polars import read_parquet
from myapp.schemas import Users

df = read_parquet("users.parquet", Users)

# Typo — caught in your editor
df.filter(Users.naem == "Alice")  # error!

# Wrong method — caught in your editor
df.select(Users.name.sum())  # error!

Type-safe columns

Column references are class attributes. Users.naem is a type error. .sum() on a string column is a type error. Caught in your editor, not in production.

Schema preserved

filter, sort, with_columns return DataFrame[S]. The schema flows through your entire pipeline.

Static + runtime safety

Your type checker catches wrong columns and schema mismatches. Runtime validation catches wrong data — missing columns, unexpected dtypes, or out-of-range values.

Backend agnostic

Write once, run on Polars, Pandas, or Dask. Same schema, same expressions, same type safety.

Generic functions

def f(df: DataFrame[S]) -> DataFrame[S] works with any schema. Build reusable utilities without losing type information.

No plugins or codegen

Works with ty, mypy, and pyright out of the box. Standard Python classes, nothing extra to install.


Quick Example

import colnade as cn
from colnade_polars import read_parquet

class Users(cn.Schema):
    id:    cn.Column[cn.UInt64]
    name:  cn.Column[cn.Utf8]
    age:   cn.Column[cn.UInt64]
    score: cn.Column[cn.Float64]

df = read_parquet("users.parquet", Users)  # DataFrame[Users]

result = (
    df.filter(Users.age > 25)
      .sort(Users.score.desc())
)  # DataFrame[Users] — schema preserved through the pipeline

Install:

pip install colnade colnade-polars

Or with Pandas: pip install colnade colnade-pandas — or Dask: pip install colnade colnade-dask


Getting Started · User Guide · Tutorials · API Reference · Comparison