feat: add file tabs and improve terminal rendering with WebGL
This commit is contained in:
@@ -5,7 +5,7 @@ import { TerminalOutputDeliveryQueue } from "./terminal-output-delivery-queue";
|
||||
describe("terminal-output-delivery-queue", () => {
|
||||
it("retries in-flight delivery when consume is missing", () => {
|
||||
vi.useFakeTimers();
|
||||
const delivered: Array<{ sequence: number; text: string }> = [];
|
||||
const delivered: Array<{ sequence: number; text: string; replay: boolean }> = [];
|
||||
const queue = new TerminalOutputDeliveryQueue({
|
||||
onDeliver: (chunk) => {
|
||||
delivered.push(chunk);
|
||||
@@ -13,45 +13,45 @@ describe("terminal-output-delivery-queue", () => {
|
||||
deliveryTimeoutMs: 100,
|
||||
});
|
||||
|
||||
queue.enqueue({ sequence: 1, text: "a" });
|
||||
queue.enqueue({ sequence: 2, text: "b" });
|
||||
queue.enqueue({ sequence: 1, text: "a", replay: false });
|
||||
queue.enqueue({ sequence: 2, text: "b", replay: false });
|
||||
|
||||
expect(delivered).toEqual([{ sequence: 1, text: "a" }]);
|
||||
expect(delivered).toEqual([{ sequence: 1, text: "a", replay: false }]);
|
||||
|
||||
vi.advanceTimersByTime(100);
|
||||
expect(delivered).toEqual([
|
||||
{ sequence: 1, text: "a" },
|
||||
{ sequence: 1, text: "a" },
|
||||
{ sequence: 1, text: "a", replay: false },
|
||||
{ sequence: 1, text: "a", replay: false },
|
||||
]);
|
||||
|
||||
queue.consume({ sequence: 1 });
|
||||
expect(delivered).toEqual([
|
||||
{ sequence: 1, text: "a" },
|
||||
{ sequence: 1, text: "a" },
|
||||
{ sequence: 2, text: "b" },
|
||||
{ sequence: 1, text: "a", replay: false },
|
||||
{ sequence: 1, text: "a", replay: false },
|
||||
{ sequence: 2, text: "b", replay: false },
|
||||
]);
|
||||
|
||||
vi.useRealTimers();
|
||||
});
|
||||
|
||||
it("delivers first chunk immediately and blocks later chunks until consumed", () => {
|
||||
const delivered: Array<{ sequence: number; text: string }> = [];
|
||||
const delivered: Array<{ sequence: number; text: string; replay: boolean }> = [];
|
||||
const queue = new TerminalOutputDeliveryQueue({
|
||||
onDeliver: (chunk) => {
|
||||
delivered.push(chunk);
|
||||
},
|
||||
});
|
||||
|
||||
queue.enqueue({ sequence: 1, text: "a" });
|
||||
queue.enqueue({ sequence: 2, text: "b" });
|
||||
queue.enqueue({ sequence: 3, text: "c" });
|
||||
queue.enqueue({ sequence: 1, text: "a", replay: false });
|
||||
queue.enqueue({ sequence: 2, text: "b", replay: false });
|
||||
queue.enqueue({ sequence: 3, text: "c", replay: false });
|
||||
|
||||
expect(delivered).toEqual([{ sequence: 1, text: "a" }]);
|
||||
expect(delivered).toEqual([{ sequence: 1, text: "a", replay: false }]);
|
||||
|
||||
queue.consume({ sequence: 1 });
|
||||
expect(delivered).toEqual([
|
||||
{ sequence: 1, text: "a" },
|
||||
{ sequence: 3, text: "bc" },
|
||||
{ sequence: 1, text: "a", replay: false },
|
||||
{ sequence: 3, text: "bc", replay: false },
|
||||
]);
|
||||
});
|
||||
|
||||
@@ -59,83 +59,83 @@ describe("terminal-output-delivery-queue", () => {
|
||||
const delivered = vi.fn();
|
||||
const queue = new TerminalOutputDeliveryQueue({ onDeliver: delivered });
|
||||
|
||||
queue.enqueue({ sequence: 1, text: "x" });
|
||||
queue.enqueue({ sequence: 1, text: "x", replay: false });
|
||||
queue.consume({ sequence: 99 });
|
||||
queue.enqueue({ sequence: 2, text: "y" });
|
||||
queue.enqueue({ sequence: 2, text: "y", replay: false });
|
||||
|
||||
expect(delivered).toHaveBeenCalledTimes(1);
|
||||
expect(delivered).toHaveBeenNthCalledWith(1, { sequence: 1, text: "x" });
|
||||
expect(delivered).toHaveBeenNthCalledWith(1, { sequence: 1, text: "x", replay: false });
|
||||
|
||||
queue.consume({ sequence: 1 });
|
||||
|
||||
expect(delivered).toHaveBeenCalledTimes(2);
|
||||
expect(delivered).toHaveBeenNthCalledWith(2, { sequence: 2, text: "y" });
|
||||
expect(delivered).toHaveBeenNthCalledWith(2, { sequence: 2, text: "y", replay: false });
|
||||
});
|
||||
|
||||
it("resets in-flight and pending chunks", () => {
|
||||
const delivered: Array<{ sequence: number; text: string }> = [];
|
||||
const delivered: Array<{ sequence: number; text: string; replay: boolean }> = [];
|
||||
const queue = new TerminalOutputDeliveryQueue({
|
||||
onDeliver: (chunk) => {
|
||||
delivered.push(chunk);
|
||||
},
|
||||
});
|
||||
|
||||
queue.enqueue({ sequence: 1, text: "hello" });
|
||||
queue.enqueue({ sequence: 2, text: " world" });
|
||||
queue.enqueue({ sequence: 1, text: "hello", replay: false });
|
||||
queue.enqueue({ sequence: 2, text: " world", replay: false });
|
||||
|
||||
queue.reset();
|
||||
queue.enqueue({ sequence: 3, text: "next" });
|
||||
queue.enqueue({ sequence: 3, text: "next", replay: false });
|
||||
|
||||
expect(delivered).toEqual([
|
||||
{ sequence: 1, text: "hello" },
|
||||
{ sequence: 3, text: "next" },
|
||||
{ sequence: 1, text: "hello", replay: false },
|
||||
{ sequence: 3, text: "next", replay: false },
|
||||
]);
|
||||
});
|
||||
|
||||
it("preserves empty chunk payloads for authoritative clears", () => {
|
||||
const delivered: Array<{ sequence: number; text: string }> = [];
|
||||
const delivered: Array<{ sequence: number; text: string; replay: boolean }> = [];
|
||||
const queue = new TerminalOutputDeliveryQueue({
|
||||
onDeliver: (chunk) => {
|
||||
delivered.push(chunk);
|
||||
},
|
||||
});
|
||||
|
||||
queue.enqueue({ sequence: 1, text: "abc" });
|
||||
queue.enqueue({ sequence: 1, text: "abc", replay: false });
|
||||
queue.consume({ sequence: 1 });
|
||||
queue.enqueue({ sequence: 2, text: "" });
|
||||
queue.enqueue({ sequence: 2, text: "", replay: false });
|
||||
|
||||
expect(delivered).toEqual([
|
||||
{ sequence: 1, text: "abc" },
|
||||
{ sequence: 2, text: "" },
|
||||
{ sequence: 1, text: "abc", replay: false },
|
||||
{ sequence: 2, text: "", replay: false },
|
||||
]);
|
||||
});
|
||||
|
||||
it("treats clear chunks as a delivery barrier and drops pending stale text", () => {
|
||||
const delivered: Array<{ sequence: number; text: string }> = [];
|
||||
const delivered: Array<{ sequence: number; text: string; replay: boolean }> = [];
|
||||
const queue = new TerminalOutputDeliveryQueue({
|
||||
onDeliver: (chunk) => {
|
||||
delivered.push(chunk);
|
||||
},
|
||||
});
|
||||
|
||||
queue.enqueue({ sequence: 1, text: "a" });
|
||||
queue.enqueue({ sequence: 2, text: "b" });
|
||||
queue.enqueue({ sequence: 3, text: "" });
|
||||
queue.enqueue({ sequence: 4, text: "c" });
|
||||
queue.enqueue({ sequence: 1, text: "a", replay: false });
|
||||
queue.enqueue({ sequence: 2, text: "b", replay: false });
|
||||
queue.enqueue({ sequence: 3, text: "", replay: false });
|
||||
queue.enqueue({ sequence: 4, text: "c", replay: false });
|
||||
|
||||
expect(delivered).toEqual([{ sequence: 1, text: "a" }]);
|
||||
expect(delivered).toEqual([{ sequence: 1, text: "a", replay: false }]);
|
||||
|
||||
queue.consume({ sequence: 1 });
|
||||
expect(delivered).toEqual([
|
||||
{ sequence: 1, text: "a" },
|
||||
{ sequence: 3, text: "" },
|
||||
{ sequence: 1, text: "a", replay: false },
|
||||
{ sequence: 3, text: "", replay: false },
|
||||
]);
|
||||
|
||||
queue.consume({ sequence: 3 });
|
||||
expect(delivered).toEqual([
|
||||
{ sequence: 1, text: "a" },
|
||||
{ sequence: 3, text: "" },
|
||||
{ sequence: 4, text: "c" },
|
||||
{ sequence: 1, text: "a", replay: false },
|
||||
{ sequence: 3, text: "", replay: false },
|
||||
{ sequence: 4, text: "c", replay: false },
|
||||
]);
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user