OverviewFilesCommitsIssuesDocsReleasesPeers

hyper-social commits / 47571b0

docs: the MVP feature list — what favela is with zero extensions loaded
Built to pass one test: the core must be a complete product with no bridge installed. Names the four agnostic components, the two extensions, and the seven things cut or deferred as atproto leakage - roughly half of what was specified today. Separates what is free to extend later (verbs, frontmatter keys, namespaces, bridges, media levels, room kinds - each free by construction) from the three that would be rewrites and so need deciding first: the address form, whether interactions are records or log entries, and the facet shape. Records the measurement that bridge:fediverse is not currently separate - it reads app.bsky.feed.post through DidPeer, so the fediverse gets a projection of a projection, already truncated at bsky's ceiling. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
47571b0b4fa40d1278ec1158af36b5951d3a2fe8
by plankatron <fleeky@gmail.com> · 2026-09-06T01:16:05.000Z

Changed files (2) +106 -0

docs/MVP.md +105 -0
……@@ -0,0 +1,105 @@
1# The MVP — what favela is when nothing is installed
2
3**Status:** proposed. Awaiting approval.
4**Date:** 2026-09-05
5**Reads with:** `SOCIAL-MODEL.md` (the model), `NAMING.md`, `EDGE-GRAPH.md`, `FAVELA-PEER.md`,
6`COMMUNITY-MODERATION.md` (moderation, already researched — used as-is).
7
8**The test this list is built to pass:** *the core must be a complete product with **zero extensions
9loaded**.* If it needs a bridge to be useful, it is not the centre.
10
11---
12
13## 1. Core — agnostic of atproto and ActivityPub
14
15| | what |
16|---|---|
17| **Identity** | one hyperident seed → N accounts (SLIP-48 `accountIndex`) → N attested devices per account. Each device has its own keypair and an `attestDevice` chain; **the seed never moves** |
18| **Rooms** | a multi-writer autobase. **Membership is the audience** — there is no visibility field to honour or forget |
19| **Records** | a markdown file: JSON frontmatter + body. Mutable; edited in place |
20| **Media** | content-addressed bytes in hyper-overlay, referenced from the markdown. The **pointer** carries the level list — no manifest file, no duplication |
21| **Interactions** | edges — like, reply, repost, follow, block, flag — written **in the room their subject lives in**, so audience is structural |
22| **Graph view** | see what was actually exchanged, per `EDGE-GRAPH.md`, with each edge's delivery state |
23| **Moderation** | room roles + `flag` signals + delisting. `COMMUNITY-MODERATION.md` already answers this; **use it, do not redesign it** |
24| **Naming** | hashes in bytes, names on screen, namespaces you subscribe to |
25| **Surface** | one SSR renderer; thin native shells display it (`favela-android` unchanged) |
26
27**Components**
28
29```
30favela-markdown the codec — a library. No storage, no network, no daemon
31favela-peer the daemon — rooms, records, identity, admission
32favela-surface the renderer it serves
33favela-android the existing shell — unchanged, it displays HTML
34```
35
36⛔ **All four are agnostic of atproto and ActivityPub.** That is the acceptance criterion, not an
37aspiration: if any of them imports an `atproto-*` or `ap-*` package, the recentring has failed.
38
39## 2. Extensions — installed and toggled by the identity manager
40
41| | is |
42|---|---|
43| **`bridge:bsky`** | the **current p2p atproto stack**, unchanged — hpp, atproto-store, atproto-room's signer, atproto-repo, the keyless membrane |
44| **`bridge:fediverse`** | **ap-bridge**, which is nearly independent already — own RSA key, own delivery, own credentials |
45
46⚠ **`bridge:fediverse` is NOT currently separate — it is downstream of `bridge:bsky`.** Measured:
47`ap-bridge/lib/records.js` imports `DidPeer` and calls
48`peer.listRecords('app.bsky.feed.post')`. The fediverse therefore receives a **projection of a
49projection** — already stripped and already truncated at bsky's 300-grapheme ceiling, on a network
50that has no such limit.
51
52⇒ **Separating it is one read**, and it makes the output strictly better rather than merely
53better-factored: AS2's `source: { content, mediaType }` can carry the **markdown verbatim** (it is
54currently hardcoded `text/plain`, `design.md` §7).
55
56## 3. ⚠ Cut or deferred — where the previous work was leaking in
57
58| carried over | why it leaks | disposition |
59|---|---|---|
60| **`collection` in the address** | atproto's `at://did/collection/rkey`. A room already says where a record is; type is a property, not a location | **cut** → `favela://<room>/<position>`, type in frontmatter |
61| **facets in `app.bsky.richtext.facet` shape** | `strip()` emits bsky's `$type` strings — atproto's data format, in the core library's output | **cut** → native `{start, end, kind, target}`; bridges translate |
62| **`net.favela.post` NSIDs** | reverse-DNS is atproto's convention | **cut** |
63| `reach` as a record field | names networks inside the record; with installable extensions that is config | **defer** |
64| `maxReach()` | built 2026-09-05; bridge-shaped and **inert with no bridges installed** | keep the code, **do not wire** |
65| `project` / `fromAS2` / `fromBsky` / loss reports | extension-only | **defer** |
66| DID, PLC, rotation keys, signing, stored projections, the double-write | every one is `bridge:bsky`'s concern | **defer entirely** |
67
68**This is roughly half of what was specified on 2026-09-05.** The specs keep it; it stops being core.
69
70## 4. Designed to extend — and what would instead be a rewrite
71
72The MVP is small on purpose, so the things we will want next must be **additions, not migrations**.
73
74**Free to add later, by construction:**
75
76| | why it is free |
77|---|---|
78| **new verbs** | an unknown verb is native-only and cannot fork a shared derivation (`interaction.md` §5.2) |
79| **new frontmatter fields** | `parse` preserves unknown keys and `serialize` orders them after the pinned ones, so an extension **never reorders — and so never changes the bytes of — a record that predates it** (tested) |
80| **new namespaces** | subscribe to one more; nothing central changes (`NAMING.md`) |
81| **new bridges** | a grant plus a co-process. Adding one adds **zero** stored files |
82| **more media levels** | the pyramid may be partial; a level is added to a pointer |
83| **new room kinds** | `maxReach` gains a row; deny-by-default means an unknown kind is already safe |
84
85⛔ **Would be a rewrite — so decide before the MVP ships:**
86
871. **The address form.** `favela://<room>/<position>` vs keeping a type segment. Records are
88 immutable in their addressing once they exist (§8 forbids rewriting).
892. **Interactions: frontmatter-only records, or pointer-valued log entries?** Changes what is on
90 disk for every edge ever written.
913. **The facet shape.** If it ships bsky-shaped it leaks forever, because every consumer will have
92 been written against it.
93
94## 5. Not in the MVP, deliberately
95
96Discovery UI, notifications UI, live updates, feeds and lists, DMs, per-network posting controls,
97offline recovery keys. Each is real product work (hyper-social #45, #28) and none of it is blocked
98by anything above — which is the point of keeping the core small.
99
100## 6. What this does not claim
101
102- It does not delete the atproto stack. It stops **loading** it. ~17,900 lines stay where they are.
103- It does not make the core faster or leaner as a goal — leanness is a consequence, and by itself a
104 bad reason (hyper-social #28: plumbing must not outrank the product).
105- It does not settle §4's three rewrite-class questions. Those need a decision, not a plan.
docs/README.md +1 -0
……@@ -17,6 +17,7 @@ P2P social layer built on Hypercore Protocol and Keet. A family of interoperable
1717| [ROADMAP.md](ROADMAP.md) | Evolutionary path from godot-keet to hyper-social — 8 phases, what exists, what to build |
1818| [AUTO-DISCOVERY.md](AUTO-DISCOVERY.md) | Layered auto-discovery design — 5 layers replacing hardcoded registries, privacy analysis |
1919| [AUTO-DISCOVERY-SPEC.md](AUTO-DISCOVERY-SPEC.md) | Implementation spec — code changes for keet-daemon, godot-keet, bridges (~1,400 LOC) |
20| [MVP.md](MVP.md) | **Proposed**: what favela is with zero extensions loaded — the core feature list, what was cut as atproto leakage, and which extensions are free later vs which are rewrites. |
2021| [NAMING.md](NAMING.md) | Hashes are unique, names are not global — there are global namespaces you can subscribe to. Zooko's triangle, four layers, and why only keys go in the bytes. |
2122| [FAVELA-PEER.md](FAVELA-PEER.md) | Scope for the peer — the fission of hyper-proto-peer, its measured baseline, and the four things that must be measured before building. |
2223| [SOCIAL-MODEL.md](SOCIAL-MODEL.md) | **Latest**: our own social model — rooms as scope/audience/governance, visibility as a place not a field, and how it translates outward to AP/atproto/IRC. Sits above favela and every bridge. |