diff --git a/packages/opencode/src/commit-message/git-context.ts b/packages/opencode/src/commit-message/git-context.ts index 3b97f44c58..d81e8a62cf 100644 --- a/packages/opencode/src/commit-message/git-context.ts +++ b/packages/opencode/src/commit-message/git-context.ts @@ -133,6 +133,7 @@ function git(args: string[], cwd: string): string { cwd, stdout: "pipe", stderr: "pipe", + windowsHide: true, // kilocode_change - prevent cmd.exe flash on Windows }) return result.stdout.toString().trimEnd() } @@ -144,7 +145,7 @@ function parseNameStatus(output: string): Array<{ status: string; path: string } let path: string if (status!.startsWith("R")) { // Rename: rest = ["old.ts", "new.ts"], use the new path - path = rest[1] ?? rest[0] + path = rest[1] ?? rest[0] ?? "" } else { path = rest.join("\t") } diff --git a/packages/opencode/test/kilocode/commit-message-windows.test.ts b/packages/opencode/test/kilocode/commit-message-windows.test.ts new file mode 100644 index 0000000000..4be42d980e --- /dev/null +++ b/packages/opencode/test/kilocode/commit-message-windows.test.ts @@ -0,0 +1,38 @@ +import { describe, expect, spyOn, test } from "bun:test" +import { getGitContext } from "../../src/commit-message/git-context" + +describe("commit-message git context", () => { + test("hides Windows console windows for git subprocesses", async () => { + const out = new Map([ + ["branch --show-current", "main"], + ["log --oneline -5", "abc1234 init"], + ["diff --name-status --cached", "M\tsrc/index.ts"], + ["diff --cached -- src/index.ts", "+console.log('hi')"], + ]) + + const spy = spyOn(Bun, "spawnSync").mockImplementation(((cmd: unknown, opts: unknown) => { + const key = Array.isArray(cmd) ? cmd.slice(1).join(" ") : "" + return { + stdout: Buffer.from(out.get(key) ?? ""), + stderr: Buffer.alloc(0), + } as never + }) as unknown as typeof Bun.spawnSync) + + try { + await getGitContext("/repo") + + expect(spy).toHaveBeenCalledTimes(4) + for (const call of spy.mock.calls) { + expect(call[0]).toEqual(expect.arrayContaining(["git"])) + expect(call[1]).toMatchObject({ + cwd: "/repo", + stdout: "pipe", + stderr: "pipe", + windowsHide: true, + }) + } + } finally { + spy.mockRestore() + } + }) +})