Skip to content

Latest commit

 

History

History
134 lines (115 loc) · 8.61 KB

File metadata and controls

134 lines (115 loc) · 8.61 KB

Perm Architecture

Overview

Perm is a terminal-based sorting analysis platform built on Python's modern async TUI framework (Textual) with high-performance tracing via msgspec and frame-based visualization.

System Architecture

┌──────────────────────────────────────────────────────────────────┐
│                        CLI Layer (Typer)                          │
│  run --viz │ benchmark │ arena │ replay │ export | config        │
└─────────────────────────┬────────────────────────────────────────┘
                          │
┌─────────────────────────▼────────────────────────────────────────┐
│                     UI Layer (Textual)                            │
│  PermApp │ SortScreen │ VizViewport │ FramePlayer │ Timeline     │
│  (FramePlayer-driven: play/pause/step/jump/reverse)              │
└─────────────────────────┬────────────────────────────────────────┘
                          │
┌─────────────────────────▼────────────────────────────────────────┐
│                      Service Layer                                │
│  ┌──────────┐ ┌──────────┐ ┌──────────┐ ┌──────────┐            │
│  │Algorithm │ │Benchmark │ │  Arena   │ │  Replay  │            │
│  │ Engine   │ │ Engine   │ │  Engine  │ │  Engine  │            │
│  └──────────┘ └──────────┘ └──────────┘ └──────────┘            │
└─────────────────────────┬────────────────────────────────────────┘
                          │
┌─────────────────────────▼────────────────────────────────────────┐
│                      Core Layer                                   │
│  ┌──────────┐ ┌──────────┐ ┌──────────┐ ┌──────────┐            │
│  │Algorithms│ │ Datasets │ │ Tracing  │ │ Metrics  │            │
│  │ 13 sorts │ │ 8 types  │ │msgspec   │ │Collector │            │
│  └──────────┘ └──────────┘ └──────────┘ └──────────┘            │
│  ┌──────────┐ ┌──────────┐ ┌──────────┐ ┌──────────┐            │
│  │Visualizer│ │Exporters │ │ Plugins  │ │  Config  │            │
│  │ 8 modes  │ │ 6 formats│ │ 3 types  │ │  TOML    │            │
│  └──────────┘ └──────────┘ └──────────┘ └──────────┘            │
└──────────────────────────────────────────────────────────────────┘

Data Flow (Visualization)

SortAlgorithm ──emit──▶ Tracer ──▶ TraceEvent[]
                                      │
                                      ▼
                                 FrameBuffer
                               (event → Frame)
                                      │
                                      ▼
                                 FramePlayer
                           (play/pause/step/jump)
                                      │
                                      ▼
                                 Visualizer.render(Frame)
                                      │
                                      ▼
                                 Renderable (Rich)

The sort algorithm emits trace events (compare, swap, write, partition, etc.) via the Tracer. The FrameBuffer converts events into discrete Frame objects (snapshot + element states). The FramePlayer drives playback. Visualizers accept a Frame and produce a Rich renderable.

Frame-Based Rendering Pipeline

  1. Algorithm runs to completion, emitting events to Tracer
  2. FrameBuffer.process_events() reconstructs array snapshots at each event
  3. Each Frame captures: array values, per-element states, timestamp
  4. FramePlayer iterates frames with play/pause/step/jump controls
  5. Visualizer converts Frame to Rich renderable (Text, Table, etc.)
  6. Rich Live or Textual displays the renderable in the terminal

Module Responsibilities

  • perm.algorithms: Sort algorithm implementations with tracing instrumentation
  • perm.datasets: Dataset generators for various distribution patterns
  • perm.tracing: High-performance event tracing with msgspec serialization
  • perm.metrics: Real-time metrics collection (comparisons, swaps, etc.)
  • perm.visualization: Frame-based rendering engine:
    • frame.py - Frame dataclass, ElementState enum, FrameBuffer (event→frame)
    • player.py - FramePlayer (playback state machine, timeline scrubbing)
    • base.py - Visualizer ABC (render(frame) → RenderableType)
    • bars.py - CAVA-style gradient bar visualizer (vertical + horizontal)
    • dots.py, heatmap.py, block.py, braille.py, numeric.py, motion.py
    • renderer.py - Mode-dispatching coordinator
  • perm.benchmarking: Statistically sound benchmarking with warmup and outlier removal
  • perm.arena: Tournament system with ELO ratings
  • perm.replay: Trace replay with play/pause/step controls
  • perm.exporters: Multi-format export (JSON, CSV, Markdown, HTML, GIF, PNG sequence)
  • perm.plugins: Plugin system for custom algorithms, datasets, and visualizers
  • perm.config: TOML-based configuration with Pydantic models
  • perm.cli: Typer-based command-line interface (--viz for live animation)
  • perm.ui: Textual-based terminal UI with FramePlayer-driven dashboard

Key Design Decisions

  1. Frame-based visualization: Algorithms emit events → FrameBuffer builds frames → Visualizer renders. Decouples algorithm logic from rendering; enables frame-by-frame scrubbing, replay, and export.
  2. msgspec for tracing: High-performance binary serialization for millions of trace events
  3. Rich for rendering: Battle-tested terminal rendering with full Unicode, gradient color support
  4. Textual for TUI: Async, non-blocking terminal UI with CSS-like styling
  5. Pydantic for config: Type-safe configuration with validation
  6. FramePlayer owns state machine: Separates playback concerns from visualizer rendering
  7. CAVA-style bars: Gradient colors (blue→cyan→white) with Unicode partial blocks for smooth edges

Visualization Modes

Mode Description Best for
bars CAVA-style vertical gradient bars General purpose, beautiful default
horizontal Left-to-right gradient bars Wide datasets, comparison overview
dots Dot plot density visualization Large datasets (10k+)
heatmap Character-cell heatmap Pattern recognition
braille High-density braille dot matrix Terminal-density visualization
block Multi-row block rendering Quick visual scan
numeric Raw number display Debugging, small datasets
motion Element movement trails Understanding swap/merge patterns

CLI --viz Animation

The perm run --viz command uses Rich's Live display to animate through frames at the specified FPS:

perm run --algorithm QuickSort --dataset Random --size 50 --viz --fps 30
Option Default Description
--viz / --no-viz --no-viz Enable live animation
--viz-mode bars Visualization mode
--fps 30 Animation speed