* perf(api): filter peer-run activity in the transcript page query The transcript loaded a raw page, dropped hidden peer-run rows in memory and rescanned when nothing visible was left, so a long delegated stretch cost two queries per hidden page. The page query now joins runs and excludes hidden peer activity in Postgres, so every page is filled with visible rows. The kept block kinds live in one list shared by paging, the in-memory filter and live event forwarding. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01YTJRkJrXAS9e3aEFcFYTy8 * test: port the main-conversation journey fix from #126 Journey 5c fails on main since every space got its own main conversation: the lookup picked the Lab conversation instead of the home one. Same change as #126 (including its chart-links warm-up), so this PR can go green; it no-ops once #126 lands. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01YTJRkJrXAS9e3aEFcFYTy8 --------- Co-authored-by: Claude <noreply@anthropic.com>
144 lines
4.9 KiB
TypeScript
144 lines
4.9 KiB
TypeScript
import type { MessageBlock } from "@rakazo/contracts";
|
|
import type { PrismaClient } from "@rakazo/db";
|
|
import { createDb, provisionMessagingIdentity } from "@rakazo/db";
|
|
import { afterAll, beforeAll, describe, expect, it } from "vitest";
|
|
import { loadMessagePage } from "./thread-message-pages.js";
|
|
|
|
const databaseUrl = process.env.DATABASE_URL;
|
|
const describePostgres =
|
|
process.env.VERIFY_DATABASE && databaseUrl ? describe.sequential : describe.skip;
|
|
|
|
describePostgres("loadMessagePage (PostgreSQL)", () => {
|
|
let prisma: PrismaClient;
|
|
let close: () => Promise<void>;
|
|
let identity: { userId: string; spaceId: string; botId: string; threadId: string };
|
|
let userRunId: string;
|
|
let peerRunId: string;
|
|
let seq = 0;
|
|
|
|
beforeAll(async () => {
|
|
const db = createDb(databaseUrl!);
|
|
prisma = db.prisma;
|
|
close = async () => {
|
|
await db.prisma.$disconnect();
|
|
await db.pool.end();
|
|
};
|
|
identity = await provisionMessagingIdentity(
|
|
prisma,
|
|
{ provider: "sendblue", address: `+1555${Date.now().toString().slice(-7)}` },
|
|
{ signupsEnabled: undefined, signupAllowlist: undefined },
|
|
);
|
|
const { spaceId, botId, threadId, userId } = identity;
|
|
const owner = { spaceId, botId, threadId, userId };
|
|
const run = async (trigger: string) => {
|
|
const task = await prisma.task.create({
|
|
data: { ...owner, prompt: "fixture", status: "completed" },
|
|
});
|
|
const created = await prisma.run.create({
|
|
data: { ...owner, taskId: task.id, status: "completed", trigger },
|
|
});
|
|
return created.id;
|
|
};
|
|
userRunId = await run("user_message");
|
|
peerRunId = await run("bot_message");
|
|
seq =
|
|
(
|
|
await prisma.message.aggregate({
|
|
where: { threadId: identity.threadId },
|
|
_max: { seq: true },
|
|
})
|
|
)._max.seq ?? 0;
|
|
});
|
|
|
|
afterAll(async () => {
|
|
if (identity) {
|
|
await prisma.messagingIdentity.deleteMany({ where: { userId: identity.userId } });
|
|
await prisma.organization.deleteMany({ where: { id: identity.spaceId } });
|
|
await prisma.user.deleteMany({ where: { id: identity.userId } });
|
|
}
|
|
await close?.();
|
|
});
|
|
|
|
async function message(id: string, runId: string | null, blocks: MessageBlock[]) {
|
|
seq += 1;
|
|
await prisma.message.create({
|
|
data: {
|
|
id: `${identity.threadId}-${id}`,
|
|
threadId: identity.threadId,
|
|
seq,
|
|
role: "bot",
|
|
runId,
|
|
blocks,
|
|
},
|
|
});
|
|
return seq;
|
|
}
|
|
|
|
const ids = (page: Awaited<ReturnType<typeof loadMessagePage>>) =>
|
|
page.messages.map((row) => row.id.slice(identity.threadId.length + 1));
|
|
|
|
it("fills a page with visible rows across a long stretch of hidden peer activity", async () => {
|
|
await message("older", userRunId, [{ kind: "text", text: "Older answer" }]);
|
|
await message("newer", userRunId, [{ kind: "text", text: "Newer answer" }]);
|
|
for (let index = 0; index < 30; index += 1) {
|
|
await message(`peer-steps-${index}`, peerRunId, [
|
|
{ kind: "steps", steps: [{ label: "Working", count: 1 }] },
|
|
]);
|
|
}
|
|
await message("peer-receipt", peerRunId, [
|
|
{ kind: "bot_message_received", fromBotId: "bot-2", fromBotName: "Coder", text: "Done." },
|
|
]);
|
|
await message("peer-reply", peerRunId, [{ kind: "text", text: "Peer summary" }]);
|
|
await message("orphan-run", "run-that-no-longer-exists", [{ kind: "text", text: "Kept" }]);
|
|
|
|
const first = await loadMessagePage(prisma, identity.threadId, undefined, 3);
|
|
expect(ids(first)).toEqual(["peer-receipt", "peer-reply", "orphan-run"]);
|
|
|
|
const second = await loadMessagePage(prisma, identity.threadId, first.olderCursor!, 2);
|
|
expect(ids(second)).toEqual(["older", "newer"]);
|
|
|
|
const peerView = await loadMessagePage(
|
|
prisma,
|
|
identity.threadId,
|
|
undefined,
|
|
3,
|
|
undefined,
|
|
true,
|
|
);
|
|
expect(ids(peerView)).toEqual(["peer-receipt", "peer-reply", "orphan-run"]);
|
|
const peerOlder = await loadMessagePage(
|
|
prisma,
|
|
identity.threadId,
|
|
peerView.olderCursor!,
|
|
1,
|
|
undefined,
|
|
true,
|
|
);
|
|
expect(ids(peerOlder)).toEqual(["peer-steps-29"]);
|
|
});
|
|
|
|
it("skips a receipt-only page for web but returns it when receipts are displayed", async () => {
|
|
await message("before-receipts", userRunId, [{ kind: "text", text: "Answer" }]);
|
|
await message("sent", userRunId, [
|
|
{ kind: "bot_message_sent", toBotId: "bot-2", toBotName: "Coder", text: "Check this." },
|
|
]);
|
|
await message("received", peerRunId, [
|
|
{ kind: "bot_message_received", fromBotId: "bot-2", fromBotName: "Coder", text: "Done." },
|
|
]);
|
|
|
|
const web = await loadMessagePage(prisma, identity.threadId, undefined, 2);
|
|
expect(ids(web)).toEqual(["orphan-run", "before-receipts"]);
|
|
|
|
const mobile = await loadMessagePage(
|
|
prisma,
|
|
identity.threadId,
|
|
undefined,
|
|
2,
|
|
undefined,
|
|
false,
|
|
true,
|
|
);
|
|
expect(ids(mobile)).toEqual(["sent", "received"]);
|
|
});
|
|
});
|