# rawatpranjal/prefgraph architecture

> Architecture diagram of the GitHub repository rawatpranjal/prefgraph, generated by GitDiagram from its file tree, README and a sample of source files (last updated 2026-06-16). It is an AI-made overview: check details against the source.

- Interactive diagram: https://gitdiagram.com/rawatpranjal/prefgraph
- Repository: https://github.com/rawatpranjal/prefgraph

## Overview

1. PrefGraph is a dual-language analytics library for revealed-preference and choice-consistency scoring. The public user-facing API is Python (`prefgraph`), while the heavy computation lives in a Rust engine (`rpt-core`) exposed through a Python binding crate (`rpt-python`).

2. The main runtime boundary is Python orchestration vs. Rust execution. Python accepts DataFrames, arrays, parquet, and domain-specific logs; it normalizes them into internal session/panel objects and dispatches scoring. Rust performs graph algorithms, LP-based checks, cycle detection, and batch evaluation in parallel, with Rayon used for multi-user throughput.

3. The Python package under `src/prefgraph` is organized around three layers: core data structures (`BehaviorLog`, `Session`, `Panel`, result types), the analysis/engine entry points (`engine.py`, `analyze.py`, `auditor.py`, `encoder.py`), and algorithm wrappers (`algorithms/`). This is the primary application boundary that users interact with.

4. `src/prefgraph/algorithms` contains the per-metric implementations and domain-specific analyzers. It spans budget-choice methods such as GARP, CCEI/AEI, HARP, MPI, Houtman-Maks, VEI, welfare, production, quasilinear, intertemporal, and stochastic choice, plus discrete-choice and menu-related routines such as attention, ranking, risk, spatial, and integrability. `contrib/` mirrors many of these as experimental or extended variants.

5. `src/prefgraph/core` holds the shared result and reporting model. The `results/` subpackage defines structured outputs for different analysis families, while `display.py`, `summary.py`, and `mixins.py` support human-readable reporting and consistent result behavior across algorithms.

6. Data ingestion is split by domain. `src/prefgraph/datasets` provides loaders for demo and real-world datasets; `src/prefgraph/io/parquet.py` handles columnar data interchange; and `src/prefgraph/datasets/_generators.py` plus test generators support synthetic scenarios and stress cases. The repository also includes many dataset-specific adapters for e-commerce and recommender-style inputs.

7. The Rust workspace under `rust/` is the computational backend. `rpt-core` contains the algorithms and low-level primitives: graph traversal/SCC/transitive closure, LP utilities, choice axioms, production and welfare routines, stochastic and intertemporal models, and type definitions. `rpt-python` is the bridge crate that converts Python inputs into Rust-native structures and supports batch/parquet-oriented execution.

8. The data flow for a typical batch analysis is: user data enters Python, gets transformed into a normalized session/panel representation, is partitioned for streaming or per-user scoring, then passed into Rust for metric evaluation, and finally returned as flat result records or rich diagnostic objects. The README’s “Engine” vs “Function API” split reflects this architecture: the engine is optimized for high-volume scoring, while the function API exposes detailed diagnostics, matrices, and graphs for single-case investigation.

9. Visualization and human inspection are first-class but downstream concerns. `src/prefgraph/viz` generates attention plots, generic plots, and HTML templates, while the `docs/` and `examples/` trees provide narrative notebooks/scripts for quickstarts, benchmarks, and theory tutorials. These do not sit in the critical path of scoring, but they document and validate expected usage patterns.

10. Benchmarking and validation are extensive and form a separate subsystem. `benchmarks/` and `case_studies/` contain performance experiments, scaling tests, and domain studies for e-commerce, menu choice, and LLM-style benchmarks. They measure throughput, memory behavior, and cross-language parity, including a dedicated Rust benchmark crate and output artifacts for published results.

11. The test suite is broad and architecture-revealing: unit tests cover algorithm correctness, backend parity, parquet I/O, engine behavior, numerical stability, and result summaries; simulation tests verify theoretical properties across synthetic scenarios; and stress/evals tests probe edge cases such as singular matrices, overflow, LP failures, and tolerance sensitivity. This indicates the project prioritizes reproducibility and backend equivalence across Python and Rust.

