// Origin-qualified content identity for the federated hub. // // The whole search operates on a single string identity (`slug`, shaped // "channelSlug/videoId"). To federate content from multiple origins WITHOUT // threading (origin, slug) tuples through every call site, we keep one opaque // string id and qualify it with an origin prefix ONLY for cross-origin content. // // same-origin (single-site export, the built-in pool): "channelSlug/videoId" // cross-origin (a user-added external site): "https://x.com\tchannelSlug/videoId" // // The separator is a TAB — impossible in a URL origin and impossible in a slug // (channel dir names + video ids), so splitting is unambiguous. Crucially // makeId("", slug) === slug, so every single-site code path produces byte-for- // byte identical strings and its behavior (URL state, filter profiles, IDB // keys) is unchanged. const SEP = "\t"; export type OriginId = string; // Combine an origin ("" = same-origin) with a bare slug into an id. A bare slug // is returned unchanged for same-origin content. export function makeId(origin: string, slug: string): OriginId { return origin ? `${origin}${SEP}${slug}` : slug; } // Decode an id back into its origin ("" = same-origin) and bare slug. export function splitId(id: OriginId): { origin: string; slug: string } { const sep = id.indexOf(SEP); if (sep < 0) return { origin: "", slug: id }; return { origin: id.slice(0, sep), slug: id.slice(sep + 1) }; } // The base URL to prefix onto a root-relative resource path for a given origin: // "" for same-origin (paths stay root-relative, unchanged), else the origin. export function idBaseUrl(origin: string): string { return origin || ""; }