本文へ移動
Chandler Nguyen
AI2分で読めます

7言語で40本のAIポッドキャストを評価した。6つのパイプライン修正で、何が改善したか。

7言語40本の実エピソードでAIポッドキャストパイプラインを評価するフレームワークを構築した。 レビューステップがスクリプトを悪化させていた(3.34 → 2.91)。引用URLはすべて偽物に見えた(スコア: 1.28)。 中国語が最も弱いロケールだった(2.88)。6つの修正、1日、そして新しいモデルの後 — これが ビフォー/アフターの数字と、私が行ったすべての変更だ。

先月、心から誇りに思えるパイプラインの変更をリリースした。プロンプトの書き直し。完全なコンテキストによるレビューステップ。繰り返しを検出し、セグメント間の構造的多様性を強制する詳細なルーブリック。

デプロイした。6週間観察した。うまく動いていると自分に言い聞かせた。

それから評価フレームワークを構築した。7言語の実際の本番エピソード40本で実行した。すると、あれほど慎重に設計したレビューステップが、スクリプトを測定可能なほど悪化させていることがわかった。

中立ではない。悪化だ。

セグメントごとの対話は5点中3.34。アウトラインは3.01。そして最終スクリプト、レビュー後のスコアは? 2.91。

スクリプトを改善するために設計されたステップが、品質を12%以上低下させていた。

「動いていると思う」から「動いていないと分かっている」へのこの転換は、数週間前に始まった。Andrew NgのDeepLearning.AIのAgentic AIコースを見ていた時のことだ。彼は当然に聞こえて実はそうでないことを強調している:評価とトレースは、あらゆるエージェンティックシステムの基盤である。 それがなければ、暗闇の中でデバッグしている。それがあれば、チェーンのどのリンクが壊れたかが正確にわかる。

私は何ヶ月も場当たり的なスクリプト品質チェックを続けていた — ターン長の比率やスピーカーバランスなどの構造的メトリクス、さらにA/Bプロンプトのバリアントを比較するLLMジャッジ。これらは明らかなリグレッションを検出していた。しかし包括的ではなかった。1つのステージ(対話)、一度に1つの言語をカバーし、パイプライン全体の品質監査ではなくプロンプトA/Bテスト用に設計されていた。

トレースに関するAndrewの指摘は胸に刺さった。私のパイプラインには、エピソードあたり5つの主要なLLM呼び出しがある — リサーチ、アウトライン、セグメントごとの対話、イントロ/アウトロ、レビュー — さらにElevenLabsのTTSパス。そのうち品質メトリクスがあったのは1つだけ。残りの4つは感覚だけで信頼されていた。

そこで本物の評価システムを構築した。完全で、多次元で、再実行可能なもの。以下がその発見、1日でリリースした6つの修正、そして実際に改善したことだ。


ベースライン:すべてを変えた3つの数字

本番データベースから完了した40エピソードを評価した — 全7言語(en, vi, ja, ko, es, zh, fr)と10のポッドキャストスタイルをカバーし — それぞれ5次元の3つのルーブリックで。LLMジャッジ(GPT-5.6-terra)が各ステージを採点した。

StageScoreWorst Dimension
Dialogue (per-segment)3.34Factual Grounding: 2.17
Outline (research + structure)3.01Citation Credibility: 1.28
Final Script (post-review)2.91Publishability: 1.95

すぐに3つのことが飛び込んできた:

1. レビューパスがスクリプトを0.43ポイント劣化させていた。 対話は3.34。レビュー後は? 2.91。品質を改善するために設計されたステップが、品質を奪っていた。

2. 引用URLがすべて不透明なリダイレクトだった。 すべてのアウトラインにあるすべての「ソースURL」が vertexaisearch.cloud.google.com/grounding-api-redirect/AUZIYQ... を指していた。クリックする人間には機能するが、自動レビュアーには完全に捏造に見える。344のファクトにソースURLがあった。resolved_url を持っていたのはゼロ — そのフィールドはまだ存在すらしていなかった。

