Archilyzer · Source

archilyzer

Archilyzer
git clone https://archilyzer.pages.dev/source/archilyzer.git
Log | Files | Refs | README | LICENSE

commit c9cbf3807d46c2642b6b0dd092c83d0336552684
parent 528d6d82c24ff2d0a947ac79d9315a01123dae55
Author: I Mean I'm Just Saying <imeanimjustsaying@kiwifarms.st>
Date:   Sat, 12 Sep 2026 11:57:54 -0400

common: a browser reader gets a browser's page-cache budget, and one comment

Two review items.

RemoteSource defaults to 48 MB per page cache and holds two of them, so the
per-origin registry was handing every origin a 96 MB ceiling — fine for one
long-lived MCP process, not for a tab, and least of all for a hub page, which
holds a reader per member site with no shared ceiling and no way for a browser
to turn the env knob down. The registry now passes 8 MB explicitly: 16 MB per
origin, so five federated members are 80 MB rather than 480 MB.

It can be that small without costing reads because the viewer memoises every
RECORD it has ever seen (transcriptCache.resolved, plus IndexedDB), so an
evicted page is only re-fetched for a video nobody has opened yet — a fetch
that was going to happen anyway. PageCache's MIN_CACHED_PAGES floor still
keeps two entries even where one page exceeds the whole budget. mcp/src/
source.ts constructs RemoteSource directly and keeps the 48 MB default, so no
bench counter moves.

And aliasesCache's comment claimed "404 -> data" while the catch returns []
for any ArchiveHttpError. The code is right — it is the old `if (!r.ok) return
[]`, and a server answering 500 should cost the suggestion chip rather than
the search — so the comment now says what it does.

Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>

Diffstat:
Mcommon/components/aliasesCache.ts | 14++++++++++----
Mcommon/lib/archive/readers.ts | 23++++++++++++++++++++++-
2 files changed, 32 insertions(+), 5 deletions(-)

diff --git a/common/components/aliasesCache.ts b/common/components/aliasesCache.ts @@ -13,10 +13,16 @@ import { coerceAliasConfig, type SearchAlias } from "../lib/searchAliases"; const EMPTY: SearchAlias[] = []; -// A site that ships no dictionary answers 404, and that is data: resolve empty. -// A TRANSPORT failure is not an answer and is rethrown, so react-query retries -// it rather than caching "this site has no aliases" for the session (the query -// below has staleTime: Infinity, so a swallowed blip would be permanent). +// ANY status the archive itself returned resolves empty — a 404 because the +// site ships no dictionary, but a 500 or a 403 the same way. That is the exact +// behaviour of the `if (!r.ok) return []` this replaced, kept deliberately: +// alias suggestions are additive, so a server that answers badly should cost +// the chip, not the search. +// +// A TRANSPORT failure is different and is rethrown, because it is not an answer +// at all. react-query then retries it rather than caching "this site has no +// aliases" for the session — the query below has staleTime: Infinity, so a +// swallowed blip would be permanent. export async function fetchAliases(origin = ""): Promise<SearchAlias[]> { try { return coerceAliasConfig(await readerFor(origin).readAliasConfig()).aliases; diff --git a/common/lib/archive/readers.ts b/common/lib/archive/readers.ts @@ -21,6 +21,27 @@ import { RemoteSource, type ChannelRef } from "./reader"; +// A BROWSER'S page-cache budget, which is not a server's. +// +// RemoteSource defaults to 48 MB (pageCacheBudgetBytes) and holds TWO page +// caches — transcripts and subs — so an origin costs 96 MB. That is a sane +// ceiling for one long-lived MCP process reading one corpus. It is not one for +// a tab, and it is emphatically not one for a hub page, which holds a reader +// per member site with no shared ceiling and no way for a browser to turn the +// env knob down. +// +// 8 MB, so an origin is 16 MB and five federated members are 80 MB rather than +// 480 MB. The reason it can be this small without costing reads: the viewer's +// caches memoise every RECORD they have ever seen (transcriptCache.resolved, +// plus IndexedDB), so an evicted page is only re-fetched for a video nobody has +// opened yet — the case that was going to be a fetch anyway. PageCache's +// MIN_CACHED_PAGES floor still keeps two entries even when one page of a +// VOD-sized corpus exceeds the whole budget on its own. +// +// The MCP path does NOT come through here: mcp/src/source.ts constructs +// RemoteSource directly and keeps the 48 MB default, so no bench counter moves. +const BROWSER_PAGE_CACHE_BYTES = 8 * 1024 * 1024; + const byOrigin = new Map<string, RemoteSource>(); // The reader for an origin, created on first use and kept for the life of the @@ -29,7 +50,7 @@ const byOrigin = new Map<string, RemoteSource>(); export function readerFor(origin = ""): RemoteSource { let reader = byOrigin.get(origin); if (reader === undefined) { - reader = new RemoteSource(origin); + reader = new RemoteSource(origin, BROWSER_PAGE_CACHE_BYTES); byOrigin.set(origin, reader); } return reader;