* feat(files): edit workspace files on web Keep source buffers synchronized with host file changes and require an explicit overwrite or reload when revisions diverge. * feat(panels): surface and protect modified tabs Expose tooltip and modification state through the generic panel boundary so tabs can show stable metadata and guard every close route consistently. * fix(tests): use portable fake timeout handle * fix(files): harden editor conflict handling Preserve modified panel state across tab eviction, use precise revisions for optimistic writes, coalesce concurrent file watchers, and localize the editor interface. * fix(files): close editor concurrency gaps Coalesce clean reloads, preserve subscriber identities and file permissions, suspend pending saves during close confirmation, and carry precise revisions through file reads. * test(files): expect read revision metadata
36 lines
1.3 KiB
TypeScript
36 lines
1.3 KiB
TypeScript
import { describe, expect, test } from "vitest";
|
|
import {
|
|
getPanelInstanceAttributes,
|
|
setPanelInstanceAttributes,
|
|
subscribePanelInstanceAttributes,
|
|
} from "./panel-instance-attributes";
|
|
|
|
describe("panel instance attributes", () => {
|
|
test("keeps runtime attributes isolated by workspace and tab", () => {
|
|
const first = { serverId: "server", workspaceId: "one", tabId: "tab" };
|
|
const second = { serverId: "server", workspaceId: "two", tabId: "tab" };
|
|
|
|
setPanelInstanceAttributes(first, { modified: true });
|
|
|
|
expect(getPanelInstanceAttributes(first)).toEqual({ modified: true });
|
|
expect(getPanelInstanceAttributes(second)).toEqual({ modified: false });
|
|
|
|
setPanelInstanceAttributes(first, { modified: false });
|
|
});
|
|
|
|
test("notifies subscribers only when attributes change", () => {
|
|
const identity = { serverId: "server", workspaceId: "workspace", tabId: "observed" };
|
|
let notifications = 0;
|
|
const unsubscribe = subscribePanelInstanceAttributes(identity, () => {
|
|
notifications += 1;
|
|
});
|
|
|
|
setPanelInstanceAttributes(identity, { modified: true });
|
|
setPanelInstanceAttributes(identity, { modified: true });
|
|
setPanelInstanceAttributes(identity, { modified: false });
|
|
|
|
expect(notifications).toBe(2);
|
|
unsubscribe();
|
|
});
|
|
});
|