89 lines
4.1 KiB
TypeScript
89 lines
4.1 KiB
TypeScript
import test from "node:test";
|
|
import assert from "node:assert/strict";
|
|
import path from "node:path";
|
|
import { readFile } from "node:fs/promises";
|
|
import { fileURLToPath } from "node:url";
|
|
|
|
const testsDir = path.dirname(fileURLToPath(import.meta.url));
|
|
|
|
async function readWorkspaceFile(relativePath: string) {
|
|
return readFile(path.join(testsDir, "..", relativePath), "utf8");
|
|
}
|
|
|
|
test("RealtimeRefresh supports project-scoped refresh filtering", async () => {
|
|
const source = await readWorkspaceFile("src/components/app-runtime.tsx");
|
|
|
|
assert.match(source, /projectId\?: string/, "expected RealtimeRefresh to accept an optional projectId");
|
|
assert.match(source, /projectIds\?: string\[]/, "expected RealtimeRefresh to accept optional projectIds");
|
|
assert.match(
|
|
source,
|
|
/conversationUpdatedNotes\?: string\[]/,
|
|
"expected RealtimeRefresh to accept optional conversationUpdatedNotes",
|
|
);
|
|
assert.match(
|
|
source,
|
|
/shouldRefreshRealtimeEvent\(\{/,
|
|
"expected RealtimeRefresh to delegate scoped filtering to helper logic",
|
|
);
|
|
assert.match(
|
|
source,
|
|
/planThrottledRefresh\(throttleState, Date\.now\(\), 400\)/,
|
|
"expected RealtimeRefresh to throttle burst refreshes on the client",
|
|
);
|
|
});
|
|
|
|
test("project conversation pages wire project-scoped realtime refresh", async () => {
|
|
const [projectPage, goalsPage, versionsPage, threadStatusPage, participantsPage] = await Promise.all([
|
|
readWorkspaceFile("src/app/conversations/[projectId]/page.tsx"),
|
|
readWorkspaceFile("src/app/conversations/[projectId]/goals/page.tsx"),
|
|
readWorkspaceFile("src/app/conversations/[projectId]/versions/page.tsx"),
|
|
readWorkspaceFile("src/app/conversations/[projectId]/thread-status/page.tsx"),
|
|
readWorkspaceFile("src/app/conversations/[projectId]/participants/page.tsx"),
|
|
]);
|
|
|
|
assert.match(projectPage, /projectId=\{detail\.project\.id\}/, "expected project chat page to pass projectId into RealtimeRefresh");
|
|
|
|
for (const [label, source] of [
|
|
["goals", goalsPage],
|
|
["versions", versionsPage],
|
|
["thread-status", threadStatusPage],
|
|
["participants", participantsPage],
|
|
] as const) {
|
|
assert.match(source, /<RealtimeRefresh/, `expected ${label} page to render RealtimeRefresh`);
|
|
assert.match(source, /projectId=\{projectId\}/, `expected ${label} page to scope refreshes to the current project`);
|
|
assert.match(source, /"conversation\.updated"/, `expected ${label} page to listen to conversation updates`);
|
|
}
|
|
|
|
assert.match(
|
|
goalsPage,
|
|
/conversationUpdatedNotes=\{\["project_goals\.updated"\]\}/,
|
|
"expected goals page to refresh only on project goal markers",
|
|
);
|
|
assert.match(
|
|
versionsPage,
|
|
/conversationUpdatedNotes=\{\["project_goals\.updated"\]\}/,
|
|
"expected versions page to refresh only on project goal markers",
|
|
);
|
|
});
|
|
|
|
test("folder conversation page wires folder thread ids into realtime refresh", async () => {
|
|
const folderPage = await readWorkspaceFile("src/app/conversations/folders/[folderKey]/page.tsx");
|
|
|
|
assert.match(folderPage, /<RealtimeRefresh/, "expected folder page to render RealtimeRefresh");
|
|
assert.match(folderPage, /projectIds=\{folder\.threads\.map\(\(thread\) => thread\.projectId\)\}/, "expected folder page to scope refreshes to folder thread project ids");
|
|
assert.match(folderPage, /deviceId=\{folder\.deviceId\}/, "expected folder page to scope device-only refreshes to the folder device");
|
|
assert.match(folderPage, /"conversation\.updated"/, "expected folder page to listen to conversation updates");
|
|
});
|
|
|
|
test("forward page wires realtime refresh for visible source and target projects", async () => {
|
|
const forwardPage = await readWorkspaceFile("src/app/conversations/[projectId]/forward/page.tsx");
|
|
|
|
assert.match(forwardPage, /<RealtimeRefresh/, "expected forward page to render RealtimeRefresh");
|
|
assert.match(
|
|
forwardPage,
|
|
/projectIds=\{\[projectId, \.\.\.targets\.map\(\(target\) => target\.id\)\]\}/,
|
|
"expected forward page to scope refreshes to visible source and target project ids",
|
|
);
|
|
assert.match(forwardPage, /"conversation\.updated"/, "expected forward page to listen to conversation updates");
|
|
});
|