NIP-10はkind 1ノートが返信スレッドを形成するためにお互いを参照する方法を規定しています。会話ビューを構築するにはこれを理解することが不可欠です。

問題

誰かがノートに返信するとき、クライアントは知る必要があります: これは何への返信か?会話のルートは何か?誰に通知すべきか?NIP-10はeタグ(イベント参照)とpタグ(pubkeyメンション)を通じてこれらの質問に答えます。

マーク付きタグ(推奨)

現代のクライアントはeタグで明示的なマーカーを使用します:

{
  "id": "f9c2e...",
  "pubkey": "a3b9c...",
  "created_at": 1734912345,
  "kind": 1,
  "tags": [
    ["e", "abc123...", "wss://relay.example.com", "root"],
    ["e", "def456...", "wss://relay.example.com", "reply"],
    ["p", "91cf9..."],
    ["p", "14aeb..."]
  ],
  "content": "素晴らしいポイント!同意します。",
  "sig": "b7d3f..."
}

rootマーカーはスレッドを開始した元のノートを指します。replyマーカーは回答している特定のノートを指します。ルートに直接返信する場合は、rootのみを使用します(replyタグは不要)。この区別はレンダリングに重要です: replyはスレッドビューでのインデントを決定し、rootはすべての返信をグループ化します。

スレッディングルール

  • ルートへの直接返信: rootマーカー付きの1つのeタグ
  • 返信への返信: 2つのeタグ、1つはroot、1つはreply
  • rootはスレッド全体で一定のまま。replyは返信先に応じて変わる

通知用のPubkeyタグ

通知されるべき全員のpタグを含めます。最低限、返信しているノートの作成者をタグ付けします。慣例として、親イベントからのすべてのpタグも含めます(会話の全員がループに留まるように)、さらにコンテンツで@メンションしたユーザーも含めます。

リレーヒント

eおよびpタグの3番目の位置には、そのイベントまたはユーザーのコンテンツが見つかる可能性のあるリレーURLを含めることができます。これにより、クライアントは元のリレーに接続していなくても参照されているコンテンツを取得できます。

非推奨の位置タグ

初期のNostr実装では、マーカーではなくタグの位置から意味を推論していました: 最初のeタグがルート、最後がリプライ、中間がメンション。このアプローチは曖昧さを生むため非推奨です。マーカーのないeタグを見た場合、おそらく古いクライアントからのものです。現代の実装は常に明示的なマーカーを使用すべきです。

スレッドビューの構築

スレッドを表示するには、ルートイベントを取得し、そのルートを参照するeタグを持つすべてのイベントをクエリします:

["REQ", "thread", {"kinds": [1], "#e": ["<root-event-id>"]}]

結果をcreated_atでソートし、replyマーカーを使用してツリー構造を構築します。replyがルートを指すイベントはトップレベルの返信です。replyが別の返信を指すイベントはネストされた応答です。


主要ソース:

言及箇所:

関連項目: