Content-Signal — AI に使い方を伝える
robots.txt が答える問いはひとつだけで、昔からそれしか答えていません。取得してよいか。パスごと、ボットごとに、はいかいいえ。ところがサイト運営者の多くが本当に取りたい立場、つまり「索引に入れてよい、引用してよい、読者を送ってほしい、ただし私の書いたものでモデルを学習させるな」を表す語彙がありません。
そこで手元にある唯一のレバーを引くことになります。Disallow で全部塞ぎ、学習と一緒に流入も失う。
取得の許可と利用の許可は別物
この二つは本当に別の問いで、帯域の話をしているのは片方だけです。あなたの料金ページを読み、誰かが「何を買えばいいか」と尋ねたときに引用してくれるクローラーは、あなたの味方です。同じバイト列が学習用データセットに流し込まれるのはまったく別の取引で、そこにあなたは参加していません。
すべてを塞ぐと、この二つがひとつの「いいえ」に潰れます。有料アーカイブならそれで正しいかもしれません。見つけてほしい、勧めてほしい事業にとっては既定値として誤りです。回答から消えるのはあなただけで、競合は消えません。
Content-Signal は、その二つを分けるための層です。
三つのシグナル
Content-Signal: search=yes, ai-input=yes, ai-train=no
search— 検索インデックスを作り、結果を返すこと。つまりリンクと短い抜粋です。AI が生成する要約は含みません。それは次のシグナルの話です。ai-input— 回答を作る時点でページをモデルに入力すること。RAG、グラウンディング、生成された回答の下に並ぶ出典。ai-train— あなたのコンテンツでモデルを学習・微調整すること。
三つは互いに独立しています。どの組み合わせも有効で、そのいくつかは手違いではなく考え抜かれた立場です。
値は yes と no の二つだけ。maybe はなく、パス単位の記法もなく、有効期限もありません。
シグナルを書かないことは no ではありません。この取り決めでは、何も述べていない用途は許可でも制限でもなく、単に答えていない状態です。私たちのジェネレーターは毎回三つとも書き出します。それが正しい習慣で、沈黙だけは誰も扱いようがないからです。
置き場所
二か所あり、どちらも安上がりです。
robots.txt の中、user-agent グループの内側に置きます。
User-agent: *
Allow: /
Content-Signal: search=yes, ai-input=yes, ai-train=no
Sitemap: https://example.com/sitemap.xml
そして HTTP レスポンスヘッダーとして。
Content-Signal: search=yes, ai-input=yes, ai-train=no
agentready.md は両方を出しています。このヘッダーがそのままの形で、すべてのレスポンスに付きます。すべてのページ、すべての .md 版、すべての API 応答に。
nginx なら:
add_header Content-Signal "search=yes, ai-input=yes, ai-train=no" always;
Apache なら:
<IfModule mod_headers.c>
Header set Content-Signal "search=yes, ai-input=yes, ai-train=no"
</IfModule>
ヘッダーには置く価値があります。robots.txt はルートに時折取りに来るものであって、誰かが貼ったリンクから深い URL に直接降りてきたエージェントは一度も読まないかもしれません。ヘッダーは持ち去られる当のものにくっついて動きます。
meta タグの形もあります。<meta name="content-signal" content="search=yes, ai-input=yes, ai-train=no">。サーバー設定に手が届かないときはこれを使ってください。HTML 以外のレスポンスも覆えるぶん、ヘッダーのほうが優れています。
実際の三つの立場
帰属表示がほしい出版社。
Content-Signal: search=yes, ai-input=yes, ai-train=no
リンク付きで回答の中に現れるのは配信であって、今の時代の「引用される」に当たります。学習は誰も対価を払わない部分で、しかも誰も送り返してくれません。
勧められたい SaaS。
Content-Signal: search=yes, ai-input=yes, ai-train=yes
ドキュメント、料金、変更履歴。ある作業に何を使うべきかとアシスタントに尋ねられたとき、その答えになりたいはずです。学習データに入っていることは、モデルが何も取得しない場面で名前を挙げてもらう道です。ここに守るものはありません。この素材はマーケティングそのものです。
有料アーカイブ。
Content-Signal: search=yes, ai-input=no, ai-train=no
見つけてはほしい。検索結果そのものが営業文句だからです。避けたいのは、記事の中身がよそ様の回答に無料で載ることです。ここが Disallow にできない仕事をシグナルがする場面で、クロールを塞げば検索結果の掲載まで一緒に消えてしまいます。
特定のボットだけ条件を変えたいなら、そのボット専用のグループを書きます。
User-agent: *
Allow: /
Content-Signal: search=yes, ai-input=yes, ai-train=no
User-agent: GPTBot
Allow: /
Content-Signal: search=yes, ai-input=yes, ai-train=yes
robots.txt のいつもの優先規則どおりです。自分の名前を見つけたボットはそのグループだけを読み、* は完全に無視します。
これが実際には何なのか
若い取り決めです。RFC でも W3C の標準でもなく、どのクローラーにも従う義務はありません。あなたが根拠にできる形で遵守を約束した会社もありません。Content-Signal がコンテンツを守ってくれると書いてあったら、それは宣伝です。
では、なぜ一行書くのか。
機械が読める形式で、費用がほぼゼロだからです。すでに配信しているファイルに一行、すでにある設定ブロックにヘッダーひとつ。この取り決めに付属する前文は、no を EU 指令 2019/790 第 4 条にもとづく権利の明示的な留保、つまりテキスト・データマイニングのオプトアウトとして位置づけています。それがあなたの法域で通用するかは弁護士に聞く話です。表明していない意思はどの法域でも通用しません。
そして、Disallow には言葉のないことを言えるからです。「学習に使うな」と「立ち去れ」は別の文であって、これまで送れたのは後者だけでした。
届いているか確かめる
curl -sI https://example.com/ | grep -i content-signal
curl -s https://example.com/robots.txt | grep -i content-signal
一つ目をトップページ以外でも試してください。ヘッダーを location ブロックの中で設定していると、思っているより狭い範囲にしか付いていないことがあります。
CDN の背後にいるなら、もう一つ。
curl -sI https://example.com/robots.txt | grep -i "server\|cf-cache-status"
返ってきた robots.txt が自分のものか確認してください。私たちのオリジンは何か月も 404 を返し続け、その間 Cloudflare がエッジで、書いた覚えのないマネージドのポリシーファイルを返していました。こちらの確認はどれも、いかにも本物らしい 200 を受け取っていたのです。