HomeBlogTranscribePlansAPI Keys

Transkrypcja YouTube w Golang: net/http i Trzy Struktury

Program Go dekodujący odpowiedź API transkrypcji YouTube do struktur

Oto cały program. Wyjaśnienie potem.

package main

import (
	"encoding/json"
	"fmt"
	"net/http"
	"net/url"
	"os"
	"time"
)

type Transcript struct {
	VideoID     string `json:"videoId"`
	Title       string `json:"title"`
	PubDate     string `json:"pubDate"`
	Content     string `json:"content"`
	ContentSize int    `json:"contentSize"`
	Truncated   bool   `json:"truncated"`
}

type APIError struct {
	Code              string `json:"code"`
	Message           string `json:"message"`
	Status            int    `json:"status"`
	RetryAfterSeconds int    `json:"retryAfterSeconds"`
}

type envelope struct {
	Result *Transcript `json:"result"`
	Error  *APIError   `json:"error"`
}

func main() {
	q := url.Values{}
	q.Set("url", "https://www.youtube.com/watch?v=dQw4w9WgXcQ")

	req, err := http.NewRequest(http.MethodGet,
		"https://youtube2text.org/api/transcribe?"+q.Encode(), nil)
	if err != nil {
		fmt.Fprintln(os.Stderr, err)
		os.Exit(1)
	}
	req.Header.Set("x-api-key", os.Getenv("YT2TEXT_KEY"))

	client := &http.Client{Timeout: 60 * time.Second}
	resp, err := client.Do(req)
	if err != nil {
		fmt.Fprintln(os.Stderr, err)
		os.Exit(1)
	}
	defer resp.Body.Close()

	var env envelope
	if err := json.NewDecoder(resp.Body).Decode(&env); err != nil {
		fmt.Fprintln(os.Stderr, "decode:", err)
		os.Exit(1)
	}

	if env.Error != nil {
		fmt.Fprintf(os.Stderr, "%s: %s\n", env.Error.Code, env.Error.Message)
		os.Exit(1)
	}

	fmt.Println(env.Result.Title)
	fmt.Printf("%d chars, truncated=%v\n",
		env.Result.ContentSize, env.Result.Truncated)
}

go run main.go, gotowe. Brak modułów firm trzecich, które to powinno być — API to zwykły HTTPS zwracający JSON, więc net/http i encoding/json obejmują wszystko. Nie ma oficjalnej biblioteki Go dla tego, i twierdzę, że to feature.

Sztuczka koperty

Odpowiedzi sukcesu umieszczają dane w result; niepowodzenia umieszczają ustrukturyzowany obiekt w error. Dekodowanie obu do jednej struktury z dwoma polami wskaźnika oznacza jedno wywołanie Decode obsługuje każdą odpowiedź — który wskaźnik jest nie-nil jest Twoją odpowiedzią. Brak ponownego czytania treści, brak wąchania Content-Type, a env.Error.Status pasuje do stanu HTTP, jeśli chcesz podwójnie sprawdzić.

Kody godne instrukcji switch

APIError.Code jest stabilny, więc rozgałęź się na nim zamiast na ciągach wiadomości:

switch env.Error.Code {
case "RATE_LIMIT_EXCEEDED":
	wait := time.Duration(env.Error.RetryAfterSeconds) * time.Second
	time.Sleep(wait) // then retry the request
case "TRANSCRIPT_UNAVAILABLE":
	// video exists but has no caption track — skip permanently
case "VIDEO_NOT_FOUND", "INVALID_URL":
	// bad input; log and move on
default:
	// UNAUTHORIZED, VALIDATION_ERROR, YOUTUBE_ERROR
}

TRANSCRIPT_UNAVAILABLE to ten, który ludzie źle obsługują. Transkrypcje pochodzą z pasów napisów YouTube — ręczny lub autogenerowany, angielski preferowany, pierwszy dostępny język w innym razie. Jeśli film ma wyłączone napisy, nie ma transkrypcji do pobrania, a ponowne próby z wykładniczym wycofywaniem nie spowodują, że napisy będą rosnąć. Traktuj to jako permanentne pominięcie w pracach wsadowych, lub kolejka Twojego pracownika zapełni się zombie.

Parametry i klucze

Dwa parametry zapytania w sumie. url przyjmuje dowolny kształt URL YouTube lub gołe 11-znakowe id. maxChars ogranicza długość wyjścia (150000 to domyślna i maksymalna) — przydatne gdy transkrypcja trafia do LLM i płacisz za token, co jest większością przypadków Go, które słyszę, zwykle RAG na całym kanale.

Aby uzyskać klucz bez żadnej rejestracji, curl https://youtube2text.org/api/demo-key zwraca działający — wspólny dla wszystkich anonimowych użytkowników na 5 filmów na miesiąc na IP, więc to ściśle do próbowania rzeczy. Jeśli ważysz to przeciwko wysłaniu do yt-dlp dla plików napisów, napisałem porównanie napisów yt-dlp vs API; i jeśli część Twojego stosu to Node, to samo wywołanie w JavaScript jest jeszcze krótsze.

Do rzeczywistego użytku zaloguj się za pomocą Google na youtube2text.org/app/keys — brak karty, brak telefonu, bezpłatny poziom 5 filmów na miesiąc, płatne poziomy od 5,99 USD za 50 do 19,99 USD bez limitu. Kod Go powyżej się nie zmienia; tylko zmienna środowiska.