1,404 videos, 648 subscribers, not one over 1,000 views. It is a discovery problem.
A channel landed in my lap for a growth read: 1,404 uploads, 648 subscribers, and the owner's only dashboard was the phone app. The raw totals said nothing. Bucketing the views said everything:
0 views 158
1-9 640
10-49 176
50-99 77
100-499 258
500-999 95
1000+ 0
1,070 of 1,404 videos (76%) sit under 50 views. Not one crosses 1,000. When a channel cannot break 1,000 views after 1,400 tries, it is not a content problem first. It is a discovery problem. Content problems produce a spread: some videos land, some do not. This is a floor, not a spread.
The four comparisons that made it a diagnosis and not a guess
The thumbnail does not match the title. I compared the text on the thumbnail against the title for each of the last 13 videos. All 13 offered a different rhyme than the video. The click offer was wrong in every one of the thirteen I checked. No dashboard tells you this. You get it by reading the artwork and the title side by side.
The titles are ten fixed strings. <Rhyme> Compilation, repeated for 1,404 videos. Nothing for a search engine or a human to tell apart.
Cadence: 942 of 1,404 videos went up in the last 14 days. About 68 a day. The other 462 average 9 a day and cover only about 51 days. So there is barely any older history: this is a young channel that spent most of its short life uploading fast into a feed that was already flat. Mass-uploading does not compound. It dilutes.
One description, 1,404 times. The identical 2,031-character block on every video: a pasted list of rhyme names. No timestamps, no links, no call to action. Zero tags on every video.
An audit is not a report of totals. It is the smallest set of comparisons that makes the cause obvious: wins against losses, title against thumbnail, upload rate against audience.
The three moves the data implies
- Cut the upload rate. Stop at a rate you can title, describe and thumbnail individually. 68 a day guarantees every video is anonymous.
- Kill the ten fixed titles. One title per video, written for a human search phrase, not a rhyme name.
- Match the thumbnail to the title. Every video's artwork should show the same rhyme the title promises. Right now it shows a different one, every time.
Nothing here needs a budget. It needs fewer uploads, each one offered honestly.
How to get the rows, free, no API key
None of the above needed the YouTube Data API. If you want the same 1,404 rows:
curl -s "https://www.youtube.com/@CHANNEL/videos" -H 'accept-language: en-US,en;q=0.9' > channel.html
The page ships a JSON blob called ytInitialData, plus two values you need later:
const html = fs.readFileSync('channel.html', 'utf8');
const data = JSON.parse(html.match(/var ytInitialData = (\{.+?\});<\/script>/s)[1]);
const apiKey = html.match(/"INNERTUBE_API_KEY":"([^"]+)"/)[1];
const visitor = html.match(/"VISITOR_DATA":"([^"]+)"/)[1];
The first ~30 videos live in contents.twoColumnBrowseResultsRenderer.tabs[0].tabRenderer.content.richGridRenderer.contents. The last item is a continuationItemRenderer; take its continuationEndpoint.continuationCommand.token and POST it back:
const res = await fetch(`https://www.youtube.com/youtubei/v1/browse?key=${apiKey}`, {
method: 'POST',
headers: { 'content-type': 'application/json', 'X-Goog-Visitor-Id': visitor },
body: JSON.stringify({
context: { client: { clientName: 'WEB', clientVersion: '2.20250101.00.00' } },
continuation: token,
}),
});
Read onResponseReceivedActions[0].appendContinuationItemsAction.continuationItems, keep the renderers, keep the next token, repeat until it is gone. That is the whole catalogue, newest first, about one request per 30 videos. I added a 400 ms sleep per page and walked 47 pages without a block. Each item gives videoId, title.runs[0].text, viewCountText, publishedTimeText and length; for exact dates, seconds, description and tags, hit the watch page and read ytInitialPlayerResponse.videoDetails.
One honest note on the road not taken: the Data API can do this cheaply too. channels.list with part=contentDetails hands you the uploads playlist id, and playlistItems.list pages 50 videos per call at one unit each, so 1,404 videos is 29 units. That road needs a key and OAuth. Mine needs neither.
Keep the request rate human, cache the HTML, and do not hammer the continuation endpoint. It is someone's page, not your database.













