import { afterEach, beforeEach, describe, expect, it } from "bun:test"; import * as fs from "node:fs/promises"; import * as os from "node:os"; import * as path from "node:path"; import { setKeybindings } from "@oh-my-pi/pi-tui"; import { YAML } from "bun"; import { KeybindingsManager } from "../src/config/keybindings"; describe("KeybindingsManager.create", () => { beforeEach(() => { setKeybindings(KeybindingsManager.inMemory()); }); afterEach(() => { setKeybindings(KeybindingsManager.inMemory()); }); it("migrates legacy keybinding JSON to YAML during create", async () => { const agentDir = await fs.mkdtemp(path.join(os.tmpdir(), "pi-keybindings-")); const jsonPath = path.join(agentDir, "keybindings.json"); const ymlPath = path.join(agentDir, "keybindings.yml"); await Bun.write( jsonPath, `${JSON.stringify( { fork: "ctrl+f", selectConfirm: "enter", cursorUp: "ctrl+p", selectModelTemporary: "alt+y", }, null, 2, )}\n`, ); try { const manager = KeybindingsManager.create(agentDir); const writtenConfig = YAML.parse(await Bun.file(ymlPath).text()); expect(manager.getKeys("app.session.fork")).toEqual(["ctrl+f"]); expect(manager.getKeys("tui.select.confirm")).toEqual(["enter"]); expect(manager.getKeys("tui.editor.cursorUp")).toEqual(["ctrl+p"]); expect(manager.getKeys("app.model.selectTemporary")).toEqual(["alt+y"]); expect(writtenConfig).toEqual({ "app.model.selectTemporary": "alt+y", "app.session.fork": "ctrl+f", "tui.editor.cursorUp": "ctrl+p", "tui.select.confirm": "enter", }); expect(writtenConfig).not.toHaveProperty("selectModelTemporary"); expect(await Bun.file(jsonPath).exists()).toBe(true); } finally { await fs.rm(agentDir, { recursive: true, force: true }); } }); it("loads keybindings.yml directly", async () => { const agentDir = await fs.mkdtemp(path.join(os.tmpdir(), "pi-keybindings-")); const configPath = path.join(agentDir, "keybindings.yml"); await Bun.write( configPath, YAML.stringify( { "app.session.fork": "ctrl+f", "app.clipboard.copyPrompt": ["alt+c", "ctrl+shift+c"], }, null, 2, ), ); try { const manager = KeybindingsManager.create(agentDir); expect(manager.getKeys("app.session.fork")).toEqual(["ctrl+f"]); expect(manager.getKeys("app.clipboard.copyPrompt")).toEqual(["alt+c", "ctrl+shift+c"]); } finally { await fs.rm(agentDir, { recursive: true, force: true }); } }); it("accepts keybindings.yaml when present", async () => { const agentDir = await fs.mkdtemp(path.join(os.tmpdir(), "pi-keybindings-")); const yamlPath = path.join(agentDir, "keybindings.yaml"); const canonicalPath = path.join(agentDir, "keybindings.yml"); await Bun.write( yamlPath, YAML.stringify( { "app.plan.toggle": "alt+shift+p", }, null, 2, ), ); try { const manager = KeybindingsManager.create(agentDir); expect(manager.getKeys("app.plan.toggle")).toEqual(["alt+shift+p"]); expect(await Bun.file(canonicalPath).exists()).toBe(false); } finally { await fs.rm(agentDir, { recursive: true, force: true }); } }); });