Skip to content

tui: /cd uses client home for ~ expansion and directory autocomplete when connected to a remote server #59554

Open

Description

@FossenWang

Summary

When the TUI connects to a remote server (opencode --server ...), /cd resolves ~ against the client's home directory and the /cd directory autocomplete lists the client's home, even though the working directory and filesystem belong to the server. Typing /cd ~/projects/foo from the home screen on a Windows client connected to a Linux server fails with "Directory does not exist".

Environment

  • opencode version: 2.1.4 (client and server)
  • OS: client Windows 10.0.19045 (win32 x64); server Linux (Ubuntu 24.04 container, HOME=/home/opencode)
  • Terminal: vscode (TERM=xterm-256color, TERM_PROGRAM=vscode, COLORTERM=truecolor)
  • Shell: C:\WINDOWS\system32\cmd.exe (client); bash in the container
  • Install/channel: latest (npm @opencode/cli on the client; /opt/opencode/opencode in the container)
  • Active plugins: title-local (local plugin in the client config); none on the server

Reproduction

  1. Start a server on a Linux host/container whose home is /home/opencode, and create /home/opencode/projects/foo.
  2. From the Windows client, connect with opencode --server http://<host>:4096 (server password supplied via OPENCODE_PASSWORD).
  3. On the home screen (no session yet), type /cd ~/projects/foo and press Enter.
  4. Alternatively type /cd ~/proj and wait for autocomplete.

Expected Behavior

  • ~ should refer to the server's home when the session/working directory is server-side, so /cd ~/projects/foo moves to /home/opencode/projects/foo.
  • The /cd directory autocomplete should list server directories and offer ~/... completions that the server can resolve.

Actual Behavior

  • Step 3: the working directory does not change; the TUI shows Failed to change directory with a server-side "Directory does not exist" error for a path like C:\Users\<user>\projects\foo.
  • Step 4: autocomplete reports that it could not search directories (it asks the server to list C:\Users\<user>, which does not exist there).
  • Using a server-side absolute path works: /cd /home/opencode/projects/foo.
  • Inside an existing session, manually typing /cd ~/projects/foo usually works (that branch sends the raw argument to the server, which expands ~ itself), but autocomplete still fails.

Additional Context

Root cause is client-side path handling in packages/tui/src/component/prompt/index.tsx (session.cd command):

const expanded =
  value === "~" ? paths.home : value.startsWith("~/") ? path.join(paths.home, value.slice(2)) : value
const directory = path.resolve(session?.location.directory ?? ..., expanded)

if (!sessionID) {
  // sends the client-computed absolute path to the server
  const location = await client.api.location.get({ location: { directory } })
  ...
} else {
  // sends the raw input, so the server expands "~" in its own home
  await client.api.session.move({ sessionID, directory: input })
}

paths.home comes from TuiPathsProvider in packages/tui/src/app.tsx, whose home is Global.home = process.env.OPENCODE_TEST_HOME ?? os.homedir() (packages/util/src/global.ts) — i.e. the client process's home. Directory autocomplete has the same problem: directoryAutocomplete() receives paths.home and calls file.list({ location, path: search.directory }) with a client path. The initial location resolution in app.tsx already falls back from the client cwd to the server default via api.location.get(), so the client/server split is known there but not used by /cd.

Possible directions:

  • Resolve and expand the /cd argument on the server (send the raw argument for the home-screen case too, or add a server-side "resolve location" endpoint), so ~ always means the server's home.
  • Or expose the server's home in the TUI runtime (e.g. via /api/info) and use it for ~ expansion and directory autocomplete when connected to a remote server.

Workaround for users: use server-side absolute paths, or paths relative to the current/session directory (on the home screen the default is the server's launch directory, e.g. /home/opencode).

Activity

  1. opencode-agent commented on Oct 27, 2026

    @opencode-agent
    Contributor

    Thanks for the detailed write-up and root-cause analysis! I think this is a duplicate of #55171, which reports the same problem: when the TUI is attached with --server, /cd ~ and ~/... directory autocomplete use the client's home instead of the server's.

    Possible duplicates and related items, ordered from most to least likely:

    Until then, your workaround (server-side absolute paths, or paths relative to the current directory) should keep working.

    The bot will close this issue as a duplicate in 1 day unless you reply explaining how your problem is different.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions