jsonMartin/omastats

System monitor for the Omarchy bar: CPU, GPU, memory, disk, network, temperature, fan and battery stats with live graphs and a detailed panel. An iStat Menus-style activity monitor.

★ 0Forks 0GitHub ↗Compare

README

OmaStats

A system monitor for the Omarchy bar, in the spirit of Bjango's iStat Menus: CPU, GPU, memory, disk, network, temperatures, fans and battery stats at a glance. Compact readouts with live mini graphs sit in the bar; clicking one opens a panel with history graphs, ring gauges, sensors and the top processes, one tab per module. Everything it shows, in the bar and in the panel, is configurable from inside the panel.

OmaStats is an independent project and is not affiliated with Bjango.

OmaStats: a system monitor for the Omarchy bar

Memory, Network, Sensors and Settings pages

Modules

Module Bar readout Panel
CPU glyph · user/system history · % User/system history, per-core rings, load, uptime, top processes
GPU one readout per GPU · history · % Its own tab, with a card for every GPU
Memory glyph · used history · % Swap and memory rings, breakdown, processes
Disks glyph · read/write history · rates Volumes (click to open in Files), activity for all disks or one, processes
Network glyph · up/down history · rates Upload/download, interfaces, public and local IPs, traffic per process
Sensors any temperatures and fans you pick CPU/GPU/fan rings, every hwmon temperature and fan
Battery glyph by level · % Charge and health rings, charge history, power, cycles, peripherals

Battery and GPU only appear when the hardware exists. A machine with more than one GPU gets a readout per card, each tagged in the bar (NVD, AMD, INT); the Settings page picks which ones appear in the bar. The firmware boot display leads, followed by the other cards in PCI address order. The GPU tab always shows every detected card, including cards whose telemetry is unavailable. Intel's i915/xe drivers publish no utilisation counter through sysfs, so an Intel readout carries its clock and temperature and reports no load. NVIDIA cards remain visible when nvidia-smi is unavailable. Existing 1.0 tab settings keep access to GPU details when upgrading; GPU can then be hidden separately.

Install

omarchy plugin add https://github.com/crmne/omastats.git --enable

Or by hand: copy this directory to ~/.config/omarchy/plugins/crmne.omastats/, then omarchy plugin enable crmne.omastats.

Remove

omarchy plugin remove crmne.omastats

That disables the plugin and deletes its directory. By hand: omarchy plugin disable crmne.omastats, then remove ~/.config/omarchy/plugins/crmne.omastats/. Nothing is written outside that directory except this widget's own entry in ~/.config/omarchy/shell.json, which omarchy plugin disable removes.

What it needs

The plugin runs one small sampler process that reads procfs and sysfs. Two implementations ship with the same JSON protocol:

  • bin/omastats-sampler — the Rust binary for x86-64, about 3 MB resident and 0.3% CPU.
  • bin/omastats-sampler-aarch64 — the Rust binary for ARM64 Linux, statically linked with musl so it does not need a particular glibc version. Both are built from sampler/. Their checksums, byte-for-byte reproducible builds, and signed GitHub attestations are documented in BINARY_PROVENANCE.md.
  • sampler.py — a Python 3 fallback used whenever that binary is missing or cannot run here (another architecture, for instance). No third-party modules.

The service starts /usr/bin/python3 in isolated mode with a cleared environment. That entry point selects the Rust binary for the machine's architecture and replaces itself with it, retaining the same process ID; otherwise it continues as the Python sampler. No shell participates in the runtime launch path. Every emitted JSON record is capped before it reaches the shell's streaming parser, and the sampler is explicitly stopped when the plugin service is destroyed.

Optional command-line tools, each used only for the feature named, and each degrading to "unavailable" when missing: nvidia-smi (NVIDIA GPU readings; AMD and Intel come from sysfs), ip and iw (addresses, Wi-Fi signal), ss from iproute2 (per-process network traffic), curl (public IP lookup), wl-copy (copy an address), xdg-open (open a volume in your file manager).

Nothing runs as root, and no data leaves the machine except the optional public-IP lookup, which you can switch off in Settings. That lookup tries api.ipify.org, icanhazip.com, then ifconfig.me over HTTPS and stops after the first valid IP-address response.

make builds the native binary and checksum into bin/. On x86-64 Linux, make build-arm64 builds the portable ARM64 binary using a checksum-pinned toolchain downloaded into .cache/; it needs Python 3.12+, a C linker and tar, and does not change the system toolchain. make verify-binary checks two native builds against the bundled artifact (using the pinned Arch environment for x86-64); make verify-arm64 does the same for the portable ARM64 build. make install syncs the plugin into the Omarchy plugin directory.