3. 公開可能性(Publishability)がパイプライン全体で最も低い次元だった(1.95)。 本物のポッドキャスターは、評価ジャッジの判断によれば、これらのスクリプトを自分の名前で公開しないだろう。検出可能なAIパターン:同一のセグメント開始文、汎用的な遷移、ホストの個性の欠如。

評価は、正確に何を修正すべきかのランク付けリストを私に与えた。その日の残りを修正に費やした。


6つの修正(と測定されたインパクト)

修正1:引用URL — 0%から100%の解決

Before: 344のリサーチファクトのうち0件が resolved_url を持っていた。すべてのURLが捏造に見えた。

Fix: アウトライン生成中に実行される60行のURLリゾルバ。Vertex AIのリダイレクトを実際のソースまで追跡し、両方のURLを保存する(オリジナルはGoogleの利用規約準拠用、解決済みはその他すべて用)。

def resolve_grounding_url(url: str) -> str:
    if "grounding-api-redirect" not in url:
        return url
    response = requests.head(url, allow_redirects=True, timeout=5)
    return response.url if response.url != url else url

After: 今日の新しいエピソードでは、23件中23件のリサーチファクトが resolved_url を持つ — simonwillison.netaxios.comthinkingmachines.ai のような実際のURL。解決率100%。


修正2:レビューモデルの交換(Gemini → DeepSeek)

Before: Gemini 3.5 Flashがレビューパスを実行していた。軽微で保守的な編集を行った:「Exactly!」を「No question about it!」に変えたが、ほとんど元のテキストを保持した。対話を平坦化するフィラーを追加した。オーディオタグ密度が低下。タイプ・トークン比が低下。ターン数が膨張した。

Fix: レビューパスをDeepSeek v4-pro(最大出力384K、96Kキャップ設定)に交換。プロバイダーを設定可能に:

provider = get_provider("review")  # reads REVIEW_PROVIDER env var
response = provider.generate(
    prompt=prompt, temperature=0.0,
    max_output_tokens=96000,
)

検証: 本番環境にデプロイ。ベトナム語のテックニュースエピソードがDeepSeekレビュー付きの完全なパイプラインを通過 — 10.3K → 11.6Kトークン、121秒で完了、引き締めパスは0回で済んだ。2つ目のエピソード(英語)は7.9K → 17Kトークンを203秒で処理。DeepSeek APIキーはGoogle Cloud Secret Managerに保存され、デプロイ時に service.yaml 経由で自動注入される。


修正3:アウトラインの自己批評(+0.50の改善)

Before: アウトラインはGeminiから内部品質チェックなしで直接ユーザーに渡っていた。平均スコア:3.01。

Fix: 自動批評ステップを追加。DeepSeek v4-proがアウトラインを6次元のルーブリック(5つのアウトライン次元+セグメント数)で評価し、スコア+具体的なフィードバックを返し、批評をポッドキャストメタデータに保存する。

その後、制御された実験を実施:アウトラインが3.0未満の6エピソードを取得し、DeepSeek批評を実行し、フィードバックを再生成指示としてGeminiに戻し、再採点。

After: 6エピソード全体で**+0.50の改善**。

DimensionBeforeAfterDelta
Content Boundaries3.334.17+0.83
Research Depth2.673.17+0.50
Citation Credibility1.001.50+0.50
Structural Logic3.674.17+0.50
Audience Fit2.172.33+0.17

最悪のエピソードは1.80から3.20(+1.40)に向上した。6つのうち悪化したのは1つだけ。批評は現在本番環境でデフォルトで有効になっており — すべての新しいアウトラインはユーザーが見る前にこの品質チェックを受ける。


修正4:1セグメントのアウトラインは強制失敗に

Before: 評価では、単一セグメントでリサーチファクトがゼロのエピソードが2.07という低スコアを記録していた。これらはパイプラインが失敗として扱っていなかった失敗ケースだった。

