fix: support Docker-backed Hermes installs in SSH mode#435
Conversation
There was a problem hiding this comment.
Thanks for jumping on #432. I agree with the direction: the data-home discovery plus Docker exec fallback addresses the core “chat works but Desktop reads the wrong filesystem / cannot find the CLI” report. I also checked this against the staged plan I had for the issue and against the earlier WSL/Docker probe I ran: for a single official nousresearch/hermes-agent container with /opt/data mounted to the host, the new discovery path is the right shape and the generated Docker CLI command worked in that live probe.
Requesting changes for a couple of blocking gaps before this lands:
-
tests/ssh-remote.test.ts:120now unconditionally executesbash. On a clean Windows dev environment this focused suite fails withError: spawnSync bash ENOENT:npm test -- --run tests/ssh-remote.test.ts FAIL tests/ssh-remote.test.ts > buildRemoteHermesCmd venv probe > quotes the remote bash script safely... Error: spawnSync bash ENOENTThis should either skip the execution assertion when bash is unavailable, resolve a known Git Bash path on Windows, or rewrite the test so the Windows test suite does not require a POSIX shell on PATH.
-
Docker-backed gateway lifecycle is still routed through the host install path.
buildGatewayStartCommand,buildGatewayStopCommand, andbuildGatewayStatusCommandstill use barehermes gateway ...and$HOME/.hermes/gateway.pid/$HOME/.hermes/gateway.loginstead of the resolved Hermes home and/orbuildRemoteHermesCmd. In the Docker/Coolify case this means the Gateway page can report stopped even while the container gateway is running, and Start/Stop targets a nonexistent host CLI or the wrong host data directory. This was the main remaining surface in my staged plan: either route these controls through the detected Docker CLI/home, or explicitly treat Docker/Coolify gateways as externally managed so Desktop does not show misleading controls.
One related design risk: dockerHermesContainerProbe() picks the first running nousresearch/hermes-agent container, and the home cache key only uses SSH host/user/port/key. If a Coolify host has more than one Hermes container, Desktop may tunnel chat to one configured remotePort but read/write config/sessions via another container’s mount. That may be acceptable as a follow-up if this PR is deliberately “single official container only”, but it should at least be documented or made explicit with a container override/selection path.
Validation run locally:
npm test -- --run tests/ssh-remote.test.tsfails on Windows as above.npm run typecheckpasses.npm run buildpasses.
|
Small clarification on my review: I am not asking for the implementation to follow my earlier staged plan specifically. Any shape is fine if the Docker-backed SSH mode works reliably. The two concrete blockers I meant are behavior-level issues:
The “first matching container” point is more of a design caveat/follow-up unless it causes common Coolify multi-container setups to read/write the wrong container’s data. |
88f2d60 to
7fe6561
Compare
|
@pmos69 thanks for the review! Lack of windows compatibility – my mistake, thanks for noticing. As for multiple containers, I've decided that for end-user it would me more valuable if solution won't be half-assed and we'd be able to detect multiple containers and let the user pick. So I updated the patch to avoid first-container selection by adding an explicit SSH Docker target selector in Settings/Welcome, and the selected container is now threaded through CLI, home resolution, cache keys, and and gateway start/stop/status. I also made the bash/python execution test skip when those tools are unavailable, while keeping portable assertions. Validated with targeted SSH/config/preload/ipc tests, 'npm run typecheck', targeted ESLint on touched files, 'nom run build' and git diff -check. And of course local build and verification on my remote container setup. |
|
Live-tested the updated branch against a WSL SSH host with a Docker-style Hermes setup, including multi-container selection and gateway lifecycle routing through the selected container. Everything behaved as expected. One small remaining change before merge: the focused SSH suite still has one Windows-local failure because After that I’m comfortable with this PR. |
7fe6561 to
b7bbcc6
Compare
|
Thanks, this now addresses the main behavior-level concerns I had: Docker-backed gateway start/stop/status is routed through the selected Docker target/resolved Hermes home, and the Settings/Welcome flow now has explicit target inspection/selection instead of blindly using the first matching container. One requested change is still not fully met: the focused SSH suite still fails on Windows. I reran: npm test -- --run tests/ssh-remote.test.ts tests/connection-config-security.test.tsCurrent result:
Suggested implementation:
The portable string-assertion tests are fine; the remaining issue is just that the execution tests still assume a POSIX-compatible path model after we intentionally override |
|
Hi — hitting this exact issue with a PR #435 looks like it addresses this directly. Is there anything blocking a merge — conflicts to resolve, a review pass still needed, or is it in the queue? Would be happy to test against a Docker install if that would help move things forward. |
Fixes #432
Problem
SSH mode assumes Hermes is installed directly on the remote host:
hermesCLI is on PATH or in known host venv paths~/.hermesDocker-backed Hermes Agent installs keep the CLI inside the container and persist data through the container
/opt/datamount. In that setup, SSH doctor/version commands can fail, while sessions, config, env, logs, models, and profiles appear empty because desktop SSH helpers read the wrong host paths.Root cause
src/main/ssh-remote.tshardcoded host install assumptions in two places:hermes~/.hermespaths directlyThat misses official Docker image deployments where the working CLI is inside the container and the real Hermes home is the host mount backing
/opt/data.Fix
nousresearch/hermes-agentcontainer/opt/datamount back to its host pathdocker exec.docs/SSH-TUNNEL-VPS.md.Validation
npm test -- --run tests/ssh-remote.test.ts tests/ssh-remote-paths.test.tsnpm run typechecknpm testnpx eslint src/main/ssh-remote.ts tests/ssh-remote.test.ts --quietnpm run build:unpackHERMES_HOMEand SSH config; the app-created SSH tunnel reached the remote Hermes/healthendpoint.Note: full
npm run lint -- --quietstill reports unrelated existing lint errors underscripts/*.js. The files touched by this PR pass ESLint directly.