Crystal Studio Labs · v1.0.3
CPU, memory, disk, network, battery, GPU — live terminal dashboard with sparklines, threshold alerts, HTTP API, file logging, CLI binary and full TypeScript support. Zero external dependencies.
Why crystalsystem.js
Built entirely on Node.js built-ins. No audit warnings, no dependency tree, no version conflicts — ever.
▁▂▄▆█ ASCII history graphs for CPU and memory inside the terminal dashboard. Color-coded by severity.cs.on('data', fn) every tick. cs.on('alert', fn) on breach. cs.on('stop', fn) on teardown./ /cpu /memory /disk /network /battery /health — all CORS enabled.logger.readAll() for historical analysis — find peak CPU, average RAM and more.crystalsystem --once --json -p 3001 -l log.json --no-gpu — full control without writing a single line of code.htop..d.ts definitions for every function, interface, option and event. Zero @types packages required.Usage
Every example below is copy-paste ready. No config, no boilerplate, no extra packages.
const { crystalsystem } = require('@crystal-studio-labs/crystalsystem.js'); crystalsystem({ interval: 5000, // refresh every 5 seconds clearConsole: true, showColors: true, showNetwork: true, showDisk: true, showBattery: true, showGPU: true, showProcesses: true, httpPort: 3001, // optional live JSON API logFile: 'stats.json', // optional file log thresholds: { cpu: 80, memory: 75, disk: 85, }, });
const { CrystalSystem } = require('@crystal-studio-labs/crystalsystem.js'); const cs = new CrystalSystem({ interval: 2000, thresholds: { cpu: 80, memory: 75, disk: 85 }, }); // Fires every tick with a full SystemStats object cs.on('data', (stats) => { console.log('CPU:', stats.cpu.loadPercent); console.log('RAM:', stats.memory.percent); console.log('Net↓:', stats.network.rxSpeed); console.log('Net↑:', stats.network.txSpeed); }); // Fires when a threshold is breached cs.on('alert', ({ type, message, value, threshold }) => { console.error(`⚠️ [${type.toUpperCase()}] ${message}`); // Send to Discord, Slack, Telegram, email — see Alerts section }); cs.on('stop', () => console.log('Monitor stopped.')); cs.start(); // Change a threshold at runtime (no restart needed) cs.setThreshold('cpu', 70); // One-shot snapshot without a display loop const snap = cs.snapshot(); console.log(snap.cpu.model, snap.memory.total); // Stop after 60 seconds setTimeout(() => cs.stop(), 60_000);
const { crystalsystem, startHttpServer } = require('@crystal-studio-labs/crystalsystem.js'); // Start dashboard + HTTP API together crystalsystem({ httpPort: 3001 }); // ── Available endpoints ────────────────────────────── // GET / → All stats as JSON // GET /cpu → CPU model, speed, cores, usage % // GET /memory → Total, used, free, percent // GET /network → Speeds + cumulative traffic // GET /disk → Partitions, total, used, free // GET /battery → Level, charging status // GET /health → { status: 'ok', uptime: ... } // All responses include Access-Control-Allow-Origin: * // Or start the API server independently (no dashboard) const server = startHttpServer(4000); // server is a Node.js http.Server — call server.close() to stop // Fetch from anywhere const res = await fetch('http://localhost:3001/cpu'); const data = await res.json(); console.log(data.model, data.loadPercent);
const { crystalsystem, createLogger, getAllStats } = require('@crystal-studio-labs/crystalsystem.js'); // Auto-log every tick via the main monitor crystalsystem({ logFile: 'stats.json', interval: 10_000 }); // ── Or log manually ────────────────────────────────── const logger = createLogger('stats.json'); // Write a snapshot right now logger.write(getAllStats()); // Read all saved snapshots back const history = logger.readAll(); console.log(`${history.length} entries recorded`); // Analyse: find peak and average CPU const peakCPU = Math.max(...history.map(s => s.cpu.loadRaw)); const avgCPU = history.reduce((a, s) => a + s.cpu.loadRaw, 0) / history.length; console.log(`Peak: ${peakCPU.toFixed(2)}% Avg: ${avgCPU.toFixed(2)}%`);
import crystalsystem, { CrystalSystem, CrystalSystemOptions, SystemStats, AlertEvent, CPUInfo, MemoryInfo, } from '@crystal-studio-labs/crystalsystem.js'; const options: CrystalSystemOptions = { interval: 3000, thresholds: { cpu: 80, memory: 75, disk: 85 }, httpPort: 3001, }; const cs: CrystalSystem = crystalsystem(options); cs.on('data', (stats: SystemStats) => { const cpu: CPUInfo = stats.cpu; const mem: MemoryInfo = stats.memory; console.log(cpu.loadPercent, mem.percent); }); cs.on('alert', (alert: AlertEvent) => { console.error(`[${alert.type.toUpperCase()}] ${alert.message}`); });
# Install globally $ npm install -g @crystal-studio-labs/crystalsystem.js # Live dashboard (5s refresh default) $ crystalsystem # Custom interval $ crystalsystem -i 2 # One-shot display then exit $ crystalsystem --once # JSON snapshot to stdout (pipe-friendly) $ crystalsystem --json | jq '.cpu.loadPercent' # Dashboard + HTTP API on port 3001 + file log $ crystalsystem -p 3001 -l stats.json # Hide sections you don't need $ crystalsystem --no-disk --no-gpu --no-battery # Pipe clean output to a file $ crystalsystem --once --no-color > snapshot.txt # All flags $ crystalsystem --help
Documentation
Every function, method, option and TypeScript interface documented in one place.
Install from npm. No other packages are installed — crystalsystem.js uses only Node.js built-in modules.
Requires Node.js 14 or higher. Works on Linux, macOS, Windows, Android (Termux) and BSD.
All functions are available as named exports. Import only what you need.
| Function | Returns | Description |
|---|---|---|
| crystalsystem(opts?) | CrystalSystem | Start live monitor. Returns a running instance. |
| buildSystemTable(opts?) | string | Full ANSI dashboard as a string. No loop started. |
| getAllStats(opts?) | SystemStats | One-shot snapshot of all stats. No display. |
| startHttpServer(port?, opts?) | http.Server | Start HTTP API independently without dashboard. |
| createLogger(path) | Logger | Create a JSON-line file logger. |
| getPlatformInfo() | PlatformInfo | OS name, arch, hostname, release. |
| getCPUInfo() | CPUInfo | Model, speed, cores, real usage % via time delta. |
| getMemoryInfo() | MemoryInfo | Total, used, free, percentage. |
| getNetworkInfo() | NetworkInfo | Cumulative traffic and live speed. |
| getDiskInfo() | DiskInfo | Partitions, total, used, free. |
| getBatteryInfo() | BatteryInfo | Level and charging status. |
| getGPUInfo() | GPUInfo | GPU model where detectable. |
| getProcessInfo() | ProcessInfo | PID, Node version, heap usage. |
| getTopProcesses(n?) | TopProcess[] | Top N processes sorted by memory. |
| formatBytes(n, dec?) | string | Convert bytes to readable string — "1.4 GB". |
| sparkline(arr, width?) | string | ANSI sparkline from a number array. |
CrystalSystem extends Node's EventEmitter. Use it when you need programmatic control — starting and stopping, listening to events, or changing thresholds at runtime.
| Method | Returns | Description |
|---|---|---|
| .start() | this | Start the monitor loop and HTTP server if configured. |
| .stop() | this | Stop loop and close HTTP server. Emits 'stop'. |
| .display() | void | Render and print the dashboard immediately. |
| .snapshot() | SystemStats | Get a one-shot stats object without displaying. |
| .setThreshold(type, n) | this | Update a threshold at runtime. No restart needed. |
Pass an options object to crystalsystem() or new CrystalSystem(). All options are optional.
| Option | Type | Default | Description |
|---|---|---|---|
| interval | number | 5000 | Refresh in ms. Set to 0 to display once with no loop. |
| clearConsole | boolean | true | Clear terminal before each render. |
| showColors | boolean | true | Enable ANSI colors in the dashboard. |
| showNetwork | boolean | true | Show network section. |
| showDisk | boolean | true | Show disk section. |
| showBattery | boolean | true | Show battery section if supported. |
| showGPU | boolean | true | Show GPU section if detectable. |
| showProcesses | boolean | true | Show top processes section. |
| historySize | number | 30 | Number of data points kept for sparklines. |
| logFile | string|null | null | Path to JSON-line log file. Written every tick. |
| httpPort | number|null | null | Port to start the HTTP API server on. |
| thresholds.cpu | number | 90 | CPU alert threshold %. |
| thresholds.memory | number | 85 | Memory alert threshold %. |
| thresholds.disk | number | 90 | Disk alert threshold %. |
All events are emitted on the CrystalSystem instance. Use cs.on(event, fn) to listen.
| Event | Payload | Description |
|---|---|---|
| 'data' | SystemStats | Emitted every tick. Contains all stats in one object. |
| 'alert' | AlertEvent | Emitted when CPU, memory or disk exceeds threshold. |
| 'stop' | void | Emitted when .stop() is called. |
The AlertEvent object has four properties: type ('cpu' | 'memory' | 'disk'), message (string), value (number — current %), threshold (number — configured limit).
All interfaces are exported from the package. No @types package needed.
| Interface | Used for |
|---|---|
| CrystalSystemOptions | Options passed to crystalsystem() or new CrystalSystem() |
| SystemStats | Full snapshot — returned by snapshot() and 'data' event |
| AlertEvent | Payload of the 'alert' event |
| PlatformInfo | Return type of getPlatformInfo() |
| CPUInfo | Return type of getCPUInfo() |
| MemoryInfo | Return type of getMemoryInfo() |
| NetworkInfo | Return type of getNetworkInfo() |
| NetworkInterface | Individual interface entry inside NetworkInfo |
| DiskInfo | Return type of getDiskInfo() |
| PartitionInfo | Individual partition inside DiskInfo |
| BatteryInfo | Return type of getBatteryInfo() |
| GPUInfo | Return type of getGPUInfo() |
| ProcessInfo | Return type of getProcessInfo() |
| TopProcess | Individual entry in getTopProcesses() |
| AlertThresholds | Shape of the thresholds option |
| Logger | Return type of createLogger() |
Enable with httpPort: 3001 in options, or start independently with startHttpServer(3001). All endpoints return JSON with Access-Control-Allow-Origin: *.
| Route | Returns |
|---|---|
| GET / | Full SystemStats object |
| GET /cpu | CPUInfo — model, speed, cores, usage |
| GET /memory | MemoryInfo — total, used, free, percent |
| GET /network | NetworkInfo — speeds and cumulative traffic |
| GET /disk | DiskInfo — partitions, total, used, free |
| GET /battery | BatteryInfo — level and charging status |
| GET /health | { status: 'ok', uptime: number } |
All flags are available when running crystalsystem from the terminal after a global install.
| Flag | Short | Description |
|---|---|---|
| --help | -h | Show help and exit |
| --once | -o | Display once and exit (no loop) |
| --json | -j | Print JSON snapshot to stdout and exit |
| --interval <sec> | -i | Refresh every N seconds (default: 5) |
| --port <port> | -p | Start HTTP API server on this port |
| --log <file> | -l | Append stats to a JSON log file each tick |
| --no-color | Disable ANSI colors (good for piping) | |
| --no-network | Hide network section | |
| --no-disk | Hide disk section | |
| --no-battery | Hide battery section | |
| --no-gpu | Hide GPU section | |
| --no-processes | Hide top processes section | |
| --no-clear | Don't clear console between updates |
Alert Integrations
Every alert type is a standalone file in the examples repository. Find them at crystalsystem.js-examples.
Platform Support
On Android/Termux, crystalsystem.js falls back to /proc/cpuinfo when os.cpus() is restricted — CPU info still works correctly.