Files
openchamber/packages/ui/src/lib/gitApi.test.ts
T
Paolo InsognaandBohdan Triapitsyn e16097b05d feat: Redesign git changes to split stage/unstaged files. (#1359)
* feat: Redesign git changes to split stage/unstaged files.

Signed-off-by: Paolo Insogna <paolo@cowtech.it>

* fixup

Signed-off-by: Paolo Insogna <paolo@cowtech.it>

* fixup

Signed-off-by: Paolo Insogna <paolo@cowtech.it>

* refactor: streamline git changes panel

* fix: label staged and working diff tabs

* fix: isolate staged and working diff files

* fix: scope staged and working diff updates

* fix: scope git row revert to working changes

---------

Signed-off-by: Paolo Insogna <paolo@cowtech.it>
Co-authored-by: Bohdan Triapitsyn <artmore@protonmail.com>
2026-05-24 00:49:38 +03:00

113 lines
3.5 KiB
TypeScript

import { describe, expect, test } from "bun:test"
import type { GitAPI, GitStatus } from "./api/types"
import { getGitStatus, stageGitFile, stageGitFiles, unstageGitFile, unstageGitFiles } from "./gitApi"
const status: GitStatus = {
current: "main",
tracking: null,
ahead: 0,
behind: 0,
files: [],
isClean: true,
}
const withRuntimeGit = async (git: GitAPI, callback: () => Promise<void>) => {
const previousWindowDescriptor = Object.getOwnPropertyDescriptor(globalThis, "window")
Object.defineProperty(globalThis, "window", {
configurable: true,
value: {
__OPENCHAMBER_RUNTIME_APIS__: { git },
},
})
try {
await callback()
} finally {
if (previousWindowDescriptor) {
Object.defineProperty(globalThis, "window", previousWindowDescriptor)
} else {
delete (globalThis as { window?: Window }).window
}
}
}
describe("getGitStatus", () => {
test("forwards light-mode options to runtime git APIs", async () => {
let received: { directory: string; options?: { mode?: "light" } } | null = null
const runtimeGit = {
getGitStatus: async (directory: string, options?: { mode?: "light" }) => {
received = { directory, options }
return status
},
} as Partial<GitAPI> as GitAPI
await withRuntimeGit(runtimeGit, async () => {
await getGitStatus("/repo", { mode: "light" })
})
expect(received).toEqual({ directory: "/repo", options: { mode: "light" } })
})
})
describe("git index mutations", () => {
test("forwards bulk stage requests to runtime git APIs", async () => {
let received: { directory: string; paths: string[] } | null = null
const runtimeGit = {
stageGitFiles: async (directory: string, paths: string[]) => {
received = { directory, paths }
},
} as Partial<GitAPI> as GitAPI
await withRuntimeGit(runtimeGit, async () => {
await stageGitFiles("/repo", ["a.ts", "b.ts"])
})
expect(received).toEqual({ directory: "/repo", paths: ["a.ts", "b.ts"] })
})
test("forwards bulk unstage requests to runtime git APIs", async () => {
let received: { directory: string; paths: string[] } | null = null
const runtimeGit = {
unstageGitFiles: async (directory: string, paths: string[]) => {
received = { directory, paths }
},
} as Partial<GitAPI> as GitAPI
await withRuntimeGit(runtimeGit, async () => {
await unstageGitFiles("/repo", ["a.ts", "b.ts"])
})
expect(received).toEqual({ directory: "/repo", paths: ["a.ts", "b.ts"] })
})
test("keeps single-file stage wrapper routed to runtime single-file API", async () => {
let received: { directory: string; path: string } | null = null
const runtimeGit = {
stageGitFile: async (directory: string, path: string) => {
received = { directory, path }
},
} as Partial<GitAPI> as GitAPI
await withRuntimeGit(runtimeGit, async () => {
await stageGitFile("/repo", "a.ts")
})
expect(received).toEqual({ directory: "/repo", path: "a.ts" })
})
test("keeps single-file unstage wrapper routed to runtime single-file API", async () => {
let received: { directory: string; path: string } | null = null
const runtimeGit = {
unstageGitFile: async (directory: string, path: string) => {
received = { directory, path }
},
} as Partial<GitAPI> as GitAPI
await withRuntimeGit(runtimeGit, async () => {
await unstageGitFile("/repo", "a.ts")
})
expect(received).toEqual({ directory: "/repo", path: "a.ts" })
})
})