Skip to content

c0m4r/kula

image

K U L A

Lightweight, self-contained Linux® server monitoring tool.

Go Go JS JS License: GPL v3

👀 Demo | 🐋 Docker Hub

Zero dependencies. No external databases. Single binary. Just deploy and go.

image

📦 What It Does

Kula collects system metrics every second by reading directly from /proc and /sys, stores them in a built-in tiered ring-buffer storage engine, and serves them through a real-time Web UI dashboard and a terminal TUI.

Metric What's Collected
CPU Total usage (user, system, iowait, irq, softirq, steal) + core count
Load 1 / 5 / 15 min averages, running & total tasks
Memory Total, free, available, used, buffers, cached, shmem
Swap Total, free, used
Network Per-interface throughput (Mbps), packets/s, errors, drops; TCP errors/s, resets/s, established connections; socket counts
Disks Per-device I/O (read/write bytes/s, reads/s, writes/s IOPS); filesystem usage
System Uptime, entropy, clock sync, hostname, logged-in user count
Processes Running, sleeping, blocked, zombie counts
Self Kula's own CPU%, RSS memory, open file descriptors

🪩 How It Works

                    ┌──────────────────────────────────────────────┐
                    │              Linux Kernel                    │
                    │     /proc/stat  /proc/meminfo  /sys/...      │
                    └──────────────────┬───────────────────────────┘
                                       │ read every 1s
                                       ▼
                              ┌──────────────────┐
                              │    Collectors    │
                              │  (cpu, mem, net, │
                              │   disk, system)  │
                              └────────┬─────────┘
                                       │ Sample struct
                          ┌────────────┼────────────┐
                          ▼            ▼            ▼
                   ┌────────────┐  ┌────────┐  ┌──────────┐
                   │  Storage   │  │  Web   │  │   TUI    │
                   │  Engine    │  │ Server │  │ Terminal │
                   └─────┬──────┘  └───┬────┘  └──────────┘
                         │             │ 
              ┌──────────┼─────────┐   └───────────┐  HTTP + WebSocket
              ▼          ▼         ▼               ▼
          ┌─────────┬─────────┬─────────┐  ┌───────────────┐
          │ Tier 1  │ Tier 2  │ Tier 3  │  │   Dashboard   │
          │   1s    │   1m    │   5m    │  │   (Browser)   │
          │ 250 MB  │ 150 MB  │  50 MB  │  └───────────────┘
          └─────────┴─────────┴─────────┘
             Ring-buffer binary files
             with circular overwrites

Storage Engine

Data is persisted in pre-allocated ring-buffer files per tier. Each tier file has a fixed maximum size — when it fills up, new data overwrites the oldest entries. This gives predictable, bounded disk usage with no cleanup needed.

  • Tier 1 — Raw 1-second samples (default 250 MB)
  • Tier 2 — 1-minute aggregates: averaged CPU & network, last-value gauges (default 150 MB)
  • Tier 3 — 5-minute aggregates, same logic (default 50 MB)

HTTP server

The HTTP server on backend exposes a REST API and a WebSocket endpoint for live streaming. Authentication is optional - when enabled, it uses Argon2id hashing with salt and session cookies. It is worth adding that Kula truly respects your privacy. It works on closed networks and does not make any calls to external services.

Dashboard

The frontend is a single-page application embedded in the binary. Built on Chart.js with custom SVG gauges, it connects via WebSocket for live updates and falls back to history API for longer time ranges. Features include:

  • Interactive zoom with drag-select (auto-pauses live stream)
  • Focus mode to show only selected graphs
  • Grid / stacked list layout toggle
  • Alert system for clock sync, entropy issues, overload

💾 Installation

Kula was built to have everything in one binary file. You can just upload it to your server and not worry about installing anything else because Kula has no dependencies. It just works out of the box! It is a great tool when you need to quickly start real-time monitoring.

Example installation methods for amd64 (x86_64) GNU/Linux.

Check Releases for ARM and RISC-V packages.

Standalone

