Omahub
← All plugins
P

Hop

by Parminder Klair

Keep your SSH machines in the bar. Pick one and it opens in your default Omarchy terminal, runs the startup script you gave it, and leaves you in an interactive shell.

Security review

No obvious issues detected

Deterministic scan — not a security guarantee

None
Risk level
None
Analyzed commit
61f5874
Scanned
1 month ago

No potentially dangerous behavior detected in the analyzed commit.

Automated analysis only — not a security guarantee.

AI advisory review

No obvious issues detected

Language-model assessment · ~deepseek/deepseek-v4-flash-latest — advisory only

Low
AI risk level
Low
Recommendation
install
Model
~deepseek/deepseek-v4-flash-latest
Analyzed commit
61f5874
Reviewed
1 month ago

The Hop plugin is a well-engineered SSH launcher that stores only host metadata, never credentials, and builds ssh commands with careful input validation and quoting to prevent option injection. The store reader is hardened against symlink/FIFO attacks and size caps, and the QML renders store data as plain text. No malicious or destructive behavior was found; the only risk is the inherent one of running ssh to user-configured machines, which is the plugin's stated purpose.

  • The plugin executes user-provided startup scripts on remote machines, which is expected but could be misused if a machine entry is tampered with by another local process; however, the store is user-owned and the plugin does not elevate privileges.
  • The plugin relies on the user's ssh configuration and keys; if a machine entry is maliciously edited to point to a hostile host, the user could be prompted for credentials, but that is standard ssh behavior.
How this check works

This review combines the deterministic scan (the rule-based results above) with an independent look at the plugin's code by a language model. The model reads a trimmed sample of the repository's files, the manifest, and the README, then gives a plain-language risk level and a recommendation: install (no notable danger), review (look closer first), or avoid (clearly dangerous).

It runs on the same analyzed commit as the deterministic scan and is strictly advisory — it is not a security guarantee and never blocks a plugin by itself. A human moderator still reviews plugins before they are listed.

AI advisory only — automated analysis, not a security guarantee.

Install
$ omarchy plugin add https://github.com/perminder-klair/omarchy-hop --enable
System #bar #quickshell #system

Hop

Your SSH machines, in the Omarchy bar. Pick one and it opens in your default terminal, runs the startup script you gave it, and leaves you at a prompt.

The machine list and the edit form

What it does

  • A bar icon listing every machine you have saved.
  • Click one and ssh runs in the terminal xdg-terminal-exec would pick — the same one every other Omarchy launcher uses.
  • Sessions can keep running on the machine. Turn on Keep the session running and the session lives in a tmux session named after the machine: close the window, lose wifi, reboot your laptop, and opening the machine again puts you back in front of the same work rather than starting over. Needs tmux on the remote side; without it you get an ordinary session.
  • Sessions outlive the bar. The window is handed to systemd rather than kept as a child of the shell process, so restarting the shell, updating Omarchy, or opening a second machine leaves the sessions you already have alone.
  • Each machine can carry a startup script: a shell snippet that runs the moment you arrive (cd /srv/app && docker compose ps, tmux attach, whatever). When it finishes you are dropped into a normal login shell rather than disconnected.
  • Adding, editing and removing machines happens in the panel, or from the hop CLI, or by editing one JSON file.

What it deliberately does not do

It never stores a password. The terminal it opens gets a real tty, so ssh prompts you there exactly as it would if you had typed the command yourself. That keeps keys, agents, ProxyJump, Match blocks and everything else in ~/.ssh/config working, and it means this plugin has no secret to leak — the machine list is just hostnames.

If you want passwordless logins, the answer is ssh-copy-id, not a plugin holding your password inside a long-lived desktop process.

Requirements

Everything here ships with Omarchy; the list is for completeness.

openssh The sessions.
jq The CLI reads and writes the store with it.
python Safely opens, validates and size-caps the store before parsing.
nautilus + gvfs Only for the Files button. Without them the rest still works.

Install

omarchy plugin add https://github.com/perminder-klair/omarchy-hop.git --enable

Omarchy clones it to ~/.config/omarchy/plugins/co.klair.hop/ and asks before enabling it, so you can read the code first. Updating is a fast-forward pull:

omarchy plugin update co.klair.hop

Removing it

omarchy plugin remove co.klair.hop

