-
Notifications
You must be signed in to change notification settings - Fork 13.4k
Description
Bug Description
When working with multiple sub-folders of the same git repository as separate sidebar entries, renaming one project renames all of them. Conversely, if you rename one back, the other gets renamed to the previous name.
Reproduction Steps
- Open a project at its git root, e.g.
~/repos/my-project— name it "My Project" - Open a sub-folder of the same repo, e.g.
~/repos/my-project/apps/service-a— it inherits "My Project" - Rename the sub-folder entry to "Service A"
- Observe: "My Project" (root) is now also named "Service A"
- Rename it back to "My Project"
- Observe: "Service A" (sub-folder) is now also named "My Project"
Root Cause
OpenCode identifies projects by their git root commit hash (not by the working directory path). All worktrees within the same git repository share a single project.name row in the SQLite DB.
The enrich() function in packages/app/src/context/layout.tsx has a two-tier name resolution system, but the per-workspace tier is only applied to non-git projects (projectID === "global"):
const isGlobal = projectID === "global" || (metadata?.id === undefined && localOverride)
if (!isGlobal) return base // ← git projects exit here
// local?.name from workspace .dat is IGNORED
return { // ← only non-git projects reach this
...base,
name: local?.name, // per-workspace name from workspace:project .dat key
}The infrastructure for per-workspace names already exists — workspace:project in per-workspace .dat files stores ProjectMeta including a name field. This is used correctly for non-git projects (added in bcf7a65e). The fix is to apply the same logic to git projects when a local workspace name is set.
Proposed Fix
packages/app/src/context/layout.tsx — extend enrich() to check local name for git projects:
// Check workspace-level name override even for git projects
if (!isGlobal) {
if (local?.name !== undefined) {
return { ...base, name: local.name }
}
return base
}packages/app/src/components/dialog-edit-project.tsx — route rename to workspace storage when in a sub-folder:
const isSubfolder = props.project.directory !== props.project.worktree
if (isSubfolder) {
// Sub-folder: write to per-workspace .dat only (does not affect root or other sub-folders)
globalSync.project.meta(props.project.directory, { name, icon, commands })
} else {
// Git root: update server DB (global rename — existing behavior)
await globalSDK.client.project.update({ projectID: props.project.id, ... })
}Expected Behavior
- Renaming a project at the git root directory → renames globally across all worktrees (existing behavior)
- Renaming a project while working in a sub-folder → renames that sidebar entry only (per-workspace)
Additional Context
- Version: 1.2.27
- The
workspace:projectper-workspace storage already exists and is used correctly for non-git projects sincebcf7a65e(Jan 23, 2026) - The issue only manifests once a custom name is set — before that,
displayName()falls back togetFilename(worktree)which is per-path and works correctly - Sub-folder sessions already correctly use their specific
directoryas CWD — only the display name is broken