mirror of
https://github.com/wassname/pi-lgtm.git
synced 2026-06-27 16:46:17 +08:00
simplify collapsed task rows
This commit is contained in:
@@ -0,0 +1,99 @@
|
||||
import { describe, expect, it, vi } from "vitest";
|
||||
import proofTasksExtension from "../src/index.js";
|
||||
|
||||
type RegisteredTool = {
|
||||
name: string;
|
||||
execute: (...args: any[]) => Promise<any>;
|
||||
};
|
||||
|
||||
function makeHarness() {
|
||||
const tools = new Map<string, RegisteredTool>();
|
||||
const pi = {
|
||||
on: vi.fn(),
|
||||
registerTool: vi.fn((tool: RegisteredTool) => tools.set(tool.name, tool)),
|
||||
registerCommand: vi.fn(),
|
||||
sendMessage: vi.fn(),
|
||||
};
|
||||
|
||||
proofTasksExtension(pi as any);
|
||||
|
||||
async function execTool(name: string, params: Record<string, unknown>) {
|
||||
const tool = tools.get(name);
|
||||
if (!tool) throw new Error(`Tool ${name} not registered`);
|
||||
return tool.execute("tool-call", params, undefined, undefined, {});
|
||||
}
|
||||
|
||||
return { execTool };
|
||||
}
|
||||
|
||||
describe("TaskList", () => {
|
||||
it("renders a compact one-line-per-task summary", async () => {
|
||||
const harness = makeHarness();
|
||||
await harness.execTool("TaskCreate", {
|
||||
subject: "Design the flux capacitor",
|
||||
description: "Desc",
|
||||
done_criterion: "done",
|
||||
});
|
||||
await harness.execTool("TaskCreate", {
|
||||
subject: "Acquiring plutonium",
|
||||
description: "Desc",
|
||||
done_criterion: "done",
|
||||
progress_label: "Acquiring plutonium",
|
||||
});
|
||||
await harness.execTool("TaskCreate", {
|
||||
subject: "Install flux capacitor in DeLorean",
|
||||
description: "Desc",
|
||||
done_criterion: "done",
|
||||
parentId: "1",
|
||||
});
|
||||
await harness.execTool("TaskCreate", {
|
||||
subject: "Test time travel at 88 mph",
|
||||
description: "Desc",
|
||||
done_criterion: "done",
|
||||
});
|
||||
|
||||
await harness.execTool("TaskUpdate", { taskId: "1", status: "completed" });
|
||||
await harness.execTool("TaskUpdate", { taskId: "2", status: "in_progress" });
|
||||
await harness.execTool("TaskUpdate", { taskId: "3", add_blocked_by: ["1"] });
|
||||
await harness.execTool("TaskUpdate", { taskId: "4", add_blocked_by: ["2", "3"] });
|
||||
|
||||
const result = await harness.execTool("TaskList", {});
|
||||
const text = result.content[0].text;
|
||||
|
||||
expect(text).toContain("● 4 tasks (1 in progress, 3 open)");
|
||||
expect(text).toContain("◻ #1 Design the flux capacitor");
|
||||
expect(text).toContain("◼ #2 Acquiring plutonium");
|
||||
expect(text).toContain("◻ #3 Install flux capacitor in DeLorean › subtask of #1 › blocked by #1");
|
||||
expect(text).toContain("◻ #4 Test time travel at 88 mph › blocked by #2, #3");
|
||||
expect(text).not.toContain("[ACTIVE]");
|
||||
expect(text).not.toContain("[PENDING]");
|
||||
expect(text).not.toContain("[DONE");
|
||||
expect(text).not.toContain("🛠");
|
||||
expect(text).not.toContain("test:");
|
||||
});
|
||||
|
||||
it("shows completed subtasks without proof-lane clutter", async () => {
|
||||
const harness = makeHarness();
|
||||
await harness.execTool("TaskCreate", {
|
||||
subject: "Top-level goal",
|
||||
description: "Desc",
|
||||
done_criterion: "done",
|
||||
});
|
||||
await harness.execTool("TaskCreate", {
|
||||
subject: "Finished checklist item",
|
||||
description: "Desc",
|
||||
done_criterion: "done",
|
||||
parentId: "1",
|
||||
});
|
||||
|
||||
await harness.execTool("TaskUpdate", { taskId: "2", status: "completed" });
|
||||
|
||||
const result = await harness.execTool("TaskList", {});
|
||||
const text = result.content[0].text;
|
||||
|
||||
expect(text).toContain("● 2 tasks (1 done, 1 open)");
|
||||
expect(text).toContain("✔ #2 Finished checklist item › subtask of #1");
|
||||
expect(text).not.toContain("[DONE");
|
||||
expect(text).not.toContain("🛠");
|
||||
});
|
||||
});
|
||||
+12
-10
@@ -1,5 +1,4 @@
|
||||
import { afterEach, beforeEach, describe, expect, it, vi } from "vitest";
|
||||
import { REVIEW_BADGES } from "../src/review-badges.js";
|
||||
import { TaskStore } from "../src/task-store.js";
|
||||
import { TaskWidget, type Theme, type UICtx } from "../src/ui/task-widget.js";
|
||||
|
||||
@@ -73,11 +72,12 @@ describe("TaskWidget", () => {
|
||||
widget.update();
|
||||
|
||||
const lines = renderWidget(ui.state);
|
||||
expect(lines).toHaveLength(3); // header + 1 task + done_criterion
|
||||
expect(lines).toHaveLength(2); // header + 1 task
|
||||
expect(lines[0]).toContain("1 tasks");
|
||||
expect(lines[0]).toContain("1 open");
|
||||
expect(lines[1]).toContain("◻");
|
||||
expect(lines[1]).toContain("Do something");
|
||||
expect(lines[1]).not.toContain("done");
|
||||
});
|
||||
|
||||
it("renders in-progress tasks with ◼ icon", () => {
|
||||
@@ -100,16 +100,18 @@ describe("TaskWidget", () => {
|
||||
expect(lines[1]).toContain("~~#1 Done task~~");
|
||||
});
|
||||
|
||||
it("renders robot review badges on completed tasks", () => {
|
||||
it("does not render proof badges on collapsed rows", () => {
|
||||
store.create("Done task", "Desc", "done");
|
||||
store.update("1", {
|
||||
metadata: { robot_review_observations: ["Observed output drift on seed 2"] },
|
||||
metadata: { robot_review_observations: ["Observed output drift on seed 2"], lgtm_evidence: "verbatim output" },
|
||||
});
|
||||
store.complete("1");
|
||||
widget.update();
|
||||
|
||||
const lines = renderWidget(ui.state);
|
||||
expect(lines[1]).toContain(REVIEW_BADGES.robot);
|
||||
expect(lines[1]).not.toContain("[");
|
||||
expect(lines[1]).not.toContain("🛠");
|
||||
expect(lines[1]).not.toContain("🤖");
|
||||
});
|
||||
|
||||
it("renders active tasks with spinner icon", () => {
|
||||
@@ -181,9 +183,9 @@ describe("TaskWidget", () => {
|
||||
widget.update();
|
||||
|
||||
const lines = renderWidget(ui.state);
|
||||
// header + 5 visible tasks (each has 2 lines: task + done_criterion) + "...and 10 more"
|
||||
expect(lines).toHaveLength(12);
|
||||
expect(lines[11]).toContain("10 more");
|
||||
// header + 5 visible tasks + "...and 10 more"
|
||||
expect(lines).toHaveLength(7);
|
||||
expect(lines[6]).toContain("10 more");
|
||||
});
|
||||
|
||||
it("tracks token usage for active tasks", () => {
|
||||
@@ -241,7 +243,7 @@ describe("TaskWidget", () => {
|
||||
|
||||
const lines = renderWidget(ui.state);
|
||||
expect(lines[1]).toContain("Processing A…");
|
||||
expect(lines[3]).toContain("Processing B…");
|
||||
expect(lines[2]).toContain("Processing B…");
|
||||
});
|
||||
|
||||
it("distributes token usage across all active tasks", () => {
|
||||
@@ -257,7 +259,7 @@ describe("TaskWidget", () => {
|
||||
const lines = renderWidget(ui.state);
|
||||
// Both tasks should have the same token counts
|
||||
expect(lines[1]).toContain("↑ 100");
|
||||
expect(lines[3]).toContain("↑ 100");
|
||||
expect(lines[2]).toContain("↑ 100");
|
||||
});
|
||||
|
||||
it("dispose clears widget and timer", () => {
|
||||
|
||||
Reference in New Issue
Block a user