arta-tui 0.3.0

Terminal workspace manager for concurrent AI coding agent sessions (tmux/zellij)
arta-tui-0.3.0 is not a library.

🖼️ a r t a

agent runtime terminal application

Terminal workspace manager for concurrent AI coding agent usage. Enables parallel agent usage over a single SSH session.

Organize projects in a sidebar, run multiple threads (each backed by tmux or zellij), and switch between them — all from a single binary. Close, reopen and continue from where you left off.

 ┌────────────────┬─────────────────────────────────────────────┐
 │ -------------- │ ─────────────────────────────────────────── │
 │                │  $ ~/projects/my-app                        │
 │   🖼 a r t a   │  > claude                                   │
 │                │  ╭─────────────────────────────────────╮    │
 │ -------------- │  │ claude> fix the login bug           │    │
 │ ▼ my-app (2)   │  │ ...                                 │    │
 │   Fix login bug│  ╰─────────────────────────────────────╯    │
 │   Add OAuth  * │  $ npm test                                 │
 │ ▶ api-svc      │  ✓ 42 tests passed                          │
 │ ▼ fe-web1 (1)  │                                             │
 │   my-app-1   * │  $ █                                        │
 │                │ focused ─────────────────────────────────── │
 │ ---------------│               interactive | v0.2.1 | MIT   │
 │ ctrl+space run │ [] 1 claude * - 2 zsh       2026-04-25 13:46│
 │ J/K reorder    │                                             │
 └────────────────┴─────────────────────────────────────────────┘
      sidebar          tmux session (full PTY)

Features

  • Project sidebar — add, rename, reorder, and remove projects
  • Tmux or Zellij threads — each thread runs your coding agent + a shell, backed by a tmux (default) or zellij session for persistence
  • Configurable coding agent — defaults to claude, but can be set globally to codex, gemini, opencode, or any command, with per-project overrides (use a different agent — or a different invocation of the same agent — on a per-project basis)
  • Auto-named threads — threads pick up their name from the agent's terminal title (e.g., Refactoring auth module) instead of showing generic IDs. Manual rename (Ctrl+Space r) pins the name and disables further auto-updates
  • Thread persistence — quit ARTA, threads keep running. Reopen and reattach instantly
  • Thread restore — remembers and reopens your last active thread on startup
  • Multiple profiles — use ARTA_CONFIG_ROOT and ARTA_SESSION_PREFIX env vars to run independent ARTA instances with separate configs and threads
  • Open IDE — press o to launch your configured IDE (e.g., webstorm ., idea .) for any project
  • Project configuration — press c to configure project name, path, or open command via a navigable menu
  • Bell notifications — focus-aware bells via a Claude Code Notification hook (auto-installed into ~/.claude/settings.json); shows a sidebar indicator and plays a sound for unfocused threads, reliable across tmux and zellij
  • Nerd Font detection — auto-detects and uses icons when available, falls back to Unicode
  • Full-width input panel — tab-complete paths, browse directories, rename with full cursor support
  • Single binary — built with Ratatui + tui-term + portable-pty

Install

arta needs tmux (the default backend) or zellij. The Homebrew install pulls in tmux automatically; for other install methods, install one yourself — see Requirements.

Homebrew (macOS, Linux)

brew install cjurjiu/arta/arta   # also installs tmux

Shell installer (macOS, Linux)

curl -fsSL https://github.com/cjurjiu/arta/releases/latest/download/arta-tui-installer.sh | sh

Cargo

cargo install arta-tui          # compile from crates.io (binary is `arta`)
cargo binstall arta-tui         # download prebuilt binary, no compile

mise / ubi

mise use -g ubi:cjurjiu/arta@latest

From source

# Install Rust: https://rustup.rs/
git clone https://github.com/cjurjiu/arta.git
cd arta
cargo build --release

The binary is at target/release/arta. Add it to your PATH or copy it somewhere convenient.

Requirements

  • macOS or Linux
  • Rust 1.85+ (via rustup)
  • tmux (default) or zellij
  • A terminal emulator (iTerm2, Ghostty, Kitty, etc.)
  • Optional: a Nerd Font for icons
  • Optional: disable macOS Ctrl+Space shortcut (System Settings → Keyboard → Keyboard Shortcuts → Input Sources)

Usage

arta

Prefix key (Ctrl+Space)

Ctrl+Space is the prefix key. Press it from any focus, then press a command. The sidebar footer shows available commands while the prefix is active.

After Ctrl+Space Action
/ Change focus (sidebar / terminal)
n New thread
o Open IDE (runs configured open command)
r Rename project or thread (pins thread name, disables auto-rename)
a Add project (path → name → open command)
c Configure project (rename, path, agent command, open command)
d Delete selected item (project or thread)
g Copy GitHub link to clipboard
q Quit (threads survive in the background)
Q Clean exit (kill all threads)

The status bar shows interactive or run mode. When Ctrl+Space is pressed, it switches to run mode with "awaiting command..." until a key is pressed.

Sidebar-only keys

These keys work only when the sidebar is focused (no prefix needed):

Key Action
j / k Navigate up/down
J / K Reorder project or thread
tab Expand/collapse project
enter Select thread
l Focus terminal

You can also click on either pane to switch focus.

Note: Ctrl+Space requires disabling macOS input source switching (see Requirements).

Inside the terminal

Each thread is backed by a tmux (or zellij) session with two windows:

  • agent — launches your configured coding agent (claude by default) automatically
  • terminal — a plain shell

