fix: correct main repo root detection for submodules (#849)

This commit is contained in:
Gero Hillebrandt
2026-01-02 21:39:21 +01:00
committed by GitHub
parent ad44b32835
commit f48ecce2b7
2 changed files with 56 additions and 3 deletions

View File

@@ -149,8 +149,13 @@ func GetMainRepoRoot() (string, error) {
if err != nil {
return "", err
}
// The main repo root is the parent of the .git directory (commonDir)
return filepath.Dir(ctx.commonDir), nil
if ctx.isWorktree {
// For worktrees, the main repo root is the parent of the shared .git directory.
return filepath.Dir(ctx.commonDir), nil
}
// For regular repos (including submodules), repoRoot is the correct root.
return ctx.repoRoot, nil
}
// GetRepoRoot returns the root directory of the current git repository.
@@ -196,4 +201,4 @@ func NormalizePath(path string) string {
func ResetCaches() {
gitCtxOnce = sync.Once{}
gitCtx = gitContext{}
}
}

View File

@@ -894,6 +894,54 @@ func TestGetMainRepoRoot(t *testing.T) {
}
})
t.Run("returns correct root for submodule repo", func(t *testing.T) {
ResetCaches() // Reset caches from previous subtests
superRepoPath, superCleanup := setupTestRepo(t)
defer superCleanup()
submoduleRepoPath, submoduleCleanup := setupTestRepo(t)
defer submoduleCleanup()
addCmd := exec.Command("git", "-c", "protocol.file.allow=always", "submodule", "add", submoduleRepoPath, "core")
addCmd.Dir = superRepoPath
if output, err := addCmd.CombinedOutput(); err != nil {
t.Fatalf("Failed to add submodule: %v\nOutput: %s", err, string(output))
}
commitCmd := exec.Command("git", "commit", "-m", "Add submodule")
commitCmd.Dir = superRepoPath
if output, err := commitCmd.CombinedOutput(); err != nil {
t.Fatalf("Failed to commit submodule: %v\nOutput: %s", err, string(output))
}
submodulePath := filepath.Join(superRepoPath, "core")
// Save current dir and change to submodule
originalDir, err := os.Getwd()
if err != nil {
t.Fatalf("Failed to get current dir: %v", err)
}
defer func() { _ = os.Chdir(originalDir) }()
if err := os.Chdir(submodulePath); err != nil {
t.Fatalf("Failed to chdir to submodule: %v", err)
}
ResetCaches() // Reset after chdir
root, err := GetMainRepoRoot()
if err != nil {
t.Fatalf("GetMainRepoRoot failed: %v", err)
}
// Resolve symlinks for comparison (e.g., /tmp -> /private/tmp on macOS)
expectedRoot, _ := filepath.EvalSymlinks(submodulePath)
actualRoot, _ := filepath.EvalSymlinks(root)
if actualRoot != expectedRoot {
t.Errorf("GetMainRepoRoot() = %s, want %s (submodule repo)", actualRoot, expectedRoot)
}
})
t.Run("returns main repo root from worktree", func(t *testing.T) {
ResetCaches() // Reset caches from previous subtests
repoPath, cleanup := setupTestRepo(t)