Fix: リカバリー試行後もアウトライン生成器が3つ未満の有効なセグメントしか生成しない場合、ポッドキャストはFAILEDとマークされる。1セグメントのアウトラインがユーザーに届くことはもうない。次の作成試行時に、ユーザーのクレジットは再試行のために解放される。


修正5:中国語ローカライゼーション・ルール

Before: 中国語エピソードのスコアは2.88 — 7言語中最低だった。翻訳アーティファクト(英語のイディオムの直訳)、同一のセグメント開始文、中国語名(明辉/晓雯)ではなくデフォルトの英語ホスト名(Alex/Maya)。

Fix: 中国語固有の対話ルールを作成:ネイティブな会話パターン(不是...而是...構文)、適切な文末助詞(吧/啊/呢)、翻訳禁止ガイドライン("medical miracle"を直訳しない)、ワールドカップエピソード用の中国語サッカーの比喩、明確な個性を持つロケール固有のホストプロフィール。

中国語対話テンプレートは、英語のデフォルトを再利用する状態から、会話パターン、不同意の表現、すべてのポッドキャストスタイルに対応するオーディエンス固有のフレーミングをカバーする80行の専用ガイドを持つまでになった。


修正6:非英語向けホスト名デフォルト

Before: 複数の非英語エピソードでホスト名がAlexとMayaだった。ロケール固有のホストプロフィールは存在していたが、アウトライン生成器のフォールバックパスが英語のデフォルトにハードコードされていた。

Fix: ロケール対応のプロフィール解決パイプラインを通じて修正を追跡。最近の本番エピソードでは、翔太/健一(ja)、Mạnh/Nga(vi)、Hugo/Camille(fr)、明辉/晓雯(zh)が使用されている。7月のコミットでエッジ関数と作成フローは既に修正済みで — 残りのフォールバックはアウトライン生成器自体にあった。


評価フレームワーク(再利用可能)

これらすべてを発見したフレームワークは、約500行のPython、3つのルーブリックファイル(各5次元)、共有のGPT-5.6-terraジャッジ、そしてオーケストレーターで構成されている:

docs/pipeline/evals/
├── run.py                  # Orchestrator: extract → judge → report
├── judge.py                # Shared LLM judge (rate with rubric)
├── rubric_outline.py       # Stage 1: 5 dimensions, 1-5 scale
├── rubric_dialogue.py      # Stage 2: 5 dimensions, 1-5 scale
├── rubric_final_script.py  # Stage 3: 5 dimensions, 1-5 scale
├── dataset_40.json         # Extracted production data
├── scores.json             # Machine-readable scores
└── report.md               # Auto-generated report

A/B比較用の実験レイヤーも構築した:

docs/pipeline/evals/experiments/
├── review_ab.py             # Compare two review models
├── outline_critique_ab.py   # Critique → regenerate → compare
├── shared.py                # Score comparator, report generator
└── results/                 # Archived by date

パイプライン変更後に python docs/pipeline/evals/run.py --full を実行すれば、約8分でレポートが得られる。モデルを比較するには experiments/review_ab.py --episodes 10 を実行。結果は日付ごとにアーカイブされ、トレンド追跡が可能 — 今月の品質が先月より改善したか知りたい? スコアをdiffすればいい。

40エピソードの完全評価はAPI呼び出しで約$1-2かかる。実験はさらに安い。その代わりに得られるシグナル — パイプラインのどのステージと次元が注意を必要としているかのランク付けリスト — これは私が作った中で最も安価なデバッグツールだ。


まだ壊れているもの

DeepSeekレビューA/B実験には本番のフルプロンプトが必要。 実験スクリプトは15行の簡略化プロンプトを使用していた。本番のレビューは、反復禁止ルール、キャッチフレーズ割り当て、編集ガードレール、長さポリシーを含む80行のプロンプトを使用する。簡略化プロンプトでは、DeepSeekは本質的に中立的な結果(-0.04)を示した。本番のフルプロンプトでは、パイプラインは英語とベトナム語で正常に完了している。実験を本番に合わせて更新し、再実行する必要がある。

