MCPcopy
hub / github.com/coder/mux / getHistoryFromLatestBoundary

Method getHistoryFromLatestBoundary

src/node/services/historyService.ts:959–1008  ·  view source on GitHub ↗

* Read messages from a compaction boundary onward. * Falls back to full history if no boundary exists (new/uncompacted workspace). * * @param skip How many boundaries to skip (counting from the latest, across * chat.jsonl and the sealed archive). 0 = read from the latest *

(workspaceId: string, skip = 0)

Source from the content-addressed store, hash-verified

957 * that only needs the active compaction epoch.
958 */
959 async getHistoryFromLatestBoundary(workspaceId: string, skip = 0): Promise<Result<MuxMessage[]>> {
960 try {
961 // One-time lazy migration: seal any pre-boundary prefix left in chat.jsonl
962 // by older builds so this read (and every later one) stays O(active epoch).
963 await this.ensureSealedHistoryRotated(workspaceId);
964
965 const chatPath = this.getChatHistoryPath(workspaceId);
966 const archivePath = this.getChatArchivePath(workspaceId);
967
968 // Try the requested boundary in chat.jsonl, falling back to less-skipped boundaries.
969 let chatBoundaryCount = 0;
970 let chatFallbackOffset: number | null = null;
971 for (let s = skip; s >= 0; s--) {
972 const offset = await this.findLastBoundaryByteOffset(chatPath, s);
973 if (offset !== null) {
974 if (s === skip) {
975 return Ok(await this.readHistoryFromOffset(chatPath, offset));
976 }
977 // chat.jsonl has fewer boundaries than requested; remember its oldest
978 // boundary as a fallback and keep counting into the archive.
979 chatBoundaryCount = s + 1;
980 chatFallbackOffset = offset;
981 break;
982 }
983 }
984
985 // Boundaries older than chat.jsonl live in the sealed archive. A window that
986 // starts at an archive boundary spans the archive tail plus all of chat.jsonl.
987 for (let s = skip - chatBoundaryCount; s >= 0; s--) {
988 const offset = await this.findLastBoundaryByteOffset(archivePath, s);
989 if (offset !== null) {
990 const archived = await this.readHistoryFromOffset(archivePath, offset);
991 const active = await this.readChatHistory(workspaceId);
992 return Ok([...archived, ...active]);
993 }
994 }
995
996 if (chatFallbackOffset !== null) {
997 return Ok(await this.readHistoryFromOffset(chatPath, chatFallbackOffset));
998 }
999
1000 // No boundaries at all — workspace is uncompacted, full read is the only option
1001 const archived = await this.readArchivedHistory(workspaceId);
1002 const active = await this.readChatHistory(workspaceId);
1003 return Ok([...archived, ...active]);
1004 } catch (error) {
1005 const message = getErrorMessage(error);
1006 return Err(`Failed to read history from boundary: ${message}`);
1007 }
1008 }
1009
1010 // ── Sealed-history rotation ─────────────────────────────────────────────
1011 // Compaction (and /clear --soft) appends a durable context boundary but, by

Calls 10

getChatHistoryPathMethod · 0.95
getChatArchivePathMethod · 0.95
readHistoryFromOffsetMethod · 0.95
readChatHistoryMethod · 0.95
readArchivedHistoryMethod · 0.95
OkFunction · 0.90
getErrorMessageFunction · 0.90
ErrFunction · 0.90

Tested by 1