RepoPilotOpen in app →

Alexays/Waybar

Highly customizable Wayland bar for Sway and Wlroots based compositors. :v: :tada:

Healthy

Healthy across the board

Use as dependencyHealthy

Permissive license, no critical CVEs, actively maintained — safe to depend on.

Fork & modifyHealthy

Has a license, tests, and CI — clean foundation to fork and modify.

Learn fromHealthy

Documented and popular — useful reference codebase to read through.

Deploy as-isHealthy

No critical CVEs, sane security posture — runnable as-is.

  • Last commit 5d ago
  • 21+ active contributors
  • Distributed ownership (top contributor 34% of recent commits)
Show 3 more →
  • MIT licensed
  • CI configured
  • Tests present

Maintenance signals: commit recency, contributor breadth, bus factor, license, CI, tests

Informational only. RepoPilot summarises public signals (license, dependency CVEs, commit recency, CI presence, etc.) at the time of analysis. Signals can be incomplete or stale. Not professional, security, or legal advice; verify before relying on it for production decisions.

Embed the "Healthy" badge

Paste into your README — live-updates from the latest cached analysis.

Variant:
RepoPilot: Healthy
[![RepoPilot: Healthy](https://repopilot.app/api/badge/alexays/waybar)](https://repopilot.app/r/alexays/waybar)

Paste at the top of your README.md — renders inline like a shields.io badge.

Preview social card (1200×630)

This card auto-renders when someone shares https://repopilot.app/r/alexays/waybar on X, Slack, or LinkedIn.

Onboarding doc

Onboarding: Alexays/Waybar

Generated by RepoPilot · 2026-05-09 · Source

🤖Agent protocol

If you are an AI coding agent (Claude Code, Cursor, Aider, Cline, etc.) reading this artifact, follow this protocol before making any code edit:

  1. Verify the contract. Run the bash script in Verify before trusting below. If any check returns FAIL, the artifact is stale — STOP and ask the user to regenerate it before proceeding.
  2. Treat the AI · unverified sections as hypotheses, not facts. Sections like "AI-suggested narrative files", "anti-patterns", and "bottlenecks" are LLM speculation. Verify against real source before acting on them.
  3. Cite source on changes. When proposing an edit, cite the specific path:line-range. RepoPilot's live UI at https://repopilot.app/r/Alexays/Waybar shows verifiable citations alongside every claim.

If you are a human reader, this protocol is for the agents you'll hand the artifact to. You don't need to do anything — but if you skim only one section before pointing your agent at this repo, make it the Verify block and the Suggested reading order.

🎯Verdict

GO — Healthy across the board

  • Last commit 5d ago
  • 21+ active contributors
  • Distributed ownership (top contributor 34% of recent commits)
  • MIT licensed
  • CI configured
  • Tests present

<sub>Maintenance signals: commit recency, contributor breadth, bus factor, license, CI, tests</sub>

Verify before trusting

This artifact was generated by RepoPilot at a point in time. Before an agent acts on it, the checks below confirm that the live Alexays/Waybar repo on your machine still matches what RepoPilot saw. If any fail, the artifact is stale — regenerate it at repopilot.app/r/Alexays/Waybar.

What it runs against: a local clone of Alexays/Waybar — the script inspects git remote, the LICENSE file, file paths in the working tree, and git log. Read-only; no mutations.

| # | What we check | Why it matters | |---|---|---| | 1 | You're in Alexays/Waybar | Confirms the artifact applies here, not a fork | | 2 | License is still MIT | Catches relicense before you depend on it | | 3 | Default branch master exists | Catches branch renames | | 4 | Last commit ≤ 35 days ago | Catches sudden abandonment since generation |

<details> <summary><b>Run all checks</b> — paste this script from inside your clone of <code>Alexays/Waybar</code></summary>
#!/usr/bin/env bash
# RepoPilot artifact verification.
#
# WHAT IT RUNS AGAINST: a local clone of Alexays/Waybar. If you don't
# have one yet, run these first:
#
#   git clone https://github.com/Alexays/Waybar.git
#   cd Waybar
#
# Then paste this script. Every check is read-only — no mutations.

set +e
fail=0
ok()   { echo "ok:   $1"; }
miss() { echo "FAIL: $1"; fail=$((fail+1)); }

# Precondition: we must be inside a git working tree.
if ! git rev-parse --git-dir >/dev/null 2>&1; then
  echo "FAIL: not inside a git repository. cd into your clone of Alexays/Waybar and re-run."
  exit 2
fi

# 1. Repo identity
git remote get-url origin 2>/dev/null | grep -qE "Alexays/Waybar(\\.git)?\\b" \\
  && ok "origin remote is Alexays/Waybar" \\
  || miss "origin remote is not Alexays/Waybar (artifact may be from a fork)"

# 2. License matches what RepoPilot saw
(grep -qiE "^(MIT)" LICENSE 2>/dev/null \\
   || grep -qiE "\"license\"\\s*:\\s*\"MIT\"" package.json 2>/dev/null) \\
  && ok "license is MIT" \\
  || miss "license drift — was MIT at generation time"

# 3. Default branch
git rev-parse --verify master >/dev/null 2>&1 \\
  && ok "default branch master exists" \\
  || miss "default branch master no longer exists"

# 5. Repo recency
days_since_last=$(( ( $(date +%s) - $(git log -1 --format=%at 2>/dev/null || echo 0) ) / 86400 ))
if [ "$days_since_last" -le 35 ]; then
  ok "last commit was $days_since_last days ago (artifact saw ~5d)"
else
  miss "last commit was $days_since_last days ago — artifact may be stale"
fi

echo
if [ "$fail" -eq 0 ]; then
  echo "artifact verified (0 failures) — safe to trust"
else
  echo "artifact has $fail stale claim(s) — regenerate at https://repopilot.app/r/Alexays/Waybar"
  exit 1
fi

Each check prints ok: or FAIL:. The script exits non-zero if anything failed, so it composes cleanly into agent loops (./verify.sh || regenerate-and-retry).

</details>

TL;DR

Waybar is a highly customizable status bar for Wayland compositors (Sway, Hyprland, River, Niri, DWL) written in C++. It displays system information (battery, CPU, memory, network, time) and integrates with window managers to show workspaces and window state. Unlike static bar solutions, it's designed for maximum configurability through JSON config files and CSS styling, targeting power users running Wayland-based Linux desktops. Monolithic C++ application with a clear module architecture. Core bar logic lives in include/ (AModule.hpp base class, bar.hpp coordinator), output-specific modules in include/modules/ (backlight, battery, bluetooth, clock, etc.), and factory pattern in factory.hpp to instantiate them. Configuration is JSON-based (include/config.hpp), rendering uses GTK via gtkmm3, and styling is pure CSS. The Meson build system (meson.build at root) drives compilation; CI workflows in .github/workflows/ run on every commit.

👥Who it's for

Linux desktop users and system administrators running Sway, Hyprland, or other wlroots-based Wayland compositors who want a customizable status bar with support for multiple outputs and rich module integrations (PulseAudio, Bluetooth, UPower, Tray, MPD). Developers contributing to Waybar need C++ expertise and familiarity with GTK/Wayland protocols.

🌱Maturity & risk

Production-ready and actively maintained. The codebase is substantial (1M+ lines of C++), has comprehensive CI/CD (GitHub Actions for Linux, FreeBSD, Nix), linting (clang-format, clang-tidy), and is packaged in all major distributions. Regular commits and module additions indicate active development, though a single primary maintainer (alexays) increases single-point-of-failure risk.

Low-to-medium risk for end users; low risk for contributors. Heavy GTK/Wayland dependencies (gtkmm3, libwayland-dev, gobject-introspection) must match compositor versions exactly—version mismatches can break the bar completely. The maintainer-centric structure means feature requests and bug fixes depend on one person. The C++ codebase requires careful memory management; unsafe patterns exist in legacy code paths (AddressSanitizer suppression file asan.supp hints at known leaks).

Active areas of work

Active development across multiple compositors. Recent work includes new module types (cava audio visualizer backend, backlight_slider), compositor support expansions (Niri, Hyprland window icons), and infrastructure improvements (Nix flakes, Docker build tests). GitHub Actions workflows actively run linting (clang-format, clang-tidy) and cross-platform testing (Linux, FreeBSD). No major breaking changes evident, but incremental feature addition is the norm.

🚀Get running

git clone https://github.com/Alexays/Waybar
cd Waybar
meson setup build
ninja -C build
./build/waybar
# Install system-wide:
ninja -C build install
waybar

Daily commands: After meson setup build && ninja -C build, run ./build/waybar to start. For development, modify include/modules/.hpp and src/modules/.cpp, then ninja -C build rebuilds. Use waybar --config /path/to/config.json to test custom configs. Set WAYBAR_STYLE=/path/to/style.css to load custom CSS. Debug builds use -Db_sanitize=address in meson setup for AddressSanitizer.

🗺️Map of the codebase

  • include/AModule.hpp: Base class for all modules; defines the interface (update(), ALabel) and signal system every custom module must inherit
  • include/bar.hpp: Core bar coordinator managing GTK window, layer shell positioning, module lifecycle, and Wayland event loop
  • src/factory.cpp: Factory pattern implementation that instantiates all available modules by name; this is where new modules must be registered
  • [include/config.hpp & src/config.cpp](https://github.com/Alexays/Waybar/blob/master/include/config.hpp & src/config.cpp): JSON configuration schema and parser; changes to bar behavior almost always require config schema updates here
  • .github/workflows/linux.yml: Primary CI pipeline defining build steps, dependency installation, and test execution on Ubuntu; critical for validating PRs
  • meson.build: Meson build configuration; declares all dependencies, compiler flags, and build targets; required for any build system changes
  • include/modules/: Directory containing all ~30 module headers (backlight, battery, bluetooth, clock, cpu, etc.); reference existing modules when creating new ones
  • src/modules/: Implementation directory for all modules; where business logic (D-Bus calls, sysfs reads, timer updates) actually happens

🛠️How to make changes

New module: Create include/modules/mymodule.hpp (inherit AModule) and src/modules/mymodule.cpp (implement update logic), then register in src/factory.cpp. Config changes: Modify include/config.hpp and src/config.cpp for schema. Styling: Edit bar.css or user's ~/.config/waybar/style.css (GTK CSS syntax). Compositor integration: Add window manager logic to src/bar.cpp (workspace updates, focus events). CI/linting: Run clang-format -i file.cpp and ensure .clang-tidy checks pass before pushing.

🪤Traps & gotchas

GTK version coupling: Waybar is tightly bound to specific gtkmm3/GTK3 versions; mismatched versions between build and runtime can cause silent crashes or missing modules. Wayland protocol fragmentation: Different compositors (Sway vs. Hyprland vs. Niri) implement slightly different protocol extensions; module behavior varies across compositors. CSS quirks: GTK CSS is not web CSS; box-shadow, gradients, and certain properties are unsupported; test styling on target compositor. D-Bus permission issues: Modules using UPower, Bluetooth, or systemd require proper D-Bus policies; runs under user session, not system session. DISPLAY unset: Waybar requires Wayland, not X11; setting DISPLAY=:0 will break it silently. Config path defaults: ~/.config/waybar/config.json is searched but not auto-created; missing config falls back to compile-time defaults which may be empty.

💡Concepts to learn

  • Wayland protocols & wlr-layer-shell — Waybar is fundamentally a Wayland client that positions itself as a layer above the compositor; the layer-shell protocol (implemented via gtk-layer-shell) is how the bar anchors to screen edges and reserves space—critical for understanding output/positioning code in bar.hpp
  • D-Bus & systemd activation — Many Waybar modules (Bluetooth, UPower, systemd services, Wireplumber audio) communicate via D-Bus; understanding D-Bus introspection and method calls is essential for debugging and extending modules that poll hardware or daemon state
  • GTK signal-slot event handling — Waybar uses libsigc++ for module-to-bar event propagation (updates, config changes); the signal pattern appears throughout AModule.hpp and avoids callback hell but requires understanding signal lifetime and connection scoping
  • JSON schema validation & configuration pipelines — Waybar's entire behavior is determined by ~/.config/waybar/config.json (schema in include/config.hpp); understanding how config is parsed, merged (per-output overrides), and validated is essential for feature development and user troubleshooting
  • Meson cross-platform build system — Unlike Make or CMake, Meson is Waybar's build toolchain; understanding meson.build syntax, dependency declarations, and feature flags is required for adding modules, changing libs, or porting to new platforms (FreeBSD tested in CI)
  • GTK CSS theming & CSS selector specificity — Waybar styling is pure GTK CSS (not web CSS); many user issues stem from CSS property misunderstandings (e.g., padding vs. margin behavior, missing properties like font-weight); understanding GTK CSS selectors and inheritance helps with styling modules
  • Factory & Strategy design patterns — Waybar uses factory pattern (factory.cpp) to instantiate modules by string name and strategy pattern (AModule base class) so modules can be swapped at runtime; understanding these patterns is key to adding new modules without touching core bar code
  • swaywm/sway — The primary window manager Waybar targets; understanding Sway's IPC protocol is essential for workspace and focus modules
  • hyprwm/Hyprland — Major Wayland compositor supported by Waybar with its own IPC; Hyprland users are Waybar's largest user segment
  • polybar/polybar — Spiritual predecessor for X11; Waybar was created as a Wayland replacement; many Waybar users migrated from Polybar and expect similar config syntax
  • greshake/i3status-rust — Alternative Wayland bar written in Rust with similar module architecture; useful for comparing design decisions and feature gaps

🪄PR ideas

To work on one of these in Claude Code or Cursor, paste: Implement the "<title>" PR idea from CLAUDE.md, working through the checklist as the task list.

Add comprehensive unit tests for module factory and IPC backends

The repo has complex module initialization logic (factory.hpp) and multiple IPC backends (Hyprland, Sway, River, DWL, Niri) but no visible test suite in the file structure. Given the variety of compositor support and the risk of regressions when adding new modules or fixing IPC communication bugs, adding tests for factory instantiation and backend message parsing would significantly improve maintainability. This is especially critical since IPC parsing bugs directly affect user experience across multiple compositors.

  • [ ] Create tests/factory_test.cpp for module instantiation logic in include/factory.hpp
  • [ ] Create tests/ipc/ directory with backend-specific tests (hyprland_ipc_test.cpp, sway_ipc_test.cpp, etc.)
  • [ ] Add test fixtures for parsing workspace/window messages from each compositor
  • [ ] Integrate tests into CI by adding test execution to .github/workflows/linux.yml
  • [ ] Reference specific IPC implementations in include/modules/hyprland/backend.hpp and equivalent files for other compositors

Add missing CI workflow validation for Clang-Tidy against actual source

The repo has .github/workflows/clang-tidy.yml.bak (disabled) and .clang-tidy configuration file, but no active static analysis in the CI pipeline. Given that Waybar is a systems-level bar with complex state management across modules and IPC communication, enabling Clang-Tidy in CI would catch potential use-after-free bugs, null pointer dereferences, and thread safety issues early. The .bak extension suggests it was deliberately disabled—investigating why and fixing the configuration would be valuable.

  • [ ] Examine .github/workflows/clang-tidy.yml.bak to understand why it was disabled
  • [ ] Create .github/workflows/clang-tidy-active.yml that runs clang-tidy against src/ and include/ directories
  • [ ] Configure it to fail on high-severity issues (performance, correctness, thread-safety)
  • [ ] Test locally using clang-tidy against include/modules/ and include/bar.hpp to validate
  • [ ] Document any suppressions needed in .clang-tidy and explain rationale in PR

Add integration tests for module state synchronization across Wayland events

Waybar supports multiple modules (battery, cpu, backlight, etc.) that must respond to Wayland events and system state changes. The file structure shows many module implementations (include/modules/battery.hpp, backlight_slider.hpp, etc.) but no visible integration tests validating that modules correctly update when underlying state changes. Adding tests that simulate Wayland events (brightness changes, power profile switches, workspace changes) and verify module output would prevent regressions when refactoring module update logic.

  • [ ] Create tests/integration/ directory with test harness for simulating Wayland/system events
  • [ ] Add tests/integration/battery_module_test.cpp to verify battery module responds to UPower signals
  • [ ] Add tests/integration/backlight_module_test.cpp to test brightness change detection
  • [ ] Add tests/integration/workspace_module_test.cpp for workspace changes across supported compositors
  • [ ] Reference AModule.hpp for the base module interface that tests should validate against
  • [ ] Integrate into CI by adding test execution to .github/workflows/linux.yml

🌿Good first issues

  • Add unit tests for config.cpp: The config parsing (include/config.hpp, src/config.cpp) lacks dedicated test coverage; write meson-integrated unit tests using existing framework to validate JSON schema edge cases and error handling.
  • Document module API in header comments: include/AModule.hpp and each include/modules/*.hpp lack doxygen-style documentation blocks; add detailed comments on signal lifecycle, update() contract, and required CSS classes for consistency with existing patterns.
  • Create a 'simple module' example: The repository lacks a minimal working module reference for contributors; create include/modules/example_simple.hpp and src/modules/example_simple.cpp that increments a counter every second, with setup.md instructions and meson registration.

Top contributors

Click to expand

📝Recent commits

Click to expand
  • 0594574 — Merge pull request #5013 from higorprado/fix/hyprland-lua-dispatch-protocol (Alexays)
  • 4c105f7 — Merge pull request #5007 from nschloe/toctou-fixes (Alexays)
  • 97917db — test(hyprland): expose dispatch internals for unit tests (higorprado)
  • e17c0d9 — fix(hyprland/workspaces): adapt dispatch commands for Lua IPC protocol (higorprado)
  • 5af324f — two more toctou bugs (nschloe)
  • 59d09c2 — fix various toctou bugs in battery.cpp (nschloe)
  • cca8dc3 — Merge pull request #4990 from B2krobbery/fix-sni-make-unique (Alexays)
  • 7e9c46e — fix(sni): use std::make_unique for Item allocation (B2krobbery)
  • 3a321d9 — Merge pull request #4982 from Mrpaoo/bug-fix (Alexays)
  • ac62754 — fix the lint problem (Mrpaoo)

🔒Security observations

Waybar appears to be a well-maintained C++ project with moderate security posture. The main concerns are around command execution in custom modules, IPC socket security for compositor communication, and configuration file handling. The project has security tooling in place (clang-tidy, ASAN) but several hardening measures should be implemented. No obvious hardcoded credentials were found in the visible file structure. The modular architecture allows users to disable features they don't trust, which is positive. Recommend: (1) conducting a security audit of IPC implementations, (2) hardening custom module execution, (3) implementing comprehensive input validation, and (4) ensuring all file operations respect proper permissions.

  • Medium · Potential Command Injection in Custom Module — include/modules/custom.hpp. The custom module (include/modules/custom.hpp) may execute arbitrary commands based on user configuration. If the waybar configuration file is writable by untrusted users or sourced from untrusted locations, this could lead to command injection attacks. Fix: Validate and sanitize all command inputs from configuration files. Use allowlist-based command validation. Ensure configuration files have proper file permissions (0600). Document security implications of custom modules.
  • Medium · IPC Communication Security — include/modules/hyprland/backend.hpp, include/modules/niri/backend.hpp, include/modules/dwl/. Multiple modules use IPC mechanisms (Hyprland, Niri, DWL, River backends) to communicate with window managers. If IPC sockets are not properly protected, local privilege escalation or information disclosure could occur. Fix: Verify that IPC sockets are created with restrictive permissions (0600). Validate all data received from IPC channels. Implement authentication checks for sensitive operations. Document IPC protocol security assumptions.
  • Medium · Hardcoded Paths and Configuration — include/config.hpp, include/bar.hpp. The codebase likely contains hardcoded paths for configuration and runtime files. If these are predictable or world-writable, they could be exploited for privilege escalation or TOCTOU attacks. Fix: Use secure temporary directories (/run/user/$UID for runtime files). Implement proper permission checks before reading/writing files. Use XDG_CONFIG_HOME and XDG_RUNTIME_DIR environment variables appropriately. Verify file ownership and permissions before operations.
  • Low · Dependency Version Management — flake.nix, flake.lock (partially present). No package lock file or version pinning information is visible in the provided file structure. This makes reproducible builds difficult and increases risk of pulling vulnerable dependency versions. Fix: Maintain and regularly update flake.lock. Pin exact versions of critical dependencies. Implement automated dependency vulnerability scanning in CI/CD. Use software composition analysis (SCA) tools.
  • Low · Potential Information Disclosure via Error Messages — include/modules/network.hpp, include/modules/bluetooth.hpp, include/modules/gps.hpp. Modules that interact with external services (network, bluetooth, GPS, etc.) may leak sensitive information through error messages or logs if not properly handled. Fix: Sanitize error messages before displaying/logging them. Avoid including sensitive paths, credentials, or system information in error output. Implement structured logging with appropriate log levels.
  • Low · Missing ASAN Suppressions Coverage — asan.supp. The presence of asan.supp file suggests potential memory safety issues. Suppressions should be minimal and all issues should be investigated. Fix: Review all entries in asan.supp and create tickets for underlying issues. Minimize suppressions to only known false positives. Enable Address Sanitizer in CI/CD pipeline. Address root causes rather than suppressing warnings.

LLM-derived; treat as a starting point, not a security audit.


Generated by RepoPilot. Verdict based on maintenance signals — see the live page for receipts. Re-run on a new commit to refresh.

Healthy signals · Alexays/Waybar — RepoPilot