Skip to content

fix(core): make worktrees read the project id from local workspace#16795

Open
jlongster wants to merge 3 commits intodevfrom
jlongster/worktree-project
Open

fix(core): make worktrees read the project id from local workspace#16795
jlongster wants to merge 3 commits intodevfrom
jlongster/worktree-project

Conversation

@jlongster
Copy link
Contributor

@jlongster jlongster commented Mar 9, 2026

Worktrees currently have a problem where the project id generated for them is always new. This registers them in the db as an entirely new project which is wrong: worktrees should be a workspaces that all connect back to the same project.

This is why things don't work as you expect with worktrees currently: when listing sessions for a project you don't get all the sessions across worktrees by default, you only get sessions for the local workspace. This PR will make anything like that work because those routes are scoped by project, and now worktrees will not create new projects. Everything will be related to a single project.

In a git worktree, .git exists but it's just a file that points to the internal git registry for that workspace inside the real .git directory. We can't cache the id in there. Instead, we need to resolve the worktree and if we still don't have an id yet we then try to read the cached id from the main dir where .git is a real directory

Note that we use git rev-list --max-parents=0 --all to derive the "root" commit. So the way it worked before might have worked in some cases (the cached id file doesn't exist, so it always goes through that path to get the id). If all cases returned the same output and derived the same id, it would have worked. but that's not realiable: rev-list that return multiple roots, and these can change over time, so it's really important that we cache it and always reuse whatever we generated first.

}
}

const worktree = await git(["rev-parse", "--git-common-dir"], {
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you look below, all I did was move this up. There shouldn't be much difference in the order of execution. Only difference will be what happens when these commands file: now we might not have an id, but that's ok. now it'll just fallback to global which is fine

// same project id as the common dir, so we resolve it now
if (id == null) {
id = await readCachedId(path.join(worktree, ".git"))
}
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is the main block of code I added

@jlongster jlongster added the beta label Mar 9, 2026
opencode-agent bot added a commit that referenced this pull request Mar 9, 2026
opencode-agent bot added a commit that referenced this pull request Mar 9, 2026
opencode-agent bot added a commit that referenced this pull request Mar 9, 2026
opencode-agent bot added a commit that referenced this pull request Mar 9, 2026
opencode-agent bot added a commit that referenced this pull request Mar 10, 2026
opencode-agent bot added a commit that referenced this pull request Mar 10, 2026
opencode-agent bot added a commit that referenced this pull request Mar 10, 2026
opencode-agent bot added a commit that referenced this pull request Mar 10, 2026
opencode-agent bot added a commit that referenced this pull request Mar 10, 2026
opencode-agent bot added a commit that referenced this pull request Mar 10, 2026
opencode-agent bot added a commit that referenced this pull request Mar 10, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant