diff --git a/packages/coding-agent/test/interactive-theme-scrollback.test.ts b/packages/coding-agent/test/interactive-theme-scrollback.test.ts index b7aaab2e2..087e7c666 100644 --- a/packages/coding-agent/test/interactive-theme-scrollback.test.ts +++ b/packages/coding-agent/test/interactive-theme-scrollback.test.ts @@ -21,7 +21,15 @@ import type { TerminalAppearance, TerminalAppearanceRequestToken } from "@oh-my- import { TempDir } from "@oh-my-pi/pi-utils"; import { VirtualTerminal } from "../../tui/test/virtual-terminal"; -const MULTIPLEXER_ENV_KEYS = ["TMUX", "STY", "ZELLIJ", "CMUX_WORKSPACE_ID", "CMUX_SURFACE_ID", "TERM"] as const; +const MULTIPLEXER_ENV_KEYS = [ + "TMUX", + "STY", + "ZELLIJ", + "HERDR_ENV", + "CMUX_WORKSPACE_ID", + "CMUX_SURFACE_ID", + "TERM", +] as const; class AppearanceVirtualTerminal extends VirtualTerminal { #appearance?: TerminalAppearance; diff --git a/packages/tui/test/component-render.test.ts b/packages/tui/test/component-render.test.ts index 8728b6dec..0d6fd6950 100644 --- a/packages/tui/test/component-render.test.ts +++ b/packages/tui/test/component-render.test.ts @@ -1,4 +1,4 @@ -import { describe, expect, it } from "bun:test"; +import { afterEach, beforeEach, describe, expect, it } from "bun:test"; import { type Component, Container, @@ -13,6 +13,17 @@ import { StressRenderScheduler } from "./render-stress-scheduler"; import { defaultEditorTheme } from "./test-themes"; import { VirtualTerminal } from "./virtual-terminal"; +const ORIGINAL_HERDR_ENV = Bun.env.HERDR_ENV; + +beforeEach(() => { + delete Bun.env.HERDR_ENV; +}); + +afterEach(() => { + if (ORIGINAL_HERDR_ENV === undefined) delete Bun.env.HERDR_ENV; + else Bun.env.HERDR_ENV = ORIGINAL_HERDR_ENV; +}); + // Behavioral tests for TUI.requestComponentRender: a component whose own // content changed (spinner frame, blink) asks for a component-scoped frame. // When every request since the last frame is component-scoped and the frame is diff --git a/packages/tui/test/image-budget.test.ts b/packages/tui/test/image-budget.test.ts index 033addb43..bd646bbe2 100644 --- a/packages/tui/test/image-budget.test.ts +++ b/packages/tui/test/image-budget.test.ts @@ -29,14 +29,18 @@ const BASE64_ONE_PIXEL_PNG = "iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAAAAAA6fptVAAAACklEQVR4nGNgAAAAAgABSK+kcQAAAABJRU5ErkJggg=="; const ORIGINAL_TMUX = Bun.env.TMUX; +const ORIGINAL_HERDR_ENV = Bun.env.HERDR_ENV; beforeEach(() => { delete Bun.env.TMUX; + delete Bun.env.HERDR_ENV; }); afterEach(() => { if (ORIGINAL_TMUX === undefined) delete Bun.env.TMUX; else Bun.env.TMUX = ORIGINAL_TMUX; + if (ORIGINAL_HERDR_ENV === undefined) delete Bun.env.HERDR_ENV; + else Bun.env.HERDR_ENV = ORIGINAL_HERDR_ENV; }); /** Drive one render pass against the budget with `count` images (ids 1..count, stable across passes). */ diff --git a/packages/tui/test/issue-2115-repro.test.ts b/packages/tui/test/issue-2115-repro.test.ts index b6672f4a9..c022e7ed8 100644 --- a/packages/tui/test/issue-2115-repro.test.ts +++ b/packages/tui/test/issue-2115-repro.test.ts @@ -1,4 +1,4 @@ -import { afterEach, describe, expect, it, vi } from "bun:test"; +import { afterEach, beforeEach, describe, expect, it, vi } from "bun:test"; import { type Component, type RenderScheduler, type RenderTimer, TUI } from "@oh-my-pi/pi-tui"; import { VirtualTerminal } from "./virtual-terminal"; @@ -13,6 +13,7 @@ import { VirtualTerminal } from "./virtual-terminal"; // replay crossed ~1-2 MiB. const PLATFORM_DESCRIPTOR = Object.getOwnPropertyDescriptor(process, "platform"); +const ORIGINAL_HERDR_ENV = Bun.env.HERDR_ENV; class LargeCjkContent implements Component { #lines: string[]; @@ -85,9 +86,15 @@ class ManualRenderScheduler implements RenderScheduler { } } +beforeEach(() => { + delete Bun.env.HERDR_ENV; +}); + describe("issue #2115: ConPTY large-session resume truncates at logical lines", () => { afterEach(() => { if (PLATFORM_DESCRIPTOR) Object.defineProperty(process, "platform", PLATFORM_DESCRIPTOR); + if (ORIGINAL_HERDR_ENV === undefined) delete Bun.env.HERDR_ENV; + else Bun.env.HERDR_ENV = ORIGINAL_HERDR_ENV; vi.restoreAllMocks(); }); diff --git a/packages/tui/test/issue-4863-repro.test.ts b/packages/tui/test/issue-4863-repro.test.ts index 33d9760ff..cd0e00707 100644 --- a/packages/tui/test/issue-4863-repro.test.ts +++ b/packages/tui/test/issue-4863-repro.test.ts @@ -1,4 +1,4 @@ -import { afterEach, describe, expect, it, vi } from "bun:test"; +import { afterEach, beforeEach, describe, expect, it, vi } from "bun:test"; import { type Component, TUI } from "@oh-my-pi/pi-tui"; import { VirtualTerminal } from "./virtual-terminal"; @@ -15,6 +15,7 @@ import { VirtualTerminal } from "./virtual-terminal"; const PLATFORM_DESCRIPTOR = Object.getOwnPropertyDescriptor(process, "platform"); const WSL_DISTRO_NAME = process.env.WSL_DISTRO_NAME; const TMUX = process.env.TMUX; +const HERDR_ENV = process.env.HERDR_ENV; // A full paint clears the viewport with ED2 (`CSI 2 J`), or — when it also // clears native scrollback — homes the cursor and emits ED3 (`CSI H CSI 3 J`) @@ -41,6 +42,10 @@ class LargeContent implements Component { } } +beforeEach(() => { + delete process.env.HERDR_ENV; +}); + describe("issue #4863: Ctrl+O full-view expand truncates the session on ConPTY", () => { afterEach(() => { if (PLATFORM_DESCRIPTOR) Object.defineProperty(process, "platform", PLATFORM_DESCRIPTOR); @@ -48,6 +53,8 @@ describe("issue #4863: Ctrl+O full-view expand truncates the session on ConPTY", else process.env.WSL_DISTRO_NAME = WSL_DISTRO_NAME; if (TMUX === undefined) delete process.env.TMUX; else process.env.TMUX = TMUX; + if (HERDR_ENV === undefined) delete process.env.HERDR_ENV; + else process.env.HERDR_ENV = HERDR_ENV; vi.restoreAllMocks(); }); diff --git a/packages/tui/test/keys.test.ts b/packages/tui/test/keys.test.ts index b7f9a6ef8..a8d36a757 100644 --- a/packages/tui/test/keys.test.ts +++ b/packages/tui/test/keys.test.ts @@ -205,6 +205,7 @@ describe("Raw 0x08 backspace disambiguation", () => { "TMUX", "STY", "ZELLIJ", + "HERDR_ENV", "TERM", "CMUX_WORKSPACE_ID", "CMUX_SURFACE_ID", diff --git a/packages/tui/test/notifications.test.ts b/packages/tui/test/notifications.test.ts index 1e6094af4..64e30219f 100644 --- a/packages/tui/test/notifications.test.ts +++ b/packages/tui/test/notifications.test.ts @@ -19,6 +19,7 @@ const stdinSetRawModeDescriptor = Object.getOwnPropertyDescriptor(process.stdin, const originalOsc99Probe = Bun.env.PI_TUI_OSC99_PROBE; const originalTmux = Bun.env.TMUX; const originalZellij = Bun.env.ZELLIJ; +const originalHerdrEnv = Bun.env.HERDR_ENV; const originalPiNotifications = Bun.env.PI_NOTIFICATIONS; const originalCmuxSurfaceId = Bun.env.CMUX_SURFACE_ID; const originalCmuxWorkspaceId = Bun.env.CMUX_WORKSPACE_ID; @@ -77,6 +78,7 @@ describe("terminal notifications", () => { // assertions never see a stray inherited TMUX leaking the DCS wrap in. delete Bun.env.TMUX; delete Bun.env.ZELLIJ; + delete Bun.env.HERDR_ENV; delete Bun.env.CMUX_SURFACE_ID; delete Bun.env.CMUX_WORKSPACE_ID; delete Bun.env.CMUX_SOCKET_PATH; @@ -94,6 +96,7 @@ describe("terminal notifications", () => { restoreEnv("PI_TUI_OSC99_PROBE", originalOsc99Probe); restoreEnv("TMUX", originalTmux); restoreEnv("ZELLIJ", originalZellij); + restoreEnv("HERDR_ENV", originalHerdrEnv); restoreEnv("PI_NOTIFICATIONS", originalPiNotifications); restoreEnv("CMUX_SURFACE_ID", originalCmuxSurfaceId); restoreEnv("CMUX_WORKSPACE_ID", originalCmuxWorkspaceId); diff --git a/packages/tui/test/overlay-exit-flicker.test.ts b/packages/tui/test/overlay-exit-flicker.test.ts index 0528b8bae..c69213c63 100644 --- a/packages/tui/test/overlay-exit-flicker.test.ts +++ b/packages/tui/test/overlay-exit-flicker.test.ts @@ -13,6 +13,7 @@ const ENV: Record = { TMUX: undefined, STY: undefined, ZELLIJ: undefined, + HERDR_ENV: undefined, CMUX_WORKSPACE_ID: undefined, CMUX_SURFACE_ID: undefined, CMUX_REMOTE_TRANSPORT: undefined, diff --git a/packages/tui/test/overlay-scroll.test.ts b/packages/tui/test/overlay-scroll.test.ts index d17c04303..d0148b43b 100644 --- a/packages/tui/test/overlay-scroll.test.ts +++ b/packages/tui/test/overlay-scroll.test.ts @@ -173,7 +173,7 @@ describe("TUI overlays", () => { // A resize on Warp takes the in-place path (no ED3), so neutralize the // ambient terminal identity to keep the direct-terminal resize/scrollback // assertions below deterministic on any dev machine. - for (const key of ["TERM_PROGRAM", "PI_TUI_RESIZE_IN_PLACE"]) { + for (const key of ["TERM_PROGRAM", "PI_TUI_RESIZE_IN_PLACE", "HERDR_ENV"]) { savedTerminalEnv[key] = Bun.env[key]; delete Bun.env[key]; } diff --git a/packages/tui/test/render-regressions.test.ts b/packages/tui/test/render-regressions.test.ts index 6ec257d96..7df42f9d2 100644 --- a/packages/tui/test/render-regressions.test.ts +++ b/packages/tui/test/render-regressions.test.ts @@ -223,7 +223,7 @@ describe("TUI terminal-state regressions", () => { // Resize classification now depends on TERM_PROGRAM (Warp takes the // in-place path), so neutralize the ambient terminal identity to keep // these direct-terminal assertions deterministic on any dev machine. - for (const key of ["TERM_PROGRAM", "PI_TUI_RESIZE_IN_PLACE"]) { + for (const key of ["TERM_PROGRAM", "PI_TUI_RESIZE_IN_PLACE", "HERDR_ENV"]) { savedTerminalEnv[key] = Bun.env[key]; delete Bun.env[key]; } @@ -4215,7 +4215,10 @@ describe("TUI terminal-state regressions", () => { }); describe("foreground-tool streaming on ED3-risk terminals", () => { + let originalHerdrEnv: string | undefined; beforeEach(() => { + originalHerdrEnv = Bun.env.HERDR_ENV; + delete Bun.env.HERDR_ENV; let monotonicNow = 0; vi.spyOn(performance, "now").mockImplementation(() => { monotonicNow += 20; @@ -4224,6 +4227,8 @@ describe("foreground-tool streaming on ED3-risk terminals", () => { }); afterEach(() => { + if (originalHerdrEnv === undefined) delete Bun.env.HERDR_ENV; + else Bun.env.HERDR_ENV = originalHerdrEnv; vi.restoreAllMocks(); }); diff --git a/packages/tui/test/resize-viewport-defer.test.ts b/packages/tui/test/resize-viewport-defer.test.ts index 7f34cdeda..213fd628b 100644 --- a/packages/tui/test/resize-viewport-defer.test.ts +++ b/packages/tui/test/resize-viewport-defer.test.ts @@ -21,6 +21,7 @@ const NO_MULTIPLEXER_ENV: Record = { TMUX: undefined, STY: undefined, ZELLIJ: undefined, + HERDR_ENV: undefined, CMUX_WORKSPACE_ID: undefined, CMUX_SURFACE_ID: undefined, CMUX_REMOTE_TRANSPORT: undefined, diff --git a/packages/tui/test/streaming-scrollback-defer.test.ts b/packages/tui/test/streaming-scrollback-defer.test.ts index 0c4638afe..793e22e2e 100644 --- a/packages/tui/test/streaming-scrollback-defer.test.ts +++ b/packages/tui/test/streaming-scrollback-defer.test.ts @@ -179,7 +179,7 @@ function saveTerminalEnv(): Record { // ambient terminal identity to keep the direct-terminal scrollback // assertions deterministic on any dev machine. const saved: Record = {}; - for (const key of ["TERM_PROGRAM", "PI_TUI_RESIZE_IN_PLACE"]) { + for (const key of ["TERM_PROGRAM", "PI_TUI_RESIZE_IN_PLACE", "HERDR_ENV"]) { saved[key] = Bun.env[key]; delete Bun.env[key]; }