12. Tooling and release infrastructure are centered on Python packaging plus CI/CD. `pyproject.toml` and the GitHub Actions workflows cover testing, installation, auditing, documentation, and release automation; ReadTheDocs configuration supports hosted docs; and the repository includes changelog/security/contribution files, suggesting a mature library distribution model rather than an application server or service.

Main entry points: [`src/prefgraph/engine.py`](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/engine.py) (Engine), [`rust/crates/rpt-core/src/lib.rs`](https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-core/src/lib.rs) (rpt-core), [`src/prefgraph/algorithms/__init__.py`](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/algorithms/__init__.py) (Algorithms), [`src/prefgraph/__init__.py`](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/__init__.py) (prefgraph)

## Diagram (Mermaid)

```mermaid
flowchart TD

subgraph group_python_api["Python API"]
  node_prefgraph_pkg["prefgraph<br/>python package<br/>[__init__.py]"]
  node_engine["Engine<br/>batch orchestration<br/>[engine.py]"]
  node_analyze["Analyze<br/>diagnostic api<br/>[analyze.py]"]
  node_auditor["Auditor<br/>inspection api<br/>[auditor.py]"]
  node_encoder["Encoder<br/>input normalization<br/>[encoder.py]"]
  node_core_types["Core types<br/>domain model<br/>[types.py]"]
  node_core_results["Result model<br/>reporting model<br/>[__init__.py]"]
  node_core_panel["Panel/session<br/>state model<br/>[panel.py]"]
  node_algorithms["Algorithms<br/>metric wrappers<br/>[__init__.py]"]
  node_contrib["Contrib<br/>experimental wrappers<br/>[__init__.py]"]
end

subgraph group_data_layer["Data & IO"]
  node_datasets["Datasets<br/>dataset loaders<br/>[__init__.py]"]
  node_parquet["Parquet IO<br/>columnar io<br/>[parquet.py]"]
  node_viz["Viz<br/>visualization<br/>[__init__.py]"]
end

subgraph group_rust_backend["Rust backend"]
  node_rpt_python["rpt-python<br/>py binding<br/>[lib.rs]"]
  node_convert["Convert<br/>rust bridge<br/>[convert.rs]"]
  node_batch["Batch exec<br/>rust bridge<br/>[batch.rs]"]
  node_rpt_core["rpt-core<br/>rust engine<br/>[lib.rs]"]
  node_graph_lp["Graph & LP<br/>native primitives<br/>[graph.rs]"]
  node_choice_metrics["Choice metrics<br/>native algorithms<br/>[garp.rs]"]
end

subgraph group_quality_docs["Validation & docs"]
  node_benchmarks["Benchmarks<br/>performance suite<br/>[rust_vs_python.py]"]
  node_tests["Tests<br/>test suite"]
  node_docs_examples["Docs & examples<br/>documentation<br/>[index.rst]"]
end

node_prefgraph_pkg -->|"exports"| node_engine
node_prefgraph_pkg -->|"exports"| node_analyze
node_prefgraph_pkg -->|"exports"| node_auditor
node_prefgraph_pkg -->|"exports"| node_algorithms
node_engine -->|"normalizes"| node_encoder
node_analyze -->|"returns"| node_core_results
node_auditor -->|"reports"| node_core_results
node_encoder -->|"builds"| node_core_types
node_core_panel -->|"wraps"| node_core_types
node_algorithms -->|"dispatches"| node_engine
node_algorithms -->|"specializes"| node_core_results
node_contrib -.->|"extends"| node_algorithms
node_datasets -->|"feeds"| node_encoder
node_parquet -->|"ingests"| node_encoder
node_viz -->|"renders"| node_core_results
node_engine -->|"calls"| node_rpt_python
node_rpt_python -->|"transforms"| node_convert
node_rpt_python -->|"executes"| node_batch
node_convert -->|"sends"| node_rpt_core
node_batch -->|"invokes"| node_rpt_core
node_rpt_core -->|"uses"| node_graph_lp
node_rpt_core -->|"implements"| node_choice_metrics
node_benchmarks -.->|"measures"| node_rpt_core
node_benchmarks -.->|"compares"| node_rpt_python
node_tests -.->|"validates"| node_engine
node_tests -.->|"parity"| node_rpt_core
node_docs_examples -.->|"documents"| node_algorithms
node_docs_examples -.->|"demonstrates"| node_engine

click node_prefgraph_pkg "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/__init__.py"
click node_engine "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/engine.py"
click node_analyze "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/analyze.py"
click node_auditor "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/auditor.py"
click node_encoder "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/encoder.py"
click node_core_types "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/core/types.py"
click node_core_results "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/core/results/__init__.py"
click node_core_panel "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/core/panel.py"
click node_algorithms "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/algorithms/__init__.py"
click node_contrib "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/contrib/__init__.py"
click node_datasets "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/datasets/__init__.py"
click node_parquet "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/io/parquet.py"
click node_viz "https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/viz/__init__.py"
click node_rpt_python "https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-python/src/lib.rs"
click node_convert "https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-python/src/convert.rs"
click node_batch "https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-python/src/batch.rs"
click node_rpt_core "https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-core/src/lib.rs"
click node_graph_lp "https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-core/src/graph.rs"
click node_choice_metrics "https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-core/src/garp.rs"
click node_benchmarks "https://github.com/rawatpranjal/prefgraph/blob/main/benchmarks/rust_vs_python.py"
click node_tests "https://github.com/rawatpranjal/prefgraph/blob/main/tests/test_backend_parity.py"
click node_docs_examples "https://github.com/rawatpranjal/prefgraph/blob/main/docs/index.rst"

classDef toneNeutral fill:#f8fafc,stroke:#334155,stroke-width:1.5px,color:#0f172a
classDef toneBlue fill:#dbeafe,stroke:#2563eb,stroke-width:1.5px,color:#172554
classDef toneAmber fill:#fef3c7,stroke:#d97706,stroke-width:1.5px,color:#78350f
classDef toneMint fill:#dcfce7,stroke:#16a34a,stroke-width:1.5px,color:#14532d
classDef toneRose fill:#ffe4e6,stroke:#e11d48,stroke-width:1.5px,color:#881337
classDef toneIndigo fill:#e0e7ff,stroke:#4f46e5,stroke-width:1.5px,color:#312e81
classDef toneTeal fill:#ccfbf1,stroke:#0f766e,stroke-width:1.5px,color:#134e4a
class node_prefgraph_pkg,node_engine,node_analyze,node_auditor,node_encoder,node_core_types,node_core_results,node_core_panel,node_algorithms,node_contrib toneBlue
class node_datasets,node_parquet,node_viz toneAmber
class node_rpt_python,node_convert,node_batch,node_rpt_core,node_graph_lp,node_choice_metrics toneMint
class node_benchmarks,node_tests,node_docs_examples toneRose
```

