Zellij improvements: zjstatus redesign, autolock, container integration#11
Zellij improvements: zjstatus redesign, autolock, container integration#11
Conversation
Replace default dual status bars with zjstatus single-line powerline bar matching tmux Catppuccin Mocha theme (mauve active tabs, transparent bg, dotted border, git branch, session name). Add plugins: zjframes (smart pane frame hiding), zellij-autolock (auto-lock in vim/neovim/helix), zsm (zoxide session switcher on Ctrl+o z). Add Ctrl+b g for lazygit floating pane (mirrors tmux Prefix g). Add 'zj' fish abbreviation for zellij. Remove ~250 lines of commented-out default options.
Two-bar layout matching merikan/catppuccin zjstatus template: - Top bar: round pill session/mode/tabs with E0B6/E0B4 glyphs, two-tone tabs (colored index + surface1 name), git branch + datetime - Bottom bar: mode-specific keybinding hints (Ctrl + Alt shortcuts) - Solid surface0 bar background, no hide_frame_for_single_pane (was causing blink loop with dual zjstatus instances)
- Set pane_frames false: no borders on single pane, simple separators between multiple panes (no full box borders) - Transparent bar background: format_space empty, bg=default for all bar elements so pills float on terminal background
Bottom bar: Ctrl shortcuts left-aligned (mode-aware), Alt shortcuts right-aligned (static). Top bar gets a dotted ┈ border in surface0 color as a subtle separator from content panes.
New component-based theme overrides frame_unselected (surface0), frame_selected (surface2), and frame_highlight (surface1) for subtle pane separators without affecting ANSI terminal colors.
…lish - Custom catppuccin-mocha-subtle theme with dim pane borders (frame_unselected, frame_selected, frame_highlight using surface0/1/2) - Right-side pills: swap layout, hostname, CPU load, datetime, session, mode - Tabs moved to left side with full width - Autolock plugin: Ctrl+g toggles both lock mode and auto-detection - Bottom hints bar gets dotted border separator above it - Removed git branch widget (zjstatus can't follow focused pane cwd) - Removed fish zjstatus git hook (caused pane freeze) - Session pill uses merikan reference icon, hard right edge flowing to mode
Track upstream features and plugins to revisit: auto tab rename (blocked on CwdChanged event), clickable session widget, autolock status indicator, mouse bindings, image protocol passthrough.
Simplify right side to: swap layout, hostname, session, mode.
There was a problem hiding this comment.
Pull request overview
Updates the Zellij setup (layouts, keybinds, plugins, and theme) to more closely match the repo’s tmux UX, and adds a small quality-of-life Fish abbreviation.
Changes:
- Adds a new default Zellij layout using
zjstatusfor redesigned top/bottom status bars and swap layouts. - Updates Zellij keybinds/plugins to integrate autolock toggling with
Ctrl+g, adds zsm/lazygit launchers, and introduces a custom “subtle” Catppuccin theme. - Adds a Fish abbreviation for
zj→zellijand introduces a “future changes” tracking doc.
Reviewed changes
Copilot reviewed 5 out of 5 changed files in this pull request and generated 8 comments.
Show a summary per file
| File | Description |
|---|---|
| dot_config/zellij/layouts/default.kdl | New default layout using zjstatus for top/bottom bars and swap layouts. |
| dot_config/zellij/config.kdl.tmpl | Autolock integration, extra keybinds, background plugin load, and custom theme selection. |
| dot_config/fish/conf.d/zz_04_abbr.fish | Normalizes some abbr definitions and adds zj abbreviation. |
| dot_config/fish/conf.d/zz_03_interactive.fish | Minor formatting-only change near the end of the interactive setup. |
| docs/zellij-future-changes.md | New doc to track upstream Zellij/zjstatus feature gaps and follow-ups. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| # Set simple hostname for prompt display | ||
| set -gx HOST (string split -f1 '.' $hostname) | ||
|
|
||
|
|
There was a problem hiding this comment.
There are two consecutive blank lines added before end, which makes the block look like it has trailing whitespace. Consider removing the extra empty lines to keep the interactive config tight/consistent.
| layout { | ||
| default_tab_template { | ||
| pane size=2 borderless=true { | ||
| plugin location="https://github.com/dj95/zjstatus/releases/latest/download/zjstatus.wasm" { |
There was a problem hiding this comment.
default.kdl hardcodes the zjstatus plugin via a GitHub releases/latest URL in two places. Since this repo already uses Zellij plugin aliases (see config.kdl.tmpl plugins { ... }), consider defining a zjstatus alias there and referencing it here to centralize updates and avoid duplicating the URL.
| plugin location="https://github.com/dj95/zjstatus/releases/latest/download/zjstatus.wasm" { | |
| plugin location="zjstatus" { |
| theme "catppuccin-mocha-subtle" | ||
| pane_frames false | ||
| copy_command "{{ template "copy-cmd" . }}" |
There was a problem hiding this comment.
The PR description calls out “subtle pane borders”, but the config sets pane_frames false, which disables pane borders entirely. Either enable pane_frames to make the new frame_* theme entries take effect, or adjust the description/theme to match the intended UI.
| bind "z" { | ||
| LaunchOrFocusPlugin "https://github.com/liam-mackie/zsm/releases/latest/download/zsm.wasm" { | ||
| floating true | ||
| move_to_focused_tab true | ||
| } | ||
| SwitchToMode "normal" |
There was a problem hiding this comment.
LaunchOrFocusPlugin uses the zsm plugin via a releases/latest URL. For consistency with the rest of the config (which uses plugin aliases like session-manager, plugin-manager, autolock), consider adding a zsm entry in the plugins { ... } section and referencing it by alias here.
| autolock location="https://github.com/fresh2dev/zellij-autolock/releases/latest/download/zellij-autolock.wasm" { | ||
| is_enabled true | ||
| triggers "nvim|vim|vi|helix|hx|fzf|atuin" | ||
| reaction_seconds "0.3" | ||
| print_to_log true | ||
| } | ||
| } | ||
|
|
||
| // Plugins to load in the background when a new session starts | ||
| // eg. "file:/path/to/my-plugin.wasm" | ||
| // eg. "https://example.com/my-plugin.wasm" | ||
| load_plugins { | ||
| autolock | ||
| } |
There was a problem hiding this comment.
The autolock plugin is configured from a mutable releases/latest GitHub URL and auto-loaded via load_plugins, so unpinned third-party WASM code is fetched and executed on every new session. A compromised GitHub release or account could replace zellij-autolock.wasm with malicious code that runs with your terminal user’s privileges. Reduce this supply-chain risk by vendoring the plugin or pinning to a specific immutable version or hash rather than using releases/latest.
| layout { | ||
| default_tab_template { | ||
| pane size=2 borderless=true { | ||
| plugin location="https://github.com/dj95/zjstatus/releases/latest/download/zjstatus.wasm" { |
There was a problem hiding this comment.
The plugin is loaded directly from a mutable releases/latest URL on GitHub, meaning unpinned third-party WASM code is automatically fetched and executed in your terminal session. If the GitHub account, release, or delivery path is compromised, an attacker can ship a new zjstatus.wasm and gain code execution with your user privileges. To reduce this supply-chain risk, vendor the plugin locally or pin it to a specific immutable version or checksum instead of using releases/latest.
| children | ||
|
|
||
| pane size=2 borderless=true { | ||
| plugin location="https://github.com/dj95/zjstatus/releases/latest/download/zjstatus.wasm" { |
There was a problem hiding this comment.
The second plugin instance is also loaded from a mutable releases/latest GitHub URL, again pulling unpinned third-party WASM code into your terminal session. A compromised release or account could silently swap in a malicious zjstatus.wasm and execute it with your user’s privileges. Prefer vendoring the binary or pinning to a specific immutable version or hash rather than using releases/latest.
| LaunchOrFocusPlugin "https://github.com/liam-mackie/zsm/releases/latest/download/zsm.wasm" { | ||
| floating true | ||
| move_to_focused_tab true | ||
| } |
There was a problem hiding this comment.
The LaunchOrFocusPlugin call references a WASM plugin via a mutable releases/latest GitHub URL, so each use may download and execute unpinned third-party code. If that release is hijacked, pressing z would transparently run attacker-controlled code with your local user privileges. To mitigate, vendor the plugin or pin it to a specific version or checksum instead of releases/latest.
There was a problem hiding this comment.
Will address all of these in a separate PR
Summary
Major overhaul of the zellij terminal multiplexer configuration to bring it closer to the existing tmux setup quality and aesthetics.
zjstatus Status Bar Redesign
┈) between status bars and content area using zjstatus border featureCustom Theme
catppuccin-mocha-subtletheme using the new component-based theme specframe_unselected(surface0),frame_selected(surface2),frame_highlight(surface1)Autolock Improvements
Ctrl+gtoggles both lock mode AND autolock on/off simultaneouslyContainer Integration
Ctrl+o e)container-fzfscript, tmux split/status scripts, zellij floating layoutOther
zj→zellij