package project import ( "os" "path/filepath" "testing" ) func TestDiscoverFindsRepositoryRootFromNestedDirectory(t *testing.T) { root := writeProjectRoot(t, false) nested := filepath.Join(root, "tools", "tht", "internal") if err := os.MkdirAll(nested, 0o755); err != nil { t.Fatal(err) } got, err := Discover(nested) if err != nil { t.Fatal(err) } want := resolvedPath(t, root) if got.Path != want { t.Fatalf("Discover() root = %q, want %q", got.Path, want) } if got.IsWorktree { t.Fatal("Discover() marked a main checkout as a worktree") } } func TestDiscoverRecognizesLinkedGitWorktree(t *testing.T) { root := writeProjectRoot(t, true) got, err := Discover(root) if err != nil { t.Fatal(err) } want := resolvedPath(t, root) if got.Path != want { t.Fatalf("Discover() root = %q, want %q", got.Path, want) } if !got.IsWorktree { t.Fatal("Discover() did not mark a linked checkout as a worktree") } } func TestDiscoverResolvesSymlinkForRootIdentity(t *testing.T) { root := writeProjectRoot(t, false) alias := filepath.Join(t.TempDir(), "checkout") if err := os.Symlink(root, alias); err != nil { t.Fatal(err) } got, err := Discover(filepath.Join(alias, "frontend")) if err != nil { t.Fatal(err) } want := resolvedPath(t, root) if got.Path != want { t.Fatalf("Discover() root = %q, want canonical %q", got.Path, want) } } func TestDiscoverRejectsDirectoriesThatAreNotThothIIProjects(t *testing.T) { _, err := Discover(t.TempDir()) if err == nil { t.Fatal("Discover() error = nil, want root discovery failure") } } func writeProjectRoot(t *testing.T, linkedWorktree bool) string { t.Helper() root := t.TempDir() for _, directory := range []string{"backend", "frontend", "harness", "tools", "deploy"} { if err := os.MkdirAll(filepath.Join(root, directory), 0o755); err != nil { t.Fatal(err) } } if err := os.WriteFile(filepath.Join(root, "compose.yaml"), []byte("services: {}\n"), 0o600); err != nil { t.Fatal(err) } gitPath := filepath.Join(root, ".git") if linkedWorktree { if err := os.WriteFile(gitPath, []byte("gitdir: /tmp/thothii-worktree.git\n"), 0o600); err != nil { t.Fatal(err) } return root } if err := os.Mkdir(gitPath, 0o755); err != nil { t.Fatal(err) } return root } func resolvedPath(t *testing.T, path string) string { t.Helper() resolved, err := filepath.EvalSymlinks(path) if err != nil { t.Fatal(err) } return resolved }