Configuring

Open the panel and click the gear at the right end of the tab strip (or press s).

  • Bar: switch each module's readout on or off, order them with the arrows, and pick each one's look: a mini history graph, a fullness ring (CPU, GPU, memory, disk capacity, battery charge), a figure, or a graph or ring with the figure. The Disks readout can follow all disks or one device; the Sensors readout shows whichever temperatures and fans you tick.
  • Panel: choose which tabs appear and which sections each page shows.
  • General: temperature unit, refresh interval (0.1 s to 10 s), history span, bar graph width, and a reset.

Every process list has an All toggle that unfolds into every process with a search field (/ from anywhere in the panel), sorted by that page's column.

Changes are written to this widget's entry in ~/.config/omarchy/shell.json, so they survive restarts and each bar instance keeps its own. The same keys can be edited there by hand or through Setup → Plugins:

Key Default Meaning
modules cpu,memory,network Bar readouts, in order: cpu gpu memory disks network sensors battery
style both Default look of a readout: graph, ring, text, both (graph and figure), or ring-text
cpuStyle … batteryStyle (inherit) Per-module override of style
tabs cpu,gpu,memory,disks,network,sensors,battery Tabs shown in the panel
graphWidth 36 Width of each mini graph in the bar
barLabels text text stacks the module's letters vertically, icon uses glyphs
disksSource all Disk readout and activity graph: all or a device like nvme0n1
barSensors cpu Sensor readouts: cpu, gpu, or hwmon ids like nct6687/fan1
barGpus all Which GPUs get a readout: all, none, or PCI addresses like 0000:01:00.0 (pick them on the Settings page)
temperatureUnit Celsius Celsius or Fahrenheit
refreshSeconds 1 Sampling interval: 0.1, 0.2, 0.5, 1, 2, 5 or 10
historySeconds 240 How far back the graphs reach, in seconds
publicIp true Look up the public address (api.ipify.org) on the Network page
showProcesses true Top processes on every page
showCores, showLoad true CPU page sections
showBreakdown true Memory breakdown
showVolumes, showActivity true Disks page sections
showInterfaces, showTotals, showAddresses true Network page sections
showTemperatures, showFans true Sensors page sections
showHistory, showDetails, showDevices true Battery page sections

Several instances are allowed, so modules can be spread across the bar:

{ "id": "crmne.omastats", "modules": "cpu,memory" },
{ "id": "crmne.omastats", "modules": "network", "networkStyle": "graph" }

Interaction

  • Left click a readout opens its page; clicking the same readout again closes the panel.
  • Right click launches btop. Middle click refreshes the public IP.
  • In the panel: h/l or ←/→ switch tabs, 1–7 jump to a tab, s opens Settings, / searches processes, j/k scroll, Tab moves to the neighbouring bar panel, Esc closes, r refreshes.
  • Addresses on the Network page copy to the clipboard when clicked. Volumes on the Disks page open in the file manager.

The sampler reads cheap counters at the chosen interval and everything that walks many files (processes, sensors, battery, socket mapping) at most once a second, so 0.1 s refresh stays inexpensive. Per-process network traffic comes from the kernel's per-socket TCP byte counters (the same ones ss -ti shows), differenced once a second and tied to processes through /proc, so it needs no root. UDP, and therefore QUIC, carries no such counters and is not attributed.

IPC:

omarchy-shell crmne.omastats show sensors    # open on a tab (or "settings")
omarchy-shell crmne.omastats toggle network
omarchy-shell crmne.omastats hide
omarchy-shell crmne.omastats status          # JSON summary

Design notes

Graph colours come from the active theme: the accent is the first series and the theme colour furthest around the hue wheel (magenta, cyan or blue preferred) is the second, so user/system, upload/download and read/write always read as a pair in any theme. Warnings use the theme's yellow and red. Text never wears a data colour; identity comes from the dot beside it.

The tab strip gives every module an equal slot, the settings gear included, so nothing shifts when you switch, and the panel sizes itself so every tab is named in full. Abbreviations live only in the bar, where height is scarce: the readouts stack the module's letters (CPU, MEM, DSK, NET) the way iStat Menus labels its menubar items, with consistent device-pixel spacing between letters on scaled displays, unless you prefer glyphs.

Packaging maintenance

Release packaging uses the native-packages gem. native-packages.yaml declares packages and downstream repositories; native recipes and installation assets live in packaging/; see PACKAGING.md for local commands and CI behavior.

License

MIT

Contributors

crmne

Issues