## Components

### Python API

User-facing package, orchestration, domain models, and algorithm wrappers.

- [prefgraph](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/__init__.py): python package · Top-level Python package entry point. · `src/prefgraph/__init__.py`
- [Engine](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/engine.py): batch orchestration · High-volume analysis entry point and batch dispatcher. · `src/prefgraph/engine.py`
- [Analyze](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/analyze.py): diagnostic api · Function-level analysis API with richer diagnostics. · `src/prefgraph/analyze.py`
- [Auditor](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/auditor.py): inspection api · Behavioral auditing and consistency workflows. · `src/prefgraph/auditor.py`
- [Encoder](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/encoder.py): input normalization · Normalizes raw inputs into sessions and panels. · `src/prefgraph/encoder.py`
- [Core types](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/core/types.py): domain model · Behavior logs, sessions, panels, and typed inputs. · `src/prefgraph/core/types.py`
- [Result model](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/core/results/__init__.py): reporting model · Structured outputs, summaries, and display behavior. · `src/prefgraph/core/results/__init__.py`
- [Panel/session](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/core/panel.py): state model · Shared session and panel containers used across the API. · `src/prefgraph/core/panel.py`
- [Algorithms](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/algorithms/__init__.py): metric wrappers · Python wrappers for revealed-preference and choice-consistency metrics. · `src/prefgraph/algorithms/__init__.py`
- [Contrib](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/contrib/__init__.py): experimental wrappers · Extended and experimental algorithm variants. · `src/prefgraph/contrib/__init__.py`

### Data & IO

Dataset loaders, parquet interchange, and visualization helpers.

