loom
What Loom is Loom is a human-in-the-loop interface for language models that lets you generate, navigate, and visualize branching “multiverses” of text. You write a prompt, spawn many continuations, and curate them as a tree, treating the model as a simulator while you steer. Moire — Loom: interface to the multiverse cyborgism.wiki — Loom oai_citation:0‡generative.ink oai_citation:1‡Cyborgism
Core interface Two primary views: Read mode renders the ancestry as a single linear story, while Visualize mode shows the multiverse as a node-link tree where you expand, collapse, split, and merge. Each node holds text plus metadata. There is also a “block multiverse” pane that plots probability mass across many near-future token paths, with zoom-in renormalization on click. Moire — Loom: interface to the multiverse Moire — Block multiverse visualizations oai_citation:2‡generative.ink
Notable UX details The desktop app exposes extensive hotkeys for navigation, generation, and topology edits, supports per-node “memory,” bookmarks, chapters, JSON import-export, and multi-tab trees. The block multiverse panel has a Wavefunction button and supports “propagate,” zoom-renormalize, and probability cutoff depth. GitHub — socketteer/loom Moire — Block multiverse visualizations oai_citation:3‡GitHub oai_citation:4‡generative.ink
Data model Trees are saved as JSON. Node metadata records prompt, response, model id, token logprobs, and counterfactual logprobs, which the UI can inspect per node. Moire — Loom: interface to the multiverse GitHub — socketteer/loom oai_citation:5‡generative.ink oai_citation:6‡GitHub
Implementation snapshot
The reference app is Python-based. Setup instructions include installing Tkinter, running main.py, and optionally using Docker. Providers are pluggable via settings, with OpenAI by default and local inference supported through an OpenAI-compatible llama-cpp server. Repo structure includes controller, model, view, and components directories. GitHub — socketteer/loom oai_citation:7‡GitHub
CLI and alt implementations GitLoom is a command-line variant that stores branches as Git branches and currently targets Claude via the Anthropic API. CLooI is a Node.js “command loom” that manages branching chat transcripts, with commands to rewind, fork, export JSON, and more. Worldspider adds VS Code completions that pair well with Loom-style curation. GitHub — socketteer/gitloom GitHub — socketteer/clooi GitHub — socketteer/worldspider oai_citation:8‡GitHub
Why people use it Compared with a single best-of-N picker, Loom makes the branching structure first-class so an operator can explore, stabilize, and merge narratives or analyses. This is why it shows up in cyborgism discussions and why external writeups describe it as a branching-tree writer for GPT. cyborgism.wiki — Loom Astral Codex Ten — Janus’ GPT Wrangling oai_citation:9‡Cyborgism oai_citation:10‡Astral Codex Ten
Quickstart See the repo for hotkeys and complete instructions. Minimal paths are shown below. GitHub — socketteer/loom oai_citation:11‡GitHub
#+BEGIN_SRC bash
Python path
Section titled “Python path”conda create -n pyloom python=3.10 && conda activate pyloom pip install -r requirements-mac.txt # or requirements.txt on Linux export OPENAI_API_KEY=… # or configure llama-cpp server (port 8009) python main.py
Docker path (Linux)
Section titled “Docker path (Linux)”make build && make run #+END_SRC
Architecture sketch #+BEGIN_mermaid flowchart LR UI[UI: Read view · Visualize view · Block multiverse] —> CTRL[Controller] CTRL —> GEN[Generation adapters: OpenAI · llama-cpp server] CTRL —> STORE[Tree store: JSON files] UI <—> META[Node metadata: prompt · response · logprobs] #+END_mermaid GitHub — socketteer/loom Moire — Block multiverse visualizations oai_citation:12‡GitHub oai_citation:13‡generative.ink
BLOCK A
Goal You want Loom’s “each rollout” mental model to behave like a DAG rather than a strict tree, so branches can later rejoin or reuse shared continuations without duplication. The sources below describe the current tree-first UI and give us the primitives we need to extend it toward DAG semantics. Moire — Loom: interface to the multiverse GitHub — socketteer/loom Moire — Block multiverse visualizations oai_citation:0‡generative.ink oai_citation:1‡GitHub
Reality check: what Loom ships today The reference app exposes Read and Visualize modes, generates N children from any node, and supports topology edits. Hotkeys include “Merge with Parent,” “Merge with children,” and “Change parent,” plus “Combine trees” for I/O. This proves the UI already supports structural moves beyond simple append-only branching, although storage is presented as JSON trees. GitHub — socketteer/loom Moire — Loom: interface to the multiverse oai_citation:2‡GitHub oai_citation:3‡generative.ink
Where DAGs enter the picture A DAG allows a node to have multiple incoming edges. In authoring terms, you can splice two branches back into a shared continuation or deduplicate repeated segments by linking to an existing node instead of cloning it. Loom’s “merge” and “change parent” affordances map cleanly to reparenting and consolidation, which are the two moves needed for practical DAG work. The missing piece is letting a node keep more than one parent in the data model. GitHub — socketteer/loom oai_citation:4‡GitHub
UI blueprint: DAG-first Visualize view
- Node identity: visually mark nodes that appear in more than one lineage. Use a halo or badge with a count to indicate multiple parents. Tooltips show the parent list and edge labels. Moire — Loom: interface to the multiverse GitHub — socketteer/loom oai_citation:5‡generative.ink oai_citation:6‡GitHub
- Edge semantics: label edges with operation and parameters, for example “generate(k=4, T=0.8)” or “splice-from #123.” This mirrors Loom’s generation and edit dialogs and keeps provenance legible. GitHub — socketteer/loom oai_citation:7‡GitHub
- Read mode over DAG: select a path by parent-pointer traversal or by checkpoint bookmarks. If a node has multiple parents, choose one parent for linearization or show a “choose lineage” picker. GitHub — socketteer/loom oai_citation:8‡GitHub
- Block multiverse sidecar: keep the probability-panel as the right sidebar. Clicking a block still renormalizes and focuses the future conditioned on the chosen partial sequence, which now attaches as a new edge into the active node. Moire — Block multiverse visualizations oai_citation:9‡generative.ink
Data model shift: from tree to DAG Replace a single parent pointer with a list of incoming edges, and canonicalize node identity so identical states dedupe. Minimal keys: normalized text so far, hidden memory at that cursor, model id, and generation settings. When a rollout produces a continuation whose canonical key already exists, add an edge to that node rather than cloning. Store edges with metadata for provenance. Moire — Loom: interface to the multiverse GitHub — socketteer/loom oai_citation:10‡generative.ink oai_citation:11‡GitHub
#+BEGIN_SRC python
Pseudocode: DAG node and edge records
Section titled “Pseudocode: DAG node and edge records”class Node: id: str # content-addressed or UUID text_prefix: str # canonicalized prefix memory: dict # per-node hidden memory model_id: str logprobs: dict | None meta: dict # misc annotations
class Edge: id: str parent: str # Node.id child: str # Node.id op: str # “generate” | “splice” | “edit” params: dict # n, temperature, top_p, prompt_delta, etc. created_at: str
def canonical_key(text_prefix, memory, model_id): return hash(normalize(text_prefix) + freeze(memory) + model_id) #+END_SRC GitHub — socketteer/loom oai_citation:12‡GitHub
On-rollout behavior Every time you hit Generate, compute the canonical key for each candidate child. If the key matches an existing node, link it by adding a new Edge. If not, allocate a Node and connect it. “Merge with children” becomes a metadata-preserving text merge plus edge compaction. “Change parent” adds a new incoming edge rather than moving the node, which is what enables true DAG reuse. GitHub — socketteer/loom oai_citation:13‡GitHub
#+BEGIN_mermaid flowchart LR A[“Root”] —>|generate(k=3)| B[“Intro v1”] A —>|generate| C[“Intro v2”] B —>|generate| D[“Scene A”] C —>|generate| E[“Scene B”] D —>|splice existing| F[“Shared Ending”] E —>|splice existing| F #+END_mermaid Moire — Loom: interface to the multiverse GitHub — socketteer/loom oai_citation:14‡generative.ink oai_citation:15‡GitHub
How this aligns with the probability UI The block multiverse panel already plots near-future token sequences and supports zoom renormalization. In a DAG rollout, “Propagate” adds candidate sequences as edges from the focused node, and “zoom” simply conditions on a particular partial sequence before you attach it. This keeps the math and the UI consistent with the multiverse framing. Moire — Block multiverse visualizations oai_citation:16‡generative.ink
Storage and export JSON files that previously stored a tree can store a DAG by adding an edges array and by removing the invariant that nodes have exactly one parent. Backward compatibility is easy: write a loader that collapses multiple incoming edges down to the first parent when you need a tree. GitHub — socketteer/loom oai_citation:17‡GitHub
Curation metrics on DAGs Janus’ curation metric depends on branching factor and the number of decision points. Extend it by counting reused nodes and edge insertions, then report: unique nodes, edges, entropy of branching choices, and reuse ratio. This exposes how much you explored vs how much you reused. Moire — Quantifying curation oai_citation:18‡generative.ink
Practical workflow today Even without changing code you can approximate a DAG in Loom: keep one “library” tree with reusable passages, then use “Combine trees” and “Change parent” to graft those passages into your working tree. The tradeoff is duplication on disk rather than true node sharing. GitHub — socketteer/loom oai_citation:19‡GitHub
Why this still fits cyborgism A DAG-first Loom increases human steering power. You can explore many futures, pull them together when they converge, and preserve provenance at every splice. That is the cyborg pattern: simulator breadth with human judgment selecting and welding paths. LessWrong — Cyborgism Astral Codex Ten — Janus’ GPT Wrangling oai_citation:20‡LessWrong oai_citation:21‡Astral Codex Ten
References for features and mental model For demo notes that mention “merge parent,” see the Loom post. For hotkeys and topology edits, see the README. For probability workflow see the block multiverse page and “multiverse generators.” Moire — Loom: interface to the multiverse GitHub — socketteer/loom Moire — Block multiverse visualizations Moire — Language models are multiverse generators oai_citation:22‡generative.ink oai_citation:23‡GitHub