Docs/Skills and code/src/
src/analysis/channel-queues.js
import { config } from "../../config.js";
import { buildSharedChannelEvidence, normalizeQualification } from "./channel-evidence.js";
export const QUEUES = [
{ key: "learn_from", label: "Best channels to learn from", purpose: "Ecosystem-relevant channels with a specific, inspectable editorial approach and repeatable evidence worth learning from." },
{ key: "breaking_out", label: "Static growth potential", purpose: "Ecosystem-relevant channels whose captured catalogue shows robust, repeatable performance relative to size; not a claim of current acceleration." },
{ key: "durable_exemplars", label: "Durable exemplars", purpose: "Ecosystem-relevant channels with a substantial body of work, longevity and repeated performance rather than scale alone." },
{ key: "unexplored_niches", label: "Unexplored niches", purpose: "Ecosystem-relevant topics or approaches that appear underrepresented and merit investigation, supported by topic evidence rather than missing data alone." },
{ key: "reference_inspiration", label: "Reference / inspiration", purpose: "Explicit human reference sources and qualified sources with useful ecosystem knowledge, topics or creative evidence." }
];
const clamp = (value, min = 0, max = 100) => Math.max(min, Math.min(max, value));
const round = (value, digits = 2) => Number.isFinite(value) ? Number(value.toFixed(digits)) : null;
const present = value => value !== null && value !== undefined && value !== "" && Number.isFinite(Number(value));
const numeric = value => present(value) ? Number(value) : null;
const logScore = (value, low, high) => {
if (!present(value) || Number(value) < 0) return null;
if (Number(value) <= low) return 0;
if (Number(value) >= high) return 100;
return clamp(100 * Math.log(Number(value) / low) / Math.log(high / low));
};
function mean(values) {
const valid = values.filter(Number.isFinite);
return valid.length ? valid.reduce((sum, value) => sum + value, 0) / valid.length : null;
}
function median(values) {
const sorted = values.filter(Number.isFinite).sort((a, b) => a - b);
if (!sorted.length) return null;
const mid = Math.floor(sorted.length / 2);
return sorted.length % 2 ? sorted[mid] : (sorted[mid - 1] + sorted[mid]) / 2;
}
function percentile(values, p) {
const sorted = values.filter(Number.isFinite).sort((a, b) => a - b);
return sorted.length ? sorted[Math.min(sorted.length - 1, Math.ceil(sorted.length * p) - 1)] : null;
}
function weighted(parts) {
const configured = parts.filter(part => Number.isFinite(part.weight) && part.weight > 0);
const totalWeight = configured.reduce((sum, part) => sum + part.weight, 0);
const available = configured.filter(part => Number.isFinite(part.value));
const availableWeight = available.reduce((sum, part) => sum + part.weight, 0);
if (!totalWeight || !availableWeight) {
return { score: null, rawAvailableScore: null, coverage: 0, availableWeightPercent: 0, components: configured.map(part => ({
name: part.name, score: null, weight: part.weight, coverage: 0, missing: true, evidence: part.evidence ?? null
})) };
}
// Missing components must not silently disappear from the denominator. First
// compute the mean of observed components, then shrink it toward a neutral 50
// in proportion to how much of the configured component weight is actually
// present. This is deliberately not a zero-fill: absent evidence is still null.
const rawAvailableScore = available.reduce((sum, part) => sum + part.value * part.weight, 0) / availableWeight;
const availableWeightPercent = availableWeight / totalWeight * 100;
const score = 50 + (rawAvailableScore - 50) * (availableWeight / totalWeight);
const coverage = configured.reduce((sum, part) => sum + (Number.isFinite(part.value) ? clamp(part.coverage ?? 100) : 0) * part.weight, 0) / totalWeight;
return {
score: round(clamp(score)),
rawAvailableScore: round(rawAvailableScore),
coverage: round(coverage),
availableWeightPercent: round(availableWeightPercent),
components: configured.map(part => ({
name: part.name, score: Number.isFinite(part.value) ? round(part.value) : null,
weight: part.weight, coverage: Number.isFinite(part.value) ? round(clamp(part.coverage ?? 100)) : 0,
missing: !Number.isFinite(part.value), evidence: part.evidence ?? null
}))
};
}
function makeRating(queueKey, data = {}) {
const score = Number.isFinite(data.score) ? round(clamp(data.score)) : null;
const components = data.components ?? [];
const missingComponents = components.filter(component => component.missing).map(component => String(component.name ?? "component").toLowerCase().replace(/[^a-z0-9]+/g, "_"));
const uncertainty = [...(data.uncertainty ?? [])];
const reasonCodes = [...(data.reasonCodes ?? [])];
if (missingComponents.length) {
uncertainty.push("one_or_more_scoring_components_missing");
reasonCodes.push("score_shrunk_for_missing_components");
for (const component of missingComponents) reasonCodes.push(`missing_component_${component}`);
}
if (Number.isFinite(data.coverage) && data.coverage < config.queueScoring.minimumCoverageForSupported) {
uncertainty.push("scoring_evidence_coverage_below_supported_threshold");
}
return {
queue_key: queueKey, score,
confidence: round(clamp(data.confidence ?? 0)), coverage: round(clamp(data.coverage ?? 0)),
sample_size: Math.max(0, Math.round(data.sampleSize ?? 0)),
status: data.status ?? (score == null ? "insufficient_evidence" : "provisional"),
rank: null, eligibility: data.eligibility ?? "qualification_pending",
qualification_classification: data.qualification?.classification ?? "unknown",
qualification_confidence: round((data.qualification?.confidence ?? 0) * 100),
uncertainty: [...new Set(uncertainty)],
reason_codes: [...new Set(reasonCodes)],
evidence_refs: [...new Set(data.evidenceRefs ?? [])].slice(0, 20),
rationale: data.rationale ?? "", components, evidence: data.evidence ?? {}
};
}
function normalizeSeedKey(value) {
return String(value ?? "").trim().replace(/^@/, "").toLowerCase().replace(/[^a-z0-9]/g, "");
}
function findSeed(channel, seeds) {
const candidates = [channel.handle, channel.name, channel.channel_url?.split("/").filter(Boolean).at(-1)].filter(Boolean).map(normalizeSeedKey);
return seeds.find(seed => [seed.handle, seed.channel_handle, seed.name, seed.channel_url].filter(Boolean)
.some(value => candidates.includes(normalizeSeedKey(String(value).split("/").filter(Boolean).at(-1) ?? value)))) ?? null;
}
function asTag(value) {
return String(typeof value === "string" ? value : value?.name ?? value?.tag ?? "").trim().toLowerCase().replace(/\s+/g, " ");
}
function topicRarity(features, qualifiedUrls) {
const frequency = new Map();
for (const [url, feature] of features) {
if (!qualifiedUrls.has(url)) continue;
for (const tag of new Set(feature.topic_tags.map(asTag).filter(Boolean))) frequency.set(tag, (frequency.get(tag) ?? 0) + 1);
}
const rarity = new Map();
for (const [url, feature] of features) {
const tags = [...new Set(feature.topic_tags.map(asTag).filter(Boolean))];
const values = tags.map(tag => 100 / Math.sqrt(frequency.get(tag) ?? 1));
rarity.set(url, values.length ? mean(values.map(v => clamp(v))) : null);
}
return { frequency, rarity };
}
function qualificationFor(channel) {
if (channel.qualification_assessment) {
return normalizeQualification(channel.qualification_assessment, { source: "llm" });
}
return normalizeQualification({
classification: channel.ecosystem_classification,
confidence: channel.ecosystem_classification_confidence,
rationale: channel.ecosystem_reason,
source: channel.ecosystem_classification_source ?? "rule_based"
}, { source: channel.ecosystem_classification_source ?? "rule_based" });
}
function makeEligibility(queueKey, qualification, seed) {
if (queueKey === "reference_inspiration" && seed) {
if (qualification.classification === "irrelevant") return "explicit_reference_conflict";
if (qualification.eligibility === "qualification_pending") return "explicit_reference_needs_qualification";
return "explicit_reference";
}
if (qualification.classification === "irrelevant") return "ineligible_irrelevant";
if (qualification.eligibility === "eligible_core") return "eligible_core";
if (qualification.eligibility === "eligible_adjacent") return "eligible_adjacent";
return "qualification_pending";
}
function qualificationUncertainty(q) {
const flags = [...q.uncertainty_flags];
if (q.source !== "llm") flags.push("llm_qualification_not_available_for_current_input");
if (q.confidence < config.qualification.minimumConfidenceToQualify) flags.push("qualification_confidence_below_threshold");
if (q.classification === "unknown") flags.push("ecosystem_classification_unknown");
return [...new Set(flags)];
}
function sampleReliability(count, full = 15) { return clamp(count / full, 0, 1); }
function qualificationBase(channel, feature) {
return feature.qualification;
}
/**
* Evidence-led, queue-specific rankings. Eligibility is evaluated before a score is allowed to rank.
* Static growth uses captured video fields only and never reads metric snapshots.
*/
export function scoreChannelQueues({ channels, referenceSeeds = [], now = new Date() }) {
const featureMap = new Map(channels.map(channel => [channel.channel_url, buildSharedChannelEvidence(channel, now)]));
const qualifiedUrls = new Set([...featureMap].filter(([, feature]) => feature.qualification.eligible).map(([url]) => url));
const topicStats = topicRarity(featureMap, qualifiedUrls);
const output = [];
for (const channel of channels) {
const url = channel.channel_url;
const feature = featureMap.get(url);
const q = qualificationBase(channel, feature);
const seed = findSeed({ ...channel, handle: channel.handle ?? channel.channel_id }, referenceSeeds);
const eligibility = Object.fromEntries(QUEUES.map(queue => [queue.key, makeEligibility(queue.key, q, seed)]));
const videos = feature.videos;
const withViews = videos.filter(video => video.views != null);
const n = withViews.length;
const medianViews = feature.median_video_views;
const p90Views = feature.p90_video_views;
const dated = withViews.filter(video => video.age_days != null && video.age_days >= config.queueScoring.breakout.minimumAgeDaysForAgeAdjustedViews);
const ageAdjustedScore = logScore(feature.median_views_per_day_proxy, 1, 10000);
const absoluteReachScore = logScore(medianViews, 100, 1000000);
const priorSubs = config.queueScoring.breakout.smallChannelSubscriberPrior;
const relativeReachScore = logScore(feature.smoothed_views_per_subscriber, 0.005, 3);
const repeatabilityScore = feature.repeatability_percent == null ? null : clamp(feature.repeatability_percent);
const consistencyScore = feature.median_to_p90_percent == null ? null : clamp(feature.median_to_p90_percent);
const sampleConfidence = sampleReliability(n, config.queueScoring.breakout.fullSampleConfidenceVideos);
const viewCoverage = channel.videos?.length ? n / channel.videos.length * 100 : 0;
const metadataCount = [channel.channel_id, channel.description, channel.subscriber_count, channel.video_count, channel.total_view_count, channel.joined_date, channel.handle, channel.metadata_source].filter(v => v !== null && v !== undefined && v !== "").length;
const metadataCoverage = metadataCount / 8 * 100;
const uncertaintyBase = qualificationUncertainty(q);
if (n < 10) uncertaintyBase.push("thin_video_sample");
if (dated.length < 5) uncertaintyBase.push("limited_age_adjusted_sample");
if (String(channel.subscriber_count_precision ?? "").toLowerCase().includes("abbreviated")) uncertaintyBase.push("subscriber_count_abbreviated");
if (feature.estimated_date_count > 0) uncertaintyBase.push("some_publication_dates_estimated");
const allowed = queueKey => eligibility[queueKey] === "eligible_core" || eligibility[queueKey] === "eligible_adjacent"
|| (queueKey === "reference_inspiration" && eligibility[queueKey] === "explicit_reference");
const blockedRating = (queueKey, why) => makeRating(queueKey, {
score: null, confidence: q.confidence * 100, coverage: 0, sampleSize: n,
status: eligibility[queueKey] === "ineligible_irrelevant" ? "ineligible" : "needs_qualification",
eligibility: eligibility[queueKey], qualification: q, uncertainty: [...uncertaintyBase, why],
reasonCodes: [q.classification === "irrelevant" ? "ecosystem_irrelevant" : q.classification === "core" ? "ecosystem_core_below_confidence_threshold" : q.classification === "adjacent" ? "ecosystem_adjacent_below_confidence_threshold" : "ecosystem_unknown", why],
evidenceRefs: [url], rationale: q.classification === "irrelevant"
? "The qualification evidence indicates that this channel is outside the target ecosystem; it is not ranked for this queue."
: "The channel needs a sufficiently confident ecosystem qualification before it can compete in this ecosystem-focused queue.",
evidence: { qualification: q, eligibility: eligibility[queueKey], required_action: "run_or_review_channel_qualification" }
});
// Queue 1: teachability and inspectable editorial approach, not popularity alone.
if (!allowed("learn_from")) output.push({ channel_url: url, queue: seed && eligibility.learn_from === "qualification_pending" ? blockedRating("learn_from", "qualification_required") : blockedRating("learn_from", "not_eligible_for_ecosystem_learning_queue") });
else {
const focusSpecificity = numeric(q.focus_specificity);
const rawPerformance = absoluteReachScore == null || repeatabilityScore == null
? null : 0.55 * absoluteReachScore + 0.45 * repeatabilityScore;
const learnParts = [
{ name: "editorial_specialization_from_raw_metadata", value: focusSpecificity, weight: 0.28, coverage: focusSpecificity != null ? 100 : 0, evidence: focusSpecificity != null ? `Qualification analysis of channel metadata and sampled titles: focus-specificity ${focusSpecificity}/100` : "Raw-metadata qualification did not provide focus-specificity" },
{ name: "repeatable_performance_from_captured_videos", value: rawPerformance, weight: 0.24, coverage: n ? Math.min(100, n / 10 * 100) : 0, evidence: `median views ${medianViews ?? "unknown"}; ${feature.repeatable_count}/${n} sampled videos above the repeatability floor` },
{ name: "absolute_audience_reach", value: absoluteReachScore, weight: 0.16, coverage: n ? viewCoverage : 0, evidence: `median video views ${medianViews ?? "unknown"}` },
{ name: "raw_evidence_coverage", value: clamp((viewCoverage * 0.55) + metadataCoverage * 0.45), weight: 0.16, coverage: metadataCoverage, evidence: `${n}/${channel.videos?.length ?? 0} linked videos have view counts; metadata ${round(metadataCoverage)}%` }
];
const score = weighted(learnParts);
const sampleShrink = 0.65 + 0.35 * sampleReliability(n, 15);
const finalScore = score.score == null ? null : 50 + (score.score - 50) * sampleShrink;
const confidence = clamp(q.confidence * 45 + Math.min(1, n / 20) * 30 + Math.min(10, metadataCoverage / 10));
const evidenceEnough = (focusSpecificity != null || rawPerformance != null || absoluteReachScore != null) && n >= 3;
output.push({ channel_url: url, queue: makeRating("learn_from", {
score: evidenceEnough ? finalScore : null, confidence, coverage: score.coverage, sampleSize: n,
status: !evidenceEnough ? "insufficient_evidence" : (confidence >= 70 && n >= 10 && score.coverage >= config.queueScoring.minimumCoverageForSupported && q.confidence >= config.queueScoring.ranking.minimumConfidenceForSupported ? "supported" : "provisional"),
eligibility: eligibility.learn_from, qualification: q, uncertainty: [...uncertaintyBase, ...(n < 10 ? ["learning_sample_is_thin"] : [])],
reasonCodes: [q.classification === "core" ? "ecosystem_core" : "ecosystem_adjacent", focusSpecificity != null ? "raw_metadata_focus_signal_available" : null, rawPerformance != null ? "captured_video_performance_signal_available" : null, n < 10 ? "thin_video_sample" : null].filter(Boolean),
evidenceRefs: [url, ...(channel.top_video_ids ?? []).slice(0, 5)],
rationale: evidenceEnough ? `Queue-specific learning score uses qualification derived from raw channel metadata and captured-video performance; channel-profile/vocabulary outputs are excluded. Eligibility: ${eligibility.learn_from}. This is a research priority, not a universal quality verdict.` : "Insufficient raw metadata or captured-video evidence to recommend this channel as a learning exemplar.",
components: score.components, evidence: { method: "queue_learn_from_v5_raw_metadata_only", qualification: q, eligibility: eligibility.learn_from, median_video_views: medianViews, repeatable_video_count: feature.repeatable_count, video_sample_size: n, metadata_coverage_percent: round(metadataCoverage), unadjusted_available_component_score: score.rawAvailableScore, available_component_weight_percent: score.availableWeightPercent }
}) });
}
// Queue 2: robust static growth potential; subscriber ratios are smoothed and absolute reach matters.
if (!allowed("breaking_out")) output.push({ channel_url: url, queue: blockedRating("breaking_out", "qualification_required_for_growth_ranking") });
else {
const growthParts = [
{ name: "absolute_median_video_reach", value: absoluteReachScore, weight: 0.25, coverage: viewCoverage, evidence: `median=${round(medianViews, 0)} views across ${n} videos` },
{ name: "smoothed_reach_relative_to_channel_size", value: relativeReachScore, weight: 0.20, coverage: present(channel.subscriber_count) ? 100 : 0, evidence: `median views / (subscribers + ${priorSubs}) = ${round(feature.smoothed_views_per_subscriber, 5)}` },
{ name: "lifetime_views_per_day_proxy", value: ageAdjustedScore, weight: 0.20, coverage: Math.min(100, dated.length / 10 * 100), evidence: `median lifetime views/day across ${dated.length} videos aged at least ${config.queueScoring.breakout.minimumAgeDaysForAgeAdjustedViews} days` },
{ name: "repeatability_above_minimum_reach", value: repeatabilityScore, weight: 0.25, coverage: Math.min(100, n / 15 * 100), evidence: `${feature.repeatable_count}/${n} videos reached at least max(1,000, 25% of subscribers)` },
{ name: "median_to_p90_consistency", value: consistencyScore, weight: 0.10, coverage: n >= 3 ? 100 : 0, evidence: `median/p90 view count=${round(feature.median_to_p90_percent, 1)}%` }
];
const growth = weighted(growthParts);
const minVideos = config.queueScoring.breakout.minVideosForScore;
const enough = n >= minVideos && growth.score != null && (absoluteReachScore != null || repeatabilityScore != null);
const reliability = sampleReliability(n, config.queueScoring.breakout.fullSampleConfidenceVideos);
const finalScore = enough ? clamp(50 + (growth.score - 50) * (0.35 + 0.65 * reliability)) : null;
const confidence = enough ? clamp(q.confidence * 40 + reliability * 35 + Math.min(1, dated.length / 10) * 15 + (metadataCoverage / 100) * 10 - (feature.estimated_date_count > 0 ? 5 : 0)) : 0;
const topVideos = [...withViews].sort((a, b) => (b.views_per_day ?? -1) - (a.views_per_day ?? -1) || b.views - a.views).slice(0, 8);
output.push({ channel_url: url, queue: makeRating("breaking_out", {
score: finalScore, confidence, coverage: growth.coverage, sampleSize: n,
status: !enough ? "insufficient_evidence" : (confidence >= 70 && n >= 15 && q.confidence >= config.queueScoring.ranking.minimumConfidenceForSupported && growth.coverage >= config.queueScoring.minimumCoverageForSupported && relativeReachScore != null && ageAdjustedScore != null && dated.length >= 5 ? "supported" : "provisional"),
eligibility: eligibility.breaking_out, qualification: q,
uncertainty: [...uncertaintyBase, ...(n < 10 ? ["small_sample_shrunk_toward_neutral"] : []), ...(String(channel.subscriber_count_precision ?? "").toLowerCase().includes("abbreviated") ? ["subscriber_count_precision_is_abbreviated"] : [])],
reasonCodes: ["static_growth_potential_proxy", "no_snapshot_dependency", "smoothed_small_channel_denominator", "repeatability_and_absolute_reach_required", q.classification === "core" ? "ecosystem_core" : "ecosystem_adjacent", n < 10 ? "thin_video_sample" : null, dated.length < 5 ? "limited_age_adjusted_sample" : null].filter(Boolean),
evidenceRefs: [url, ...topVideos.slice(0, 5).map(v => v.video_id ? `https://www.youtube.com/watch?v=${v.video_id}` : null).filter(Boolean)],
rationale: enough ? `Static growth-potential score from smoothed channel-relative reach, absolute median views, repeatability above a 1,000-view floor, age-adjusted lifetime views/day and consistency. Sample size ${n}; ${dated.length} videos support the age-adjusted proxy. No snapshots are read; this does not prove current acceleration.` : `At least ${minVideos} videos with captured view counts and usable performance evidence are required; ${n} are available.`,
components: growth.components,
evidence: { method: "static_growth_potential_v2_evidence_led", snapshot_dependent: false, qualification: q, eligibility: eligibility.breaking_out,
input_video_count: (channel.videos ?? []).length, video_count_with_views: n, dated_video_count_with_views: dated.length,
median_video_views: round(medianViews, 0), p90_video_views: round(p90Views, 0), subscriber_count: numeric(channel.subscriber_count),
subscriber_count_precision: channel.subscriber_count_precision ?? "unknown", smoothed_views_per_subscriber: round(feature.smoothed_views_per_subscriber, 6),
median_lifetime_views_per_day_proxy: round(feature.median_views_per_day_proxy, 2), repeatable_video_count: feature.repeatable_count,
repeatability_threshold_views: Math.max(1000, numeric(channel.subscriber_count) == null ? 0 : numeric(channel.subscriber_count) * 0.25),
repeatability_percent: round(feature.repeatability_percent, 2), median_to_p90_percent: round(feature.median_to_p90_percent, 2),
channel_age_years: round(feature.channel_age_years, 2), unadjusted_available_component_score: growth.rawAvailableScore,
available_component_weight_percent: growth.availableWeightPercent, videos_used: topVideos.map(v => ({ video_id: v.video_id, title: v.title, views: v.views, published_at: v.date?.toISOString().slice(0, 10) ?? null, age_days: round(v.age_days, 1), lifetime_views_per_day_proxy: round(v.views_per_day, 2), date_precision: v.published_at_precision })) }
}) });
}
// Queue 3: durable body of work, not age/scale alone.
if (!allowed("durable_exemplars")) output.push({ channel_url: url, queue: blockedRating("durable_exemplars", "qualification_required_for_durable_ranking") });
else {
const age = feature.channel_age_years;
const longevityScore = age == null ? null : clamp(age / 15 * 100);
const catalogueScore = logScore(channel.video_count, 10, 5000);
const lifetimeScale = logScore(channel.total_view_count, 10000, 1000000000);
const repeatability = feature.repeatability_percent;
const datedYears = withViews.map(v => v.date?.getUTCFullYear()).filter(Number.isFinite);
const yearSpan = datedYears.length >= 2 ? Math.max(...datedYears) - Math.min(...datedYears) : null;
const spanScore = yearSpan == null ? null : clamp(yearSpan / 10 * 100);
const durableParts = [
{ name: "longevity", value: longevityScore, weight: 0.25, coverage: age == null ? 0 : 100, evidence: `channel age ${round(age, 2) ?? "unknown"} years` },
{ name: "declared_catalogue_depth", value: catalogueScore, weight: 0.20, coverage: present(channel.video_count) ? 100 : 0, evidence: `declared uploads ${channel.video_count ?? "unknown"}` },
{ name: "repeatable_video_performance", value: repeatability, weight: 0.25, coverage: Math.min(100, n / 15 * 100), evidence: `${feature.repeatable_count}/${n} sampled videos above the minimum reach floor` },
{ name: "median_video_reach", value: absoluteReachScore, weight: 0.15, coverage: viewCoverage, evidence: `median views ${medianViews ?? "unknown"}` },
{ name: "observed_time_span", value: spanScore, weight: 0.10, coverage: datedYears.length ? 100 : 0, evidence: yearSpan == null ? "publication-date span unavailable" : `${yearSpan} years between sampled publication dates` },
{ name: "lifetime_scale_context", value: lifetimeScale, weight: 0.05, coverage: present(channel.total_view_count) ? 100 : 0, evidence: `total views ${channel.total_view_count ?? "unknown"}; low weight so scale cannot dominate` }
];
const durable = weighted(durableParts);
const enough = n >= 3 && (age != null || catalogueScore != null) && durable.score != null;
const reliability = sampleReliability(n, 20);
const score = enough ? clamp(50 + (durable.score - 50) * (0.45 + 0.55 * reliability)) : null;
const confidence = enough ? clamp(q.confidence * 45 + reliability * 30 + (age != null ? 10 : 0) + (catalogueScore != null ? 10 : 0) + (spanScore != null ? 5 : 0)) : 0;
output.push({ channel_url: url, queue: makeRating("durable_exemplars", {
score, confidence, coverage: durable.coverage, sampleSize: n,
status: !enough ? "insufficient_evidence" : (confidence >= 70 && n >= 10 && yearSpan != null && durable.coverage >= config.queueScoring.minimumCoverageForSupported && q.confidence >= config.queueScoring.ranking.minimumConfidenceForSupported ? "supported" : "provisional"),
eligibility: eligibility.durable_exemplars, qualification: q,
uncertainty: [...uncertaintyBase, ...(n < 10 ? ["durability_sample_is_thin"] : []), ...(yearSpan == null ? ["temporal_span_not_established"] : [])],
reasonCodes: ["durability_requires_repeatability", age != null ? "channel_age_known" : null, catalogueScore != null ? "catalogue_size_known" : null, n < 10 ? "thin_video_sample" : null].filter(Boolean),
evidenceRefs: [url],
rationale: enough ? "Durability combines longevity and catalogue depth with repeated performance and sampled temporal spread. Lifetime views have deliberately low weight; a large or old channel is not automatically an exemplar." : "A durability score needs qualification, at least three view-bearing videos, and at least one reliable longevity/catalogue signal.",
components: durable.components, evidence: { method: "durable_exemplar_v5_raw_metadata_only", qualification: q, eligibility: eligibility.durable_exemplars, channel_age_years: round(age, 2), declared_video_count: channel.video_count ?? null, total_view_count: channel.total_view_count ?? null, video_sample_size: n, observed_publication_year_span: yearSpan, unadjusted_available_component_score: durable.rawAvailableScore, available_component_weight_percent: durable.availableWeightPercent }
}) });
}
// Queue 4: niche opportunity needs topic evidence; data gaps are actions, not novelty.
if (!allowed("unexplored_niches")) output.push({ channel_url: url, queue: blockedRating("unexplored_niches", "qualification_required_for_niche_opportunity") });
else {
const rarity = topicStats.rarity.get(url);
const focusSpecificity = numeric(q.focus_specificity);
const tags = [...new Set(q.topic_tags.map(asTag).filter(Boolean))];
const nicheEvidence = tags.length > 0 || focusSpecificity != null;
const topicRarityScore = tags.length ? rarity : null;
const audienceSignal = absoluteReachScore;
const nicheParts = [
{ name: "raw_metadata_topic_rarity", value: topicRarityScore, weight: 0.45, coverage: topicRarityScore == null ? 0 : 100, evidence: `${tags.length} qualification topic tags; corpus tag rarity ${round(rarity) ?? "unavailable"}` },
{ name: "raw_metadata_focus_specificity", value: focusSpecificity, weight: 0.30, coverage: focusSpecificity == null ? 0 : 100, evidence: q.focus_summary ?? "Qualification focus-specificity unavailable" },
{ name: "captured_audience_interest_context", value: audienceSignal, weight: 0.25, coverage: audienceSignal == null ? 0 : viewCoverage, evidence: `median views ${medianViews ?? "unknown"}; audience signal is context, not proof of demand` }
];
const niche = weighted(nicheParts);
const enough = nicheEvidence && n >= 3 && niche.score != null;
const confidence = enough ? clamp(q.confidence * 50 + Math.min(1, n / 12) * 25 + (tags.length ? 15 : 0)) : 0;
output.push({ channel_url: url, queue: makeRating("unexplored_niches", {
score: enough ? niche.score : null, confidence, coverage: niche.coverage, sampleSize: n,
status: !enough ? "insufficient_evidence" : (confidence >= 70 && n >= 8 && niche.coverage >= config.queueScoring.minimumCoverageForSupported && q.confidence >= config.queueScoring.ranking.minimumConfidenceForSupported && tags.length >= 2 && audienceSignal != null ? "supported" : "provisional"),
eligibility: eligibility.unexplored_niches, qualification: q,
uncertainty: [...uncertaintyBase, ...(tags.length < 2 ? ["niche_novelty_not_independently_supported"] : []), ...(n < 8 ? ["niche_evidence_sample_is_thin"] : [])],
reasonCodes: ["niche_rarity_is_not_demand", tags.length ? "qualification_topic_tags_available" : null, !enough ? "more_topic_evidence_required" : null].filter(Boolean),
evidenceRefs: [url, ...(channel.top_video_ids ?? []).slice(0, 5)],
rationale: enough ? "Niche opportunity combines corpus-relative topic rarity, qualification focus-specificity from raw channel/video metadata, and captured audience-interest context. Channel profiles, vocabulary, embeddings and prior priority scores are excluded." : "The channel is qualified, but current raw metadata/topic evidence is too thin to assert a niche opportunity. Collect representative titles or refresh qualification evidence.",
components: niche.components, evidence: { method: "unexplored_niche_v5_raw_metadata_only", qualification: q, eligibility: eligibility.unexplored_niches, topic_tags: tags, topic_tag_frequency: Object.fromEntries(tags.map(tag => [tag, topicStats.frequency.get(tag) ?? 0])), corpus_topic_rarity: round(rarity), topic_evidence_count: tags.length, video_sample_size: n, unadjusted_available_component_score: niche.rawAvailableScore, available_component_weight_percent: niche.availableWeightPercent, follow_up_action: enough ? "inspect niche and validate audience demand" : "collect evidence / qualify channel" }
}) });
}
// Queue 5: qualification gates inferred candidates. Explicit seeds remain visible,
// but an irrelevant or unqualified seed is flagged and cannot masquerade as a ranked exemplar.
const refEligibility = eligibility.reference_inspiration;
if (seed && refEligibility !== "explicit_reference") {
const conflict = refEligibility === "explicit_reference_conflict";
output.push({ channel_url: url, queue: makeRating("reference_inspiration", {
score: null, confidence: q.confidence * 100, coverage: 0, sampleSize: n,
status: conflict ? "explicit_reference_conflict" : "explicit_reference_needs_qualification",
eligibility: refEligibility, qualification: q,
uncertainty: [...uncertaintyBase, conflict ? "human_seed_conflicts_with_ecosystem_qualification" : "human_seed_requires_fresh_qualification"],
reasonCodes: ["explicit_reference_seed", "seed_membership_separate_from_score", conflict ? "seed_ecosystem_conflict" : "seed_needs_qualification"],
evidenceRefs: [url],
rationale: conflict
? `This channel is an explicit human reference seed, but current qualification marks it irrelevant to the configured ecosystem (${q.rationale ?? "no rationale recorded"}). It is preserved for review but is not given an inferred inspiration rank.`
: "This explicit human reference seed is preserved, but its current ecosystem qualification is missing, stale, or below the confidence threshold. Re-qualify or review it before ranking.",
components: [], evidence: { method: "reference_inspiration_v3", explicit_reference_seed: true, seed_name: seed.name ?? seed.handle ?? null, qualification: q, eligibility: refEligibility, required_action: conflict ? "review_seed_or_ecosystem_boundary" : "refresh_qualification" }
}) });
continue;
}
if (!allowed("reference_inspiration")) {
output.push({ channel_url: url, queue: blockedRating("reference_inspiration", "qualified_ecosystem_membership_required_for_inferred_reference") });
continue;
}
const titleEvidenceScore = n ? clamp(100 * (1 - Math.exp(-n / 12))) : null;
const metadataEvidenceScore = metadataCoverage > 0 ? metadataCoverage : null;
// Topic evidence comes only from qualification analysis of raw metadata and
// captured titles. Stage 03 profiles, vocabulary, concepts and patterns are excluded.
const topicEvidenceCount = q.topic_tags.length;
const topicEvidenceScore = topicEvidenceCount > 0
? clamp(8 * Math.log2(1 + topicEvidenceCount) + (q.focus_specificity ?? 0) * 0.15)
: null;
const relevanceBase = q.relevance_score ?? (q.classification === "core" ? 85 : q.classification === "adjacent" ? 65 : null);
const relevanceEvidenceScore = relevanceBase == null ? null : clamp(relevanceBase * q.confidence);
const refParts = [
{ name: "ecosystem_relevance_confidence", value: relevanceEvidenceScore, weight: 0.35, coverage: relevanceEvidenceScore == null ? 0 : q.confidence * 100, evidence: `${q.classification}; reported qualification confidence ${round(q.confidence * 100)}%; relevance score ${q.relevance_score ?? "fallback class prior"}` },
{ name: "raw_metadata_topic_evidence", value: topicEvidenceScore, weight: 0.30, coverage: topicEvidenceScore == null ? 0 : 100, evidence: `${q.topic_tags.length} qualification topic tags; logarithmic saturation` },
{ name: "representative_catalogue_evidence", value: titleEvidenceScore, weight: 0.20, coverage: n ? viewCoverage : 0, evidence: `${n} videos with views in current sample` },
{ name: "metadata_completeness", value: metadataEvidenceScore, weight: 0.15, coverage: metadataCoverage, evidence: `${round(metadataCoverage)}% of core channel metadata fields present` }
];
const reference = weighted(refParts);
const hasReferenceEvidence = reference.score != null && (n > 0 || q.topic_tags.length > 0 || seed);
const refScore = hasReferenceEvidence ? reference.score : null;
const refConfidence = clamp(q.confidence * 45 + Math.min(1, n / 15) * 25 + (topicEvidenceScore != null ? 20 : 0) + metadataCoverage / 10);
const referenceSupported = refConfidence >= 70 && reference.coverage >= config.queueScoring.minimumCoverageForSupported
&& q.confidence >= config.queueScoring.ranking.minimumConfidenceForSupported;
const referenceStatus = seed
? (refScore == null ? "explicit_reference_needs_evidence" : (referenceSupported ? "explicit_reference" : "explicit_reference_provisional"))
: (refScore == null ? "insufficient_evidence" : (referenceSupported ? "supported" : "provisional"));
output.push({ channel_url: url, queue: makeRating("reference_inspiration", {
score: refScore, confidence: refScore == null ? 0 : refConfidence, coverage: reference.coverage, sampleSize: n + topicEvidenceCount,
status: referenceStatus,
eligibility: refEligibility, qualification: q,
uncertainty: [...uncertaintyBase, ...(seed ? [] : ["inferred_reference_candidate_not_human_seed"]), ...(refScore == null ? ["reference_usefulness_evidence_missing"] : []), ...(reference.coverage < config.queueScoring.minimumCoverageForSupported ? ["reference_evidence_coverage_low"] : [])],
reasonCodes: [seed ? "explicit_reference_seed" : "inferred_reference_candidate", seed ? "seed_membership_separate_from_score" : null, topicEvidenceScore != null ? "topic_evidence_available" : null, reference.coverage < config.queueScoring.minimumCoverageForSupported ? "low_reference_evidence_coverage" : null].filter(Boolean),
evidenceRefs: [url, ...(channel.top_video_ids ?? []).slice(0, 5)],
rationale: seed ? `Explicit human reference seed (${seed.name ?? seed.handle ?? "named seed"}). Seed membership is preserved separately from usefulness score; this score reflects qualification from raw metadata, captured-video catalogue evidence and metadata completeness.` : "Qualified inferred inspiration candidate scored on raw-metadata qualification, captured catalogue evidence and metadata completeness. Channel-profile/vocabulary outputs are excluded; human review is still required.",
components: reference.components, evidence: { method: "reference_inspiration_v5_raw_metadata_only", qualification: q, eligibility: refEligibility, explicit_reference_seed: Boolean(seed), seed_name: seed?.name ?? null, topic_tags: q.topic_tags, video_sample_size: n, raw_available_component_score: reference.rawAvailableScore, available_component_weight_percent: reference.availableWeightPercent }
}) });
}
// Only qualified rows with an actual score and a rankable status receive ranks.
// Seed membership never bypasses qualification or improves a score by itself.
const blockedStatuses = new Set(["ineligible", "needs_qualification", "insufficient_evidence", "explicit_reference_conflict", "explicit_reference_needs_qualification", "explicit_reference_needs_evidence"]);
const tier = rating => rating.qualification_classification === "core" ? 0 : rating.qualification_classification === "adjacent" ? 1 : 9;
for (const queue of QUEUES) {
const ranked = output.filter(row => {
if (row.queue.queue_key !== queue.key || row.queue.score == null || blockedStatuses.has(row.queue.status)) return false;
if (queue.key === "reference_inspiration") return ["eligible_core", "eligible_adjacent", "explicit_reference"].includes(row.queue.eligibility);
return ["eligible_core", "eligible_adjacent"].includes(row.queue.eligibility);
}).sort((a, b) => tier(a.queue) - tier(b.queue) || b.queue.score - a.queue.score || b.queue.confidence - a.queue.confidence || a.channel_url.localeCompare(b.channel_url));
ranked.forEach((row, index) => { row.queue.rank = index + 1; });
}
return { queues: QUEUES, ratings: output, scoring_version: config.queueScoring.version, diagnostics: {
qualificationSources: Object.fromEntries([...new Set(channels.map(c => c.qualification_assessment ? "llm" : (c.ecosystem_classification_source ?? "rule_based")))].map(source => [source, channels.filter(c => (c.qualification_assessment ? "llm" : (c.ecosystem_classification_source ?? "rule_based")) === source).length])),
eligibleCore: [...featureMap.values()].filter(f => f.qualification.eligibility === "eligible_core").length,
eligibleAdjacent: [...featureMap.values()].filter(f => f.qualification.eligibility === "eligible_adjacent").length,
qualificationPending: [...featureMap.values()].filter(f => f.qualification.eligibility === "qualification_pending").length,
irrelevant: [...featureMap.values()].filter(f => f.qualification.classification === "irrelevant").length
} };
}
Shown as it is in the repository at build time (2026-11-03); the home directory appears as <home>. If this page and the file differ, the file is right. Back to the catalogue.