wget https://github.com/c0m4r/kula/releases/download/0.7.4/kula-0.7.4-amd64.tar.gz
echo "6e1a6a389b446d599032f1b3e9940e706fdf820efad25fcac0606ba6a581fac2 kula-0.7.4-amd64.tar.gz" | sha256sum -c || rm kula-0.7.4-amd64.tar.gz
tar -xvf kula-0.7.4-amd64.tar.gz
cd kula
./kula

Docker

# With persistent storage
docker run -d --name kula --pid host --network host -v /proc:/proc:ro -v kula_data:/app/data c0m4r/kula:latest
docker logs -f kula

# Temporary, no persistent storage
docker run --rm -it --name kula --pid host --network host -v /proc:/proc:ro c0m4r/kula:latest

Debian / Ubuntu

wget https://github.com/c0m4r/kula/releases/download/0.7.4/kula-0.7.4-amd64.deb
echo "1444c1ec923c2df04ccc50955401392fc177cff1af57e91982b70d4549b52035 kula-0.7.4-amd64.deb" | sha256sum -c || rm kula-0.7.4-amd64.deb
sudo dpkg -i kula-0.7.4-amd64.deb
systemctl status kula

Arch / Manjaro (AUR)

wget https://github.com/c0m4r/kula/releases/download/0.7.4/kula-0.7.4-aur.tar.gz
echo "dffc7bf3adbb2476f690d494c6f086d64088c10ac4705663a6488849e96478c8 kula-0.7.4-aur.tar.gz" | sha256sum -c || rm kula-0.7.4-aur.tar.gz
tar -xvf kula-0.7.4-aur.tar.gz 
cd kula-0.7.4-aur
makepkg -si

Build from Source

git clone https://github.com/c0m4r/kula.git
cd kula
bash addons/build.sh

💻 Usage

Quick Start

# 1. Copy and edit config (optional)
cp config.example.yaml config.yaml

# 2. Start the server
./kula serve
# Dashboard at http://127.0.0.1:8080

# 3. Or use the terminal UI
./kula tui

Authentication (Optional)

# Generate password hash
./kula hash-password

# Add the output to config.yaml under web.auth

Service Management

Init system files are provided in addons/init/:

# systemd
sudo cp addons/init/systemd/kula.service /etc/systemd/system/
sudo systemctl enable --now kula

# OpenRC
sudo cp addons/init/openrc/kula /etc/init.d/
sudo rc-update add kula default

# runit
sudo cp -r addons/init/runit/kula /etc/sv/
sudo ln -s /etc/sv/kula /var/service/

⚙️ Configuration

All settings live in config.yaml. See config.example.yaml for defaults.


🧰 Development

# Lint + test suite
bash ./addons/check.sh

# Build dev (Binary size: ~11MB)
CGO_ENABLED=0 go build -o kula ./cmd/kula/

# Build prod (Binary size: ~8MB)
CGO_ENABLED=0 go build -trimpath -ldflags="-s -w" -buildvcs=false -o kula ./cmd/kula/

Updating Dependencies

To safely update only the Go modules used by Kula to their latest minor/patch versions, and prune any unused dependencies:

go get -u ./...
go mod tidy

Testing & Benchmarks

# Run unit tests with race detector
go test -race ./...

# Run the full storage benchmark suite (default: 3s per bench)
bash addons/benchmark.sh

# Shorter run for quick iteration
bash addons/benchmark.sh 500ms

# Python scripts formatter and linters
black addons/*.py
pylint addons/*.py
mypy --strict addons/*.py

Cross-Compile

bash addons/build.sh cross    # builds amd64, arm64, riscv64

Debian / Ubuntu (.deb)

bash addons/build_deb.sh
ls -1 dist/kula-*.deb

Arch Linux / Manjaro (AUR)

bash addons/build_aur.sh
cd dist/aur && makepkg -si

Red Hat / Fedora / Rocky Linux / AlmaLinux (.rpm)

bash addons/build_rpm.sh
ls -1 dist/kula-*.rpm

Docker

bash addons/docker/build.sh
docker compose -f addons/docker/docker-compose.yml up -d

📖 License

GNU Affero General Public License v3.0


🫶 Attributions

  • Linux® is the registered trademark of Linus Torvalds in the U.S. and other countries.
  • Chart.js library licensed under MIT