Switch between them with your tmux prefix (e.g., Ctrl+A 1 / Ctrl+A 2) or zellij tab switching.

Input panel

When adding a project or renaming:

Key Action
Tab Autocomplete path
Up / Down Browse directory listing
Enter Confirm / descend into directory
Esc Cancel
Left / Right Move cursor in text

Configuration

ARTA stores its configuration and workspace state under ~/.arta/ by default.

Config file (~/.arta/config.yaml)

All fields are optional — ARTA uses sensible defaults if the file is missing or incomplete.

# The command launched in the agent window of new threads (default: "claude").
# This is the global default; individual projects can override it via
# Ctrl+Space c → Agent command.
coding_agent_command: claude

# Terminal multiplexer backend: "tmux" (default) or "zellij"
multiplexer: tmux

Per-project agent command

Each project can override the global coding_agent_command. From the sidebar, select a project and press Ctrl+Space cAgent command. Examples:

  • claude — plain Claude Code
  • codex — OpenAI Codex CLI
  • gemini, opencode, aider, … — anything you can run from a shell

Submit an empty value to clear the override and fall back to the global. The override is read at thread-create time; existing threads are not affected.

Environment variables

Variable Default Description
ARTA_CONFIG_ROOT ~/.arta/ Config directory. Set to a different path for separate profiles.
ARTA_SESSION_PREFIX (empty) Prefix added to session names. Prevents collisions between profiles.

Multiple profiles

Run independent ARTA instances with separate configs and threads:

# Work profile
ARTA_CONFIG_ROOT=~/.arta-work ARTA_SESSION_PREFIX=work arta

# Personal profile
ARTA_CONFIG_ROOT=~/.arta-personal ARTA_SESSION_PREFIX=personal arta

Each profile has its own config.yaml, workspace.yaml, and distinctly-named multiplexer sessions backing its threads (arta_work_t_* vs arta_personal_t_*).

Migration from older versions

On first run, ARTA automatically migrates your workspace from the legacy location (~/.config/arta/data/workspace.json) to the new location (~/.arta/workspace.yaml). Existing tmux sessions are also renamed to the new naming scheme. Workspace files using the older sessions: / active_session: / next_session_id: keys are loaded transparently and rewritten with the new threads: keys on first save.

Architecture

ARTA (Rust binary)
├── Config (YAML, ~/.arta/config.yaml)
│   └── Coding agent (global default + per-project overrides), multiplexer choice
├── Sidebar (ratatui widget)
│   └── Project & thread management
├── Input Panel (ratatui widget)
│   └── Full-width bottom panel for path/rename input
├── Terminal Panes (one per thread, via portable-pty + tui-term)
│   ├── vt100::Parser processes PTY output on background thread
│   └── tui-term::PseudoTerminal renders to ratatui buffer
├── Multiplexer (tmux or zellij, configurable)
│   └── One session backs each thread
│       ├── Window/tab "agent" → auto-launches coding agent
│       └── Window/tab "terminal" → plain shell
└── workspace.yaml (~/.arta/)
    └── Projects, threads, active thread & per-project config

Vocabulary: thread is the user-facing concept (what shows in the sidebar). Under the hood, each thread maps to a tmux/zellij session — the term is preserved everywhere ARTA talks to the multiplexer (CLI args, env vars, persistence keys for backward compat).

How it works

  • The sidebar manages projects and threads in ~/.arta/workspace.yaml
  • Each thread maps to a multiplexer session named arta_{prefix?}_{t|z}_{project}-{n} (e.g., arta_t_myproj-1); the thread's display name is independent and updates from the agent's terminal title
  • Each thread has its own PTY (via portable-pty) attached to its multiplexer session
  • A background reader thread per pane feeds PTY output into a vt100::Parser
  • Switching threads just changes which parser's screen is rendered — instant, no teardown
  • Auto-rename — every 500ms, ARTA queries the agent pane's terminal title (tmux display-message #{pane_title} / zellij action list-panes); if it changed and the user hasn't pinned the name with Ctrl+Space r, the sidebar updates. Generic agent labels like Claude Code are accepted as the initial name but never overwrite a more specific one (the "generic" check uses the thread's effective agent — global default or per-project override)
  • Per-project agent command — each project can override coding_agent_command via Ctrl+Space c → Agent command. Stored on the project in workspace.yaml. Resolved at thread-create time only — existing threads keep their original agent
  • Bell notifications are driven by a Claude Code Notification hook (merged idempotently into ~/.claude/settings.json) that touches a marker file under ~/.local/share/arta/bells/ for the current multiplexer session; ARTA polls that directory and raises attention for unfocused threads. Raw PTY BEL is also handled as a fallback
  • Key input is written directly to the active PTY's master fd — no message queue, minimal latency
  • Thread restore — the last active thread is saved to workspace.yaml and auto-reopened on startup; falls back to the first alive thread if the saved one is gone
  • When you quit (q), multiplexer sessions stay alive — reopen ARTA to reattach
  • When you clean exit (Q), all tracked threads (and their backing sessions) are killed

Known Issues

Ctrl+Space captured by macOS

Disable in System Settings → Keyboard → Keyboard Shortcuts → Input Sources.

Platforms

Platform Status
macOS Works
Linux Works
Windows + WSL Works (it's Linux)
Windows native Not supported (no tmux/zellij)

License

MIT. PRs are welcome.