That disables the plugin and deletes the checkout. Nothing else is touched — no system files, no units, no ~/.ssh. Your machine list survives in ~/.config/hop/hosts.json, so reinstalling picks up where you left off; delete that directory too if you want it gone.

Hacking on it instead of just using it? See CONTRIBUTING.md.

Using it

Click the 󰒋 icon in the bar. Add machine opens the form:

Field Notes
Name What the bar shows. Defaults to the host.
Host Hostname, IP, or a Host alias from ~/.ssh/config.
User Leave empty to let ssh_config decide.
Port 22 unless you say otherwise.
Identity file Optional -i. ~ is expanded.
Initial path Where sessions start: the terminal cds here, and Files opens here.
Startup script Runs on arrival, then hands you a login shell.
Forward ssh agent -A. Off by default — only turn it on for machines you trust.

In the list, each machine carries three buttons: the folder opens it in Files over SFTP, the pencil edits it, and the last one copies the exact ssh command to your clipboard.

Browsing a machine in Files

The folder button hands Nautilus an sftp:// URL, so browsing is gvfs's job, not a mount this plugin manages. It gets its own connection and its own auth prompt — you can browse a machine without a terminal session open, and closing one does not disturb the other. gvfs ships with Omarchy, so there is nothing to install.

gvfs does not expand ~ and cannot know what the remote home is, so with no initial path set Hop sends /home/<user> (or /root, or / when no user is configured). Set Initial path on any machine where that guess is wrong — a NAS, a BSD box, a container.

Startup scripts run in a login shell

ssh host "some-command" normally runs that command in a shell that is neither a login shell nor interactive, so nothing on the far side that builds PATH — /etc/profile, ~/.profile, ~/.bashrc, mise/asdf/nvm shims, ~/.local/bin — has run yet. Tools you use every day come back as command not found.

Hop runs your script through $SHELL -lc instead, so it sees the same environment an interactive login would, and the session you are handed afterwards inherits it. If something still is not found, it is genuinely missing from your login PATH on that machine — check with hop connect <name> and echo $PATH.

From the terminal

Everything the panel does goes through bin/hop, so it is all available without the bar:

hop list
hop add --host 10.0.0.5 --name "Prod web" --user deploy --init 'cd /srv/app'
hop set <id> --port 2222
hop set <id> --persist      # keep it running in tmux (--no-persist undoes it)
hop connect "Prod web"      # opens a terminal, same as clicking
hop files "Prod web"        # opens Files over SFTP
hop uri "Prod web"          # prints the sftp:// URL instead of opening it
hop command "Prod web"      # prints the ssh command instead of running it
hop rm "Prod web"

--init-file some-script.sh is there for startup scripts long enough that you would rather keep them in a file.

Keeping a session alive

--persist runs the session inside tmux new-session -A -D -s hop-<id> on the remote machine. The consequences worth knowing:

  • The session is named after the machine's id, not its name, so renaming a machine in the panel does not strand the session you are working in. Run tmux ls on the machine to see them.
  • The startup script runs when the session is created. Reattaching does not run it again, so whatever it launched is not started a second time.
  • Reattaching detaches any other client, which is what makes a window killed mid-session let go of it rather than hold it at its old size.
  • On a machine without tmux you get an ordinary session instead, rather than an error in a window that is about to close.

From a keybinding

The shell exposes an IPC target, so a machine is one hotkey away:

bindd = SUPER SHIFT, S, Prod web, exec, omarchy-shell hop connect "Prod web"
bindd = SUPER SHIFT, F, Prod web files, exec, omarchy-shell hop files "Prod web"

Window rules

Sessions launch with app-id org.omarchy.hop, so Hyprland can treat them differently from an ordinary terminal:

windowrule = workspace 4, class:^(org\.omarchy\.hop)$

Where things live

Path What
~/.config/hop/hosts.json The machine list. Plain JSON, safe to edit or sync.
bin/hop The CLI the panel drives.
bin/hop-read-store The bounded, descriptor-validated, field-checked store reader.

Everything the bar reads goes through bin/hop-read-store, which caps how many machines a store may hold and checks every field's type, length and range before the shell sees it. Hand-edit the file if you like — an entry that does not fit is dropped with a note on stderr rather than shown.

The store holds no secrets, but it is created 0600 inside a 0700 directory anyway — a list of which machines you have and who you log in as is not something to hand out either.

License

MIT.