import Link from "next/link";
import { formatBytes } from "yt-dlp-transcript-common/lib/format";
import {
STATION_DOT,
STATION_TEXT,
formatCount,
} from "yt-dlp-transcript-common/views/pipeline/tone";
import type { StageTone } from "yt-dlp-transcript-common/views/pipeline/stageStatus";
import type { CleanupSummary } from "../lib/loadCleanup";
// THE SIEVE. The cleanup sweep is a cascade of `continue`s — a video leaves at
// the FIRST gate it hits — so this is the shape the page takes: all the audio on
// disk enters at the top, each gate siphons off its share, and the remainder
// steps down the column to the reclaimable figure the hero already prints.
//
// The gates are NUMBERED because they genuinely are a sequence. The order IS the
// attribution rule, and it is the only thing stopping the five figures from
// double-counting each other.
//
// No new colours, no new type. The rail and its station dots are the transit
// vocabulary the channel page established (flow/tone.ts, which the two maps are
// imported from rather than copied — laneState.ts warns that a third copy would
// guarantee drift), and the bars use the same --chart-N tokens as the hero bar
// directly above.
type Gate = {
n: number;
label: string;
// What clears it. Split so the prescription can be a link where one exists.
clears: React.ReactNode;
bytes: number;
count: number;
// Bytes inside this gate that NOTHING queued will ever release.
neverClears?: number;
};
export function HoldSieve({ summary }: { summary: CleanupSummary }) {
const {
totalAudioBytes,
heldBytes,
heldCounts,
measuredReclaimBytes,
atRiskBytes,
staleSnapshotCount,
} = summary;
// Nothing measured at all: every figure would be a zero nobody computed.
if (totalAudioBytes <= 0) {
return (
—
{staleSnapshotCount > 0 ? (
<>
No report yet says what is holding this audio.{" "}
~{formatBytes(totalAudioBytes)}
~{formatBytes(measuredReclaimBytes)}
the upstream check may still refuse ~{formatBytes(atRiskBytes)} cached
as gone-from-source
{staleSnapshotCount} channel{staleSnapshotCount === 1 ? "" : "s"} not
in this measurement —
{steps.map(({ gate, remainder: left }) => (
{/* What survives all four — the number the page already leads with. */}
{gate.clears} {never > 0 && ( <> {" · "} ~{formatBytes(never)} will not clear on its own > )}
{children}
); } function RefreshLink() { return ( Refresh reports ); }