中国語ローカライゼーションには検証が必要。 ルールは紙の上では正しく見える。ホストプロフィールは書かれ、対話ガイドは配置されている。しかし、スコアが2.88から上がったことを確認するために、新しい中国語エピソードで評価をまだ実行していない。これは今週の優先事項だ。

新しいエピソードで完全40エピソード評価を再実行する必要がある。 6つの修正はすべてデプロイ済みだ。次のステップは、これらの変更後に生成された40エピソードを抽出し、同じ評価に通し、過去のベースラインと比較すること。最終スクリプトスコアが2.91から3.0以上に上がり、引用の信頼性が1.28から妥当な値になれば、変更はエンドツーエンドで機能したと分かる。


3つの質問によるパイプライン監査

この経験を経て、今ではすべてのパイプライン変更を3つの質問で監査している:

1. 各ステップの間に品質ゲートはあるか? アウトラインはGeminiから直接ユーザーに渡っていた。批評ステップの追加により、誰かが見る前に最悪のアウトラインを捕捉できた。すべてのパイプラインステップには品質チェックが必要だ — 明示的な基準に対する自動化されたLLM評価。

2. 各ステップは測定したときに実際に品質を改善しているか? 動かして効果があると仮定するだけでは不十分だ。同じコンテンツでの文字通りのビフォー/アフタースコアが必要だ。私のレビューステップは、測定するまでの6週間、スクリプトを劣化させていた。まず測定し、何も仮定するな。

3. どの次元が壊れたか特定できるか? 「品質が悪い」は実行可能ではない。「引用の信頼性が1.28なのは、100%のURLが不透明なリダイレクトだからだ」は実行可能だ。ステージごとの多次元ルーブリックが、正確にどこを見るべきかを教えてくれる。評価の前は、レビューステップの調査に何時間も費やした。評価があれば、数秒で済んだ — 数字が直接、公開可能性とレビューモデルを指していた。


よくある質問

LLM評価の実行は高くつかないのか?

40エピソードの完全評価はAPI呼び出しで約$1-2(GPT-5.6-terra、合計約420Kトークン)。A/B実験はさらに安い。その代わりに得られるシグナル — パイプラインのどのステージが注意を必要としているかのランク付けリスト — これは私が作った中で最も安価なデバッグツールであり、ユーザーが壊れたエピソードに浪費するクレジットよりも安い。

なぜステージごとに5次元なのか?「全体的な品質」だけではダメなのか?

「全体的な品質」は何かが間違っていると教えてくれる。何がとは教えてくれない。引用の信頼性が1.28だと見たとき、すぐにURLが壊れていると分かった。公開可能性が1.95だと見たとき、AIの痕跡が検出可能だと分かった。5次元は鑑別診断を与える。1次元は体温計を与える。

LLMジャッジの一貫性をどう保っているのか?

同じモデル(GPT-5.6-terra)、同じ温度(0.0)、同じ推論努力(medium)、毎回同じルーブリックプロンプト。スコアはタイムスタンプ付きでアーカイブされ、日付を跨いで比較できる。ジャッジを変えるとベースラインが変わる — 1つ選んだらそれに固執すること。

ジャッジ自体が間違っていたらどうなるのか?

ルーブリックには各スコアの必須の正当化が含まれている — ジャッジはコンテンツから特定の証拠を引用しなければならない。また、ジャッジを較正するために全7言語で10エピソードの手動の定性的レビューも行った。LLMスコアは私の人間の判断と密接に一致した。LLMが信頼できない可能性がある重要な次元(文化的判断を必要とする「公開可能性」など)については、人間によるスポットチェックが不可欠だ。


私はDIALOGUEというAIポッドキャストプラットフォームを、夜と週末に一人で開発しています。道中で学んだことを書いています。

もしあなたが自身のLLMパイプライン用の評価システムを構築したなら、興味がある:品質をどう測定しているか、そして驚いた発見は何だったか?

以上です。

それでは、Chandler