- [Datasets](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/datasets/__init__.py): dataset loaders · Demo, real-world, and synthetic dataset adapters. · `src/prefgraph/datasets/__init__.py`
- [Parquet IO](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/io/parquet.py): columnar io · Columnar interchange for batch-oriented analysis. · `src/prefgraph/io/parquet.py`
- [Viz](https://github.com/rawatpranjal/prefgraph/blob/main/src/prefgraph/viz/__init__.py): visualization · Plots, attention figures, and HTML templates. · `src/prefgraph/viz/__init__.py`

### Rust backend

Native computation engine and Python binding bridge.

- [rpt-python](https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-python/src/lib.rs): py binding · Python-facing Rust bridge crate. · `rust/crates/rpt-python/src/lib.rs`
- [Convert](https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-python/src/convert.rs): rust bridge · Transforms Python inputs into Rust-native structures. · `rust/crates/rpt-python/src/convert.rs`
- [Batch exec](https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-python/src/batch.rs): rust bridge · Batch and parquet-oriented execution entry points. · `rust/crates/rpt-python/src/batch.rs`
- [rpt-core](https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-core/src/lib.rs): rust engine · Native computation engine for preference analysis. · `rust/crates/rpt-core/src/lib.rs`
- [Graph & LP](https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-core/src/graph.rs): native primitives · Graph traversal, closure, SCC, and LP utilities. · `rust/crates/rpt-core/src/graph.rs`
- [Choice metrics](https://github.com/rawatpranjal/prefgraph/blob/main/rust/crates/rpt-core/src/garp.rs): native algorithms · Core axioms, welfare, stochastic, production, and model checks. · `rust/crates/rpt-core/src/garp.rs`

### Validation & docs

Benchmarks, tests, examples, docs, and release tooling.

- [Benchmarks](https://github.com/rawatpranjal/prefgraph/blob/main/benchmarks/rust_vs_python.py): performance suite · Scaling, parity, memory, and benchmark experiments. · `benchmarks/rust_vs_python.py`
- [Tests](https://github.com/rawatpranjal/prefgraph/blob/main/tests/test_backend_parity.py): test suite · Correctness, parity, stress, and simulation coverage. · `tests/test_backend_parity.py`
- [Docs & examples](https://github.com/rawatpranjal/prefgraph/blob/main/docs/index.rst): documentation · Narrative docs, quickstarts, and example workflows. · `docs/index.rst`

## Connections

- prefgraph → Engine: exports · Package exposes the engine-oriented API.
- prefgraph → Analyze: exports · Package exposes the function-level API.
- prefgraph → Auditor: exports · Package exposes audit workflows.
- prefgraph → Algorithms: exports · Package exposes metric wrappers.
- Engine → Encoder: normalizes · Engine turns raw inputs into normalized analysis objects.
- Analyze → Result model: returns · Analysis API produces structured results and diagnostics.
- Auditor → Result model: reports · Auditing surfaces summaries and human-readable output.
- Encoder → Core types: builds · Encoder constructs session and panel objects.
- Panel/session → Core types: wraps · Panel and session containers build on shared typed inputs.
- Algorithms → Engine: dispatches · Metric wrappers route scoring through the engine boundary.
- Algorithms → Result model: specializes · Algorithms map outcomes into result families.
- Contrib → Algorithms: extends · Experimental variants mirror core algorithm families.
- Datasets → Encoder: feeds · Dataset loaders supply inputs for normalization.
- Parquet IO → Encoder: ingests · Parquet interchange feeds batch-oriented analysis.
- Viz → Result model: renders · Visualization consumes results for plots and HTML.
- Engine → rpt-python: calls · Python runtime hands batches to the binding layer.
- rpt-python → Convert: transforms · Binding layer converts Python objects to native structures.
- rpt-python → Batch exec: executes · Binding layer supports streaming and batch execution.
- Convert → rpt-core: sends · Converted inputs become native Rust workloads.
- Batch exec → rpt-core: invokes · Batch execution calls the Rust engine.
- rpt-core → Graph & LP: uses · Core algorithms rely on graph and LP primitives.
- rpt-core → Choice metrics: implements · Native engine computes the main preference and choice metrics.
- Benchmarks → rpt-core: measures · Benchmarks assess native throughput and scaling.
- Benchmarks → rpt-python: compares · Benchmarks compare Rust and Python execution paths.
- Tests → Engine: validates · Tests cover engine behavior and corner cases.
- Tests → rpt-core: parity · Tests check Python/Rust equivalence and numerical stability.
- Docs & examples → Algorithms: documents · Docs and examples explain the algorithm families.
- Docs & examples → Engine: demonstrates · Docs and examples show the high-volume workflow.
