rs-rich-data
Tabular data for rs-rich,
the Rust port of Python's rich: one row source contract with adapters
behind it, so a file, a stream of records or a query result becomes a table
without hand-written glue. This crate is an rs-rich addition, not a port:
rich reads no data files. It builds on
rs-rich-ext's public API.
- Row sources.
RowSourceyields column names, an optional schema (inrich_ext::schema's format-neutral model) and rows ofrich_ext::table::Value, one at a time.Rowsholds them in memory and becomes arich_ext::table::TableDatato sort, group, total or style. - Adapters. CSV and TSV through the port of Python's
csvsniffer and reader thatrich --csvuses, JSON Lines, anyserde::Serializerows, and ArrowRecordBatches (and the schema of an Arrow IPC file or stream,arrow::read_schema) behind the off-by-defaultarrowfeature. - Type inference, on request: integers, floats, booleans, dates, timestamps, nulls and text per column, with the evidence (how many cells parsed as each type) and per-column overrides.
- Column statistics: count, nulls, distinct values, min, max, mean, median, quantiles and the most common values, as a table or as a summary under each column heading.
- Large results (
window):Rowsfeedrich_ext's virtualisedVirtualTable, andRowWindowreads one window of any forward-only source in constant memory, with its row count. - SQL result sets (
sql):ResultSetrenders a query result with typed alignment from the schema,NULLmarked apart from empty text, and a(3 rows, 12ms)footer, windowed withlimitandoffset. No database connection: rows come from an adapter or the caller.
use Console;
use CsvReader;
use Inferrer;
use Stats;
let mut rows = new
.read
.unwrap;
let inference = new.infer;
inference.apply; // p99 becomes numbers; `--csv` never does this
let console = new;
console.print; // column, type, how many cells parsed, nulls
console.print;
console.print;
Conditional styles for these tables (rules that style a cell, row or
column by value, from Rust predicates or TOML rule tables) are
rich_ext::table::rules.
Profiling and data quality
A profile says what each column of any row source holds: its inferred
type, null count and rate, distinct values, min, max, mean, median and
quartiles, and a distribution (a histogram from rich_ext::chart::Histogram
for a numeric column, the most common values for any other), with a
missing-value map (rich_ext::chart::Heatmap) of where the nulls are, rows
bucketed in order against the columns. rich profile draws it.
use Console;
use CsvReader;
use ;
let file = new;
let source = new.source?; // streamed, not read whole
let options = ProfileOptions ;
let profile = from_source?.with_name;
new.print;
println!; // the same model, as JSON
Profiles are bounded. A Profiler reads one row at a time and keeps a
uniform reservoir sample (Algorithm R with a fixed seed, so a profile is
reproducible) of at most sample rows, 10,000 by default: types, distinct
values, statistics and distributions describe the sample, while the row
count, null counts and the missing-value map (at most 20 buckets, merged as
rows arrive) count every row. The heading prints the sample size
(sampled 10,000 of 3,000,000 rows), and Profile::sampled says whether
there was one. CsvReader::source and jsonl::source stream from any
BufRead, so memory is the sample, whatever the input's size.
Data quality results are a model, not an engine: a quality::CheckResult
holds a check's name, its column, a status (pass, warn, fail or error),
what it observed and expected, a message and a sample of the failing rows.
QualityReport draws them as rich_ext's test report draws a test run:
failures, errors and warnings first with their failing rows, then a table
of every check and a summary (3 passed, 1 warned, 2 failed).
quality::not_null and quality::unique are two small checks over Rows.
use ;
let report = new;
console.print;
Both draw with theme keys a console theme can override: profile::STYLES
(profile.title, profile.column, profile.type, profile.note,
profile.null) and quality::STYLES (quality.pass, quality.warn,
quality.fail, quality.error, quality.check, quality.dim).
Features
| Feature | Default | What it adds |
|---|---|---|
arrow |
no | rich_data::arrow: RecordBatch rows, a streaming BatchSource, Arrow schemas in the model, and the schema explorer (tree, diff) (arrow-array and arrow-schema) |
er |
no | rich_data::er: ER diagrams of a schema or of SQL DDL (model, from_sql), through rs-rich-diagram |
Limits
JSON Lines refuses a line longer than 64 MiB, and every adapter describes nested values to 32 levels. Streaming sources choose their columns from the first 1,000 records (configurable) and report keys seen later instead of growing new columns. A window holds at most 10,000 rows, and samples at most 10,000 rows for its column widths. A streamed CSV record (a line, or a quoted field across lines) is refused past 64 MiB, and a profile holds at most its sample.
Independent SemVer from 0.0.1; see the repository's AGENTS.md.