fix: yt-dlp'ye YouTube cookie desteği ekle (bot-check bypass)

android player_client YouTube'un "Sign in to confirm you're not a bot"
duvarını aşmadı — Coolify sunucusunun IP'si datacenter olarak
işaretlenmiş. Kimlik doğrulanmış bir tarayıcı oturumunun cookies.txt'i
YTDLP_COOKIES_B64 env değişkeni (Coolify'da ayarlandı, repo'da yok)
üzerinden container'a taşınıp /tmp'e yazılıyor ve her yt-dlp
çağrısına --cookies olarak veriliyor.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
2026-08-30 16:14:46 +03:00
co-authored by Claude Sonnet 5
parent 81d71bd761
commit 09b958ec00
6 changed files with 39 additions and 1 deletions
+6 -1
View File
@@ -6,6 +6,7 @@ import { prisma } from "@streamclipper/db";
import { env } from "../env";
import { QUEUE_NAMES, signalDetectionQueue, type StreamIngestJob } from "../queues";
import { redisConnection } from "../redis";
import { ytdlpCookieArgs } from "../ytdlpCookies";
const SEGMENT_LIST_POLL_MS = 5_000;
@@ -73,7 +74,11 @@ async function runCapture(job: Job<StreamIngestJob>): Promise<void> {
const ytdlp = spawn(
"yt-dlp",
["--extractor-args", "youtube:player_client=android", "-f", "best", "-o", "-", youtubeUrl],
[
"--extractor-args", "youtube:player_client=android",
...ytdlpCookieArgs(),
"-f", "best", "-o", "-", youtubeUrl,
],
{ stdio: ["ignore", "pipe", "pipe"] },
);
+1
View File
@@ -7,4 +7,5 @@ export const env = {
segmentTimeSec: Number(process.env.SEGMENT_TIME_SEC ?? 900),
port: Number(process.env.API_DAEMON_PORT ?? 4001),
forceLiveUrl: process.env.FORCE_LIVE_URL ?? "",
ytdlpCookiesB64: process.env.YTDLP_COOKIES_B64 ?? "",
};
+2
View File
@@ -4,6 +4,7 @@ import { prisma } from "@streamclipper/db";
import { env } from "./env";
import { streamIngestQueue } from "./queues";
import { sendTelegramMessage } from "./telegram";
import { ytdlpCookieArgs } from "./ytdlpCookies";
const execFileAsync = promisify(execFile);
@@ -32,6 +33,7 @@ async function findLiveVideoId(channelId: string): Promise<string | null> {
"--simulate",
"--no-warnings",
"--extractor-args", "youtube:player_client=android",
...ytdlpCookieArgs(),
"--print", "%(id)s",
liveUrl,
],
+22
View File
@@ -0,0 +1,22 @@
import { writeFileSync } from "node:fs";
import { env } from "./env";
const COOKIES_PATH = "/tmp/yt-cookies.txt";
/**
* YouTube increasingly bot-checks yt-dlp requests from datacenter IPs
* ("Sign in to confirm you're not a bot"), which no --extractor-args
* combination reliably bypasses. An authenticated session's cookies avoid
* the check. The cookies file is never committed — it's decoded once at
* startup from a Coolify-managed env var into a local temp file.
*/
const cookiesFilePath: string | null = env.ytdlpCookiesB64
? (() => {
writeFileSync(COOKIES_PATH, Buffer.from(env.ytdlpCookiesB64, "base64"), { mode: 0o600 });
return COOKIES_PATH;
})()
: null;
export function ytdlpCookieArgs(): string[] {
return cookiesFilePath ? ["--cookies", cookiesFilePath] : [];
}