clone

every nostr nip as a chapter of an illustrated, early-2000s printed game manual

main
nip.guide / site / nips / 7d.html
7d.html 15.5K
1<!DOCTYPE html>2<html lang="en">3<head>4<meta charset="utf-8">5<meta name="viewport" content="width=device-width, initial-scale=1">6<title>NIP-7D - Forum Threads — Nostr Instruction Manual</title>7<meta name="description" content="NIP-7D: forum threads on Nostr. Kind 11 thread events with a title tag, and flat kind 1111 replies that always point to the root. Complete manual page.">8<link rel="preload" href="../assets/fonts/michroma-400-latin.woff2" as="font" type="font/woff2" crossorigin>9<link rel="preload" href="../assets/fonts/exo2-var-latin.woff2" as="font" type="font/woff2" crossorigin>10<link rel="preload" href="../assets/fonts/sairacondensed-600-latin.woff2" as="font" type="font/woff2" crossorigin>11<link rel="preload" href="../assets/fonts/sairacondensed-700-latin.woff2" as="font" type="font/woff2" crossorigin>12<link rel="preload" href="../assets/fonts/sairacondensed-500-latin.woff2" as="font" type="font/woff2" crossorigin>13<link rel="preload" href="../assets/fonts/sharetechmono-400-latin.woff2" as="font" type="font/woff2" crossorigin>14<link rel="preload" href="../assets/fonts/exo2-400i-latin.woff2" as="font" type="font/woff2" crossorigin>15<link rel="icon" href="../assets/favicon.svg" type="image/svg+xml">16<link rel="stylesheet" href="../assets/manual.css">17</head>18<body>1920<svg width="0" height="0" style="position:absolute">21 <defs>22 <marker id="arr" markerWidth="9" markerHeight="9" refX="7" refY="4.5" orient="auto">23 <path d="M1,1 L8,4.5 L1,8 Z" fill="#f26a00"/>24 </marker>25 <marker id="arrb" markerWidth="9" markerHeight="9" refX="7" refY="4.5" orient="auto">26 <path d="M1,1 L8,4.5 L1,8 Z" fill="#2e5f9e"/>27 </marker>28 </defs>29</svg>3031<div class="page">32 <span class="staple s1"></span><span class="staple s2"></span>3334 <header class="band">35 <a class="logo" href="../index.html">NOSTR<b>▸</b>PROTOCOL MANUAL</a>36 <span class="booklet-note">Chapter 7D - Social</span>37 </header>38 <nav class="tabs">39 <a href="../index.html">Contents</a>40 <a href="#overview" class="on">Overview</a>41 <a href="#spec">Spec</a>42 <a href="#examples">Examples</a>43 <a href="#history">History</a>44 </nav>4546 <div class="chapter">47 <div class="nipno" data-n="7D">7D</div>48 <div class="titles">49 <div class="kicker">Nostr Implementation Possibility - Hex № 7D</div>50 <h1>Forum Threads</h1>51 <p class="sub">A titled thread event for forum-style boards, with flat replies that always answer the root post.</p>52 </div>53 </div>5455 <main class="spread">56 <div class="main">5758 <h2 class="bar" id="overview"><span class="num">1</span> Overview</h2>59 <p>A classic forum has topics. A user opens a topic with a title. Other users reply under the topic. Replies do not nest. This NIP maps that model onto Nostr with one event kind.</p>60 <p>A <strong>thread</strong> is a <code>kind 11</code> event. The thread text lives in <code>content</code>. The thread title lives in a <code>title</code> tag. Replies are not a new kind. Replies reuse the <code>kind 1111</code> comment format from <a href="22.html">NIP-22</a>.</p>61 <p>The result is a flat discussion. Every reply points at the root thread event. Clients render the thread as one ordered list, like a forum topic page. This NIP was split out of the group-chat work in <a href="29.html">NIP-29</a> so that threads work on any relay.</p>6263 <div class="box hint">64 <span class="tag">Hint!</span>65 <p>Threads are not text notes. A <code>kind 1</code> note (see <a href="10.html">NIP-10</a>) has no title and nests freely. Use <code>kind 11</code> when you want a titled topic with a flat reply list.</p>66 </div>6768 <h2 class="bar" id="spec"><span class="num">2</span> The Thread Event — Kind 11</h2>69 <p>A thread is a regular event with <code>kind</code> set to <code>11</code>. All base rules from <a href="01.html">NIP-01</a> apply: the event is signed, hashed, and published like any other event. Threads SHOULD include a <code>title</code> tag.</p>7071 <div class="crt">72 <div class="titlebar">Wire format - kind 11 thread</div>73<pre>{74 <span class="k">"kind"</span>: 11,75 <span class="k">"content"</span>: <span class="s">"Good morning"</span>,76 <span class="k">"tags"</span>: [77 [<span class="s">"title"</span>, <span class="s">"GM"</span>]78 ]79}</pre>80 </div>8182 <div class="tscroll"><table class="ref">83 <caption>Kind 11 reference</caption>84 <tr><th>Item</th><th>Value</th><th>Rule</th></tr>85 <tr><td class="btn">kind</td><td><code>11</code></td><td>Marks the event as a forum thread. Regular storage class per <a href="01.html">NIP-01</a>.</td></tr>86 <tr><td class="btn">content</td><td>string</td><td>The body text of the thread's opening post.</td></tr>87 <tr><td class="btn">title</td><td><code>["title", &lt;string&gt;]</code></td><td>The thread title. Threads SHOULD include this tag.</td></tr>88 </table></div>8990 <h2 class="bar" id="replies"><span class="num">3</span> Replies — Kind 1111</h2>91 <p>Replies to a <code>kind 11</code> thread MUST use <a href="22.html">NIP-22</a> <code>kind 1111</code> comment events. A reply SHOULD always point to the root <code>kind 11</code> event. Do not reply to a reply. This rule avoids arbitrarily nested reply hierarchies.</p>9293 <div class="crt">94 <div class="titlebar">Wire format - kind 1111 reply</div>95<pre>{96 <span class="k">"kind"</span>: 1111,97 <span class="k">"content"</span>: <span class="s">"Cool beans"</span>,98 <span class="k">"tags"</span>: [99 [<span class="s">"K"</span>, <span class="s">"11"</span>],100 [<span class="s">"E"</span>, <span class="c">&lt;event-id&gt;</span>, <span class="c">&lt;relay-url&gt;</span>, <span class="c">&lt;pubkey&gt;</span>]101 ]102}</pre>103 </div>104105 <div class="tscroll"><table class="ref">106 <caption>Reply tags (from <a href="22.html">NIP-22</a>)</caption>107 <tr><th>Tag</th><th>Form</th><th>Rule</th></tr>108 <tr><td class="btn">K</td><td><code>["K", "11"]</code></td><td>The kind of the root event. Always <code>"11"</code> for forum threads.</td></tr>109 <tr><td class="btn">E</td><td><code>["E", &lt;event-id&gt;, &lt;relay-url&gt;, &lt;pubkey&gt;]</code></td><td>Points to the root <code>kind 11</code> event: its id, a relay URL hint, and the author's pubkey.</td></tr>110 </table></div>111112 <div class="box tech">113 <span class="tag">Tech Note</span>114 <p>The reply example in the source shows only the uppercase root tags <code>K</code> and <code>E</code>. <a href="22.html">NIP-22</a> also defines lowercase parent tags (<code>k</code>, <code>e</code>, <code>p</code>). Because every reply targets the root, the parent equals the root; the source does not state whether the lowercase set is still required. Follow <a href="22.html">NIP-22</a> for the full comment tag rules.</p>115 </div>116117 <figure class="diagram">118 <div class="frame">119 <svg viewBox="0 0 560 210" role="img" aria-label="Three kind 1111 replies all point to one kind 11 root thread; replies do not point to each other">120 <rect class="d-actor" x="200" y="14" width="160" height="50" rx="8"/>121 <text class="d-actor-label" x="280" y="36" text-anchor="middle">Thread</text>122 <text class="d-note" x="280" y="53" text-anchor="middle">kind 11 - "GM"</text>123 <rect class="d-actor" x="20" y="140" width="140" height="46" rx="8"/>124 <text class="d-actor-label" x="90" y="160" text-anchor="middle">Reply 1</text>125 <text class="d-note" x="90" y="176" text-anchor="middle">kind 1111</text>126 <rect class="d-actor" x="210" y="140" width="140" height="46" rx="8"/>127 <text class="d-actor-label" x="280" y="160" text-anchor="middle">Reply 2</text>128 <text class="d-note" x="280" y="176" text-anchor="middle">kind 1111</text>129 <rect class="d-actor" x="400" y="140" width="140" height="46" rx="8"/>130 <text class="d-actor-label" x="470" y="160" text-anchor="middle">Reply 3</text>131 <text class="d-note" x="470" y="176" text-anchor="middle">kind 1111</text>132 <path class="d-msg" d="M100,138 C130,100 190,80 240,68"/>133 <path class="d-msg" d="M280,138 L280,68"/>134 <path class="d-msg" d="M460,138 C430,100 370,80 320,68"/>135 <text class="d-label" x="140" y="92" text-anchor="middle">E → root</text>136 <text class="d-label" x="420" y="92" text-anchor="middle">E → root</text>137 <circle r="4" fill="#f26a00">138 <animateMotion dur="2.6s" repeatCount="indefinite" path="M280,138 L280,68"/>139 </circle>140 </svg>141 </div>142 <figcaption>Fig. 7D-1 — <b>Flat threading.</b> Every reply carries an <code>E</code> tag to the root thread. Replies never point at other replies.</figcaption>143 </figure>144145 <h2 class="bar" id="examples"><span class="num">4</span> Worked Example</h2>146 <p>Alice opens a thread. Bob loads the thread and its replies, then posts one reply. Orange lines go to the relay. Blue lines come from the relay.</p>147148 <div class="crt">149 <div class="titlebar">Session transcript - wss://forum.example.com</div>150<pre><span class="c">-- Alice opens a thread --</span>151<span class="send">→ ["EVENT", {"id":"a3f1c02d9e…","pubkey":"8a2f11bc…","created_at":1749800000,152 "kind":11,"tags":[["title","GM"]],"content":"Good morning","sig":"91bb04c2…"}]</span>153<span class="recv">← ["OK", "a3f1c02d9e…", true, ""]</span>154155<span class="c">-- Bob fetches the thread and all replies to it --</span>156<span class="send">→ ["REQ", "topic", {"ids":["a3f1c02d9e…"]},157 {"kinds":[1111], "#E":["a3f1c02d9e…"]}]</span>158<span class="recv">← ["EVENT", "topic", {"id":"a3f1c02d9e…", "kind":11, "content":"Good morning", …}]</span>159<span class="recv">← ["EOSE", "topic"]</span>160161<span class="c">-- Bob replies to the root --</span>162<span class="send">→ ["EVENT", {"id":"c9d24be071…","pubkey":"5e90aa47…","created_at":1749800180,163 "kind":1111,"tags":[["K","11"],164 ["E","a3f1c02d9e…","wss://forum.example.com","8a2f11bc…"]],165 "content":"Cool beans","sig":"7fe210da…"}]</span>166<span class="recv">← ["OK", "c9d24be071…", true, ""]</span>167<span class="c">-- the reply streams into Bob's open subscription --</span>168<span class="recv">← ["EVENT", "topic", {"id":"c9d24be071…", "kind":1111, "content":"Cool beans", …}]</span></pre>169 </div>170171 <figure class="diagram">172 <div class="frame">173 <svg viewBox="0 0 560 230" role="img" aria-label="Sequence diagram: client requests the kind 11 root and kind 1111 replies with an uppercase E filter, relay returns them, then live replies stream in">174 <line class="d-wire" x1="110" y1="40" x2="110" y2="215" stroke-dasharray="3 4"/>175 <line class="d-wire" x1="450" y1="40" x2="450" y2="215" stroke-dasharray="3 4"/>176 <rect class="d-actor" x="55" y="8" width="110" height="30" rx="6"/>177 <text class="d-actor-label" x="110" y="28" text-anchor="middle">Client</text>178 <rect class="d-actor" x="395" y="8" width="110" height="30" rx="6"/>179 <text class="d-actor-label" x="450" y="28" text-anchor="middle">Relay</text>180 <path class="d-msg" d="M110,62 L445,62"/>181 <text class="d-label" x="280" y="55" text-anchor="middle">["REQ", "topic", {"kinds":[1111],"#E":[root]}]</text>182 <path class="d-msg blue" d="M450,95 L115,95"/>183 <text class="d-label" x="280" y="88" text-anchor="middle">["EVENT", "topic", {kind 1111}] × stored replies</text>184 <path class="d-msg blue" d="M450,128 L115,128"/>185 <text class="d-label" x="280" y="121" text-anchor="middle">["EOSE", "topic"]</text>186 <path class="d-msg blue d-flow" d="M450,170 L115,170"/>187 <text class="d-label" x="280" y="163" text-anchor="middle">["EVENT", "topic", {kind 1111}] live replies</text>188 <text class="d-note" x="280" y="205" text-anchor="middle">The E tag is indexed, so one #E filter returns the whole flat thread.</text>189 </svg>190 </div>191 <figcaption>Fig. 7D-2 — <b>Loading a topic.</b> One <code>#E</code> filter on the root id fetches every reply, stored and live.</figcaption>192 </figure>193194 <h2 class="bar" id="history"><span class="num">5</span> Version History</h2>195 <p>NIP-7D began as part of the relay-based groups work and was split into its own document in late 2024. Notable changes, newest first:</p>196 <ul class="patchnotes">197 <li class="minor"><span class="ver">2026</span><span class="when">2026-05</span>Editorial sanity fix by fiatjaf; no rule change.</li>198 <li><span class="ver">2025</span><span class="when">2025-04</span>Renamed the thread title tag from <code>subject</code> to <code>title</code> (<a href="https://github.com/nostr-protocol/nips/pull/1874">#1874</a>).</li>199 <li><span class="ver">Origin</span><span class="when">2024-11</span>hodlbod broke chat and threads out of <a href="29.html">NIP-29</a>; <code>kind 11</code> threads became this standalone NIP (<a href="https://github.com/nostr-protocol/nips/pull/1591">#1591</a>).</li>200 </ul>201202 <div class="credits">203 <h3 class="cardhead">Original Proposal - Credits</h3>204 <table>205 <tr><td>Author</td><td>hodlbod</td></tr>206 <tr><td>First commit</td><td>2024-11-21 — “Break out chat and threads from nip 29” (<a href="https://github.com/nostr-protocol/nips/pull/1591">PR #1591</a>)</td></tr>207 <tr><td>Status</td><td>draft - optional</td></tr>208 <tr><td>Source</td><td><a href="https://github.com/nostr-protocol/nips/blob/master/7D.md">7D.md on GitHub</a> - <a href="https://github.com/nostr-protocol/nips/commits/master/7D.md">full change history</a></td></tr>209 </table>210 </div>211212 <h2 class="bar"><span class="num">6</span> See Also</h2>213 <ul>214 <li><a href="01.html">NIP-01</a> — the base event format, kinds, and filters that threads build on.</li>215 <li><a href="22.html">NIP-22</a> — the <code>kind 1111</code> comment format that all thread replies MUST use.</li>216 <li><a href="29.html">NIP-29</a> — relay-based groups; the document this NIP was split out of.</li>217 <li><a href="10.html">NIP-10</a> — <code>kind 1</code> text notes with nested replies; the contrasting model.</li>218 <li><a href="c7.html">NIP-C7</a> — chats; the sibling kind split out of <a href="29.html">NIP-29</a> in the same change.</li>219 </ul>220 </div>221222 <aside>223 <div class="cartridge">224 <div class="inner">225 <h3 class="cardhead">Spec Card</h3>226 <div class="lights"><span class="led on"></span><span class="led on"></span><span class="led on"></span></div>227 <dl>228 <dt>Status</dt><dd><span class="chip draft">draft</span><span class="chip">optional</span></dd>229 <dt>Defines</dt><dd>kind 11 threads - title tag</dd>230 <dt>Kind(s)</dt><dd>11 (replies reuse 1111)</dd>231 <dt>Requires</dt><dd><a href="01.html">NIP-01</a> - <a href="22.html">NIP-22</a></dd>232 <dt>Transport</dt><dd>WebSocket - JSON arrays</dd>233 <dt>First commit</dt><dd>2024-11-21</dd>234 <dt>Last updated</dt><dd>2026-05-28</dd>235 </dl>236 </div>237 </div>238 </aside>239 </main>240241 <nav class="navbtns">242 <a href="78.html">◀ NIP-78: Arbitrary custom app data</a>243 <a href="84.html">NIP-84: Highlights ▶</a>244 </nav>245246 <footer class="pagefoot">247 <a href="../index.html">Nostr Protocol Manual</a>248 <span class="pageno">NIP 7D / F4</span>249 </footer>250</div>251252<script src="../assets/webmcp.js" defer></script>253</body>254</html>