@real-life/trust-protocol 0.3.2 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (264) hide show
  1. package/CHANGELOG.md +32 -0
  2. package/README.md +187 -78
  3. package/dist/ack.d.ts +84 -0
  4. package/dist/ack.d.ts.map +1 -0
  5. package/dist/ack.js +114 -0
  6. package/dist/ack.js.map +1 -0
  7. package/dist/adapters/vti-mediator.d.ts +154 -0
  8. package/dist/adapters/vti-mediator.d.ts.map +1 -0
  9. package/dist/adapters/vti-mediator.js +621 -0
  10. package/dist/adapters/vti-mediator.js.map +1 -0
  11. package/dist/anchor.d.ts +226 -0
  12. package/dist/anchor.d.ts.map +1 -0
  13. package/dist/anchor.js +347 -0
  14. package/dist/anchor.js.map +1 -0
  15. package/dist/{holder.d.ts → carrier-holder.d.ts} +1 -1
  16. package/dist/carrier-holder.d.ts.map +1 -0
  17. package/dist/{holder.js → carrier-holder.js} +5 -4
  18. package/dist/carrier-holder.js.map +1 -0
  19. package/dist/carrier-identity.js +4 -4
  20. package/dist/carrier-identity.js.map +1 -1
  21. package/dist/carrier.d.ts.map +1 -1
  22. package/dist/carrier.js +4 -3
  23. package/dist/carrier.js.map +1 -1
  24. package/dist/ceremony.d.ts +3 -2
  25. package/dist/ceremony.d.ts.map +1 -1
  26. package/dist/ceremony.js +16 -26
  27. package/dist/ceremony.js.map +1 -1
  28. package/dist/codec.d.ts +46 -0
  29. package/dist/codec.d.ts.map +1 -0
  30. package/dist/codec.js +410 -0
  31. package/dist/codec.js.map +1 -0
  32. package/dist/continuity.d.ts +67 -0
  33. package/dist/continuity.d.ts.map +1 -0
  34. package/dist/continuity.js +110 -0
  35. package/dist/continuity.js.map +1 -0
  36. package/dist/core.d.ts +4 -0
  37. package/dist/core.d.ts.map +1 -1
  38. package/dist/core.js.map +1 -1
  39. package/dist/crypto.d.ts +23 -7
  40. package/dist/crypto.d.ts.map +1 -1
  41. package/dist/crypto.js +54 -20
  42. package/dist/crypto.js.map +1 -1
  43. package/dist/delivery.d.ts +31 -3
  44. package/dist/delivery.d.ts.map +1 -1
  45. package/dist/delivery.js +75 -28
  46. package/dist/delivery.js.map +1 -1
  47. package/dist/encounter/ceremony.d.ts +37 -0
  48. package/dist/encounter/ceremony.d.ts.map +1 -0
  49. package/dist/encounter/ceremony.js +662 -0
  50. package/dist/encounter/ceremony.js.map +1 -0
  51. package/dist/encounter.d.ts +91 -1
  52. package/dist/encounter.d.ts.map +1 -1
  53. package/dist/encounter.js +191 -12
  54. package/dist/encounter.js.map +1 -1
  55. package/dist/engine.d.ts +291 -0
  56. package/dist/engine.d.ts.map +1 -0
  57. package/dist/engine.js +1395 -0
  58. package/dist/engine.js.map +1 -0
  59. package/dist/entropy.d.ts +28 -0
  60. package/dist/entropy.d.ts.map +1 -0
  61. package/dist/entropy.js +96 -0
  62. package/dist/entropy.js.map +1 -0
  63. package/dist/events.d.ts +177 -0
  64. package/dist/events.d.ts.map +1 -0
  65. package/dist/events.js +2 -0
  66. package/dist/events.js.map +1 -0
  67. package/dist/fixtures.d.ts +30 -0
  68. package/dist/fixtures.d.ts.map +1 -0
  69. package/dist/fixtures.js +155 -0
  70. package/dist/fixtures.js.map +1 -0
  71. package/dist/forge.d.ts +47 -0
  72. package/dist/forge.d.ts.map +1 -0
  73. package/dist/forge.js +20 -0
  74. package/dist/forge.js.map +1 -0
  75. package/dist/group-star.d.ts +251 -0
  76. package/dist/group-star.d.ts.map +1 -0
  77. package/dist/group-star.js +348 -0
  78. package/dist/group-star.js.map +1 -0
  79. package/dist/holder-api.d.ts +137 -0
  80. package/dist/holder-api.d.ts.map +1 -0
  81. package/dist/holder-api.js +132 -0
  82. package/dist/holder-api.js.map +1 -0
  83. package/dist/holder-state-v1.d.ts +801 -0
  84. package/dist/holder-state-v1.d.ts.map +1 -0
  85. package/dist/holder-state-v1.js +2 -0
  86. package/dist/holder-state-v1.js.map +1 -0
  87. package/dist/identity-state.d.ts +43 -0
  88. package/dist/identity-state.d.ts.map +1 -0
  89. package/dist/identity-state.js +345 -0
  90. package/dist/identity-state.js.map +1 -0
  91. package/dist/identity.d.ts +24 -2
  92. package/dist/identity.d.ts.map +1 -1
  93. package/dist/identity.js +70 -11
  94. package/dist/identity.js.map +1 -1
  95. package/dist/index.d.ts +26 -1
  96. package/dist/index.d.ts.map +1 -1
  97. package/dist/index.js +77 -29
  98. package/dist/index.js.map +1 -1
  99. package/dist/internal.d.ts +36 -0
  100. package/dist/internal.d.ts.map +1 -0
  101. package/dist/internal.js +22 -0
  102. package/dist/internal.js.map +1 -0
  103. package/dist/introduction/holder.d.ts +18 -0
  104. package/dist/introduction/holder.d.ts.map +1 -0
  105. package/dist/introduction/holder.js +757 -0
  106. package/dist/introduction/holder.js.map +1 -0
  107. package/dist/introduction.d.ts +101 -0
  108. package/dist/introduction.d.ts.map +1 -0
  109. package/dist/introduction.js +132 -0
  110. package/dist/introduction.js.map +1 -0
  111. package/dist/invariants.d.ts +43 -0
  112. package/dist/invariants.d.ts.map +1 -0
  113. package/dist/invariants.js +883 -0
  114. package/dist/invariants.js.map +1 -0
  115. package/dist/keys-seed.d.ts +7 -0
  116. package/dist/keys-seed.d.ts.map +1 -0
  117. package/dist/keys-seed.js +133 -0
  118. package/dist/keys-seed.js.map +1 -0
  119. package/dist/log-memory.d.ts +12 -0
  120. package/dist/log-memory.d.ts.map +1 -0
  121. package/dist/log-memory.js +101 -0
  122. package/dist/log-memory.js.map +1 -0
  123. package/dist/membership/holder.d.ts +35 -0
  124. package/dist/membership/holder.d.ts.map +1 -0
  125. package/dist/membership/holder.js +852 -0
  126. package/dist/membership/holder.js.map +1 -0
  127. package/dist/membership.d.ts +92 -0
  128. package/dist/membership.d.ts.map +1 -0
  129. package/dist/membership.js +157 -0
  130. package/dist/membership.js.map +1 -0
  131. package/dist/ports.d.ts +237 -0
  132. package/dist/ports.d.ts.map +1 -0
  133. package/dist/ports.js +2 -0
  134. package/dist/ports.js.map +1 -0
  135. package/dist/profile.d.ts +56 -0
  136. package/dist/profile.d.ts.map +1 -0
  137. package/dist/profile.js +193 -0
  138. package/dist/profile.js.map +1 -0
  139. package/dist/prompts.d.ts +14 -0
  140. package/dist/prompts.d.ts.map +1 -0
  141. package/dist/prompts.js +69 -0
  142. package/dist/prompts.js.map +1 -0
  143. package/dist/receive.d.ts +133 -0
  144. package/dist/receive.d.ts.map +1 -0
  145. package/dist/receive.js +298 -0
  146. package/dist/receive.js.map +1 -0
  147. package/dist/results.d.ts +158 -0
  148. package/dist/results.d.ts.map +1 -0
  149. package/dist/results.js +21 -0
  150. package/dist/results.js.map +1 -0
  151. package/dist/schemas.d.ts.map +1 -1
  152. package/dist/schemas.js +42 -38
  153. package/dist/schemas.js.map +1 -1
  154. package/dist/sha256.d.ts +3 -0
  155. package/dist/sha256.d.ts.map +1 -0
  156. package/dist/sha256.js +69 -0
  157. package/dist/sha256.js.map +1 -0
  158. package/dist/star.d.ts +31 -0
  159. package/dist/star.d.ts.map +1 -0
  160. package/dist/star.js +56 -0
  161. package/dist/star.js.map +1 -0
  162. package/dist/state-builder.d.ts +42 -0
  163. package/dist/state-builder.d.ts.map +1 -0
  164. package/dist/state-builder.js +100 -0
  165. package/dist/state-builder.js.map +1 -0
  166. package/dist/state.d.ts +853 -0
  167. package/dist/state.d.ts.map +1 -0
  168. package/dist/state.js +36 -0
  169. package/dist/state.js.map +1 -0
  170. package/dist/store-contract.d.ts +11 -0
  171. package/dist/store-contract.d.ts.map +1 -0
  172. package/dist/store-contract.js +189 -0
  173. package/dist/store-contract.js.map +1 -0
  174. package/dist/store-memory.d.ts +8 -0
  175. package/dist/store-memory.d.ts.map +1 -0
  176. package/dist/store-memory.js +17 -0
  177. package/dist/store-memory.js.map +1 -0
  178. package/dist/testing.d.ts +22 -0
  179. package/dist/testing.d.ts.map +1 -0
  180. package/dist/testing.js +21 -0
  181. package/dist/testing.js.map +1 -0
  182. package/dist/trust/continuity.d.ts +71 -0
  183. package/dist/trust/continuity.d.ts.map +1 -0
  184. package/dist/trust/continuity.js +1216 -0
  185. package/dist/trust/continuity.js.map +1 -0
  186. package/dist/trust/duties.d.ts +67 -0
  187. package/dist/trust/duties.d.ts.map +1 -0
  188. package/dist/trust/duties.js +179 -0
  189. package/dist/trust/duties.js.map +1 -0
  190. package/dist/trust/entries.d.ts +139 -0
  191. package/dist/trust/entries.d.ts.map +1 -0
  192. package/dist/trust/entries.js +694 -0
  193. package/dist/trust/entries.js.map +1 -0
  194. package/dist/trust/group-star.d.ts +43 -0
  195. package/dist/trust/group-star.d.ts.map +1 -0
  196. package/dist/trust/group-star.js +188 -0
  197. package/dist/trust/group-star.js.map +1 -0
  198. package/dist/trust/mapping.d.ts +56 -0
  199. package/dist/trust/mapping.d.ts.map +1 -0
  200. package/dist/trust/mapping.js +584 -0
  201. package/dist/trust/mapping.js.map +1 -0
  202. package/dist/trust/profile.d.ts +25 -0
  203. package/dist/trust/profile.d.ts.map +1 -0
  204. package/dist/trust/profile.js +249 -0
  205. package/dist/trust/profile.js.map +1 -0
  206. package/dist/trust/star.d.ts +208 -0
  207. package/dist/trust/star.d.ts.map +1 -0
  208. package/dist/trust/star.js +588 -0
  209. package/dist/trust/star.js.map +1 -0
  210. package/dist/trust/state.d.ts +83 -0
  211. package/dist/trust/state.d.ts.map +1 -0
  212. package/dist/trust/state.js +154 -0
  213. package/dist/trust/state.js.map +1 -0
  214. package/dist/util-freeze.d.ts +3 -0
  215. package/dist/util-freeze.d.ts.map +1 -0
  216. package/dist/util-freeze.js +11 -0
  217. package/dist/util-freeze.js.map +1 -0
  218. package/dist/views.d.ts +147 -0
  219. package/dist/views.d.ts.map +1 -0
  220. package/dist/views.js +268 -0
  221. package/dist/views.js.map +1 -0
  222. package/dist/visibility.d.ts +5 -5
  223. package/dist/visibility.d.ts.map +1 -1
  224. package/dist/visibility.js +22 -28
  225. package/dist/visibility.js.map +1 -1
  226. package/dist/wire.d.ts +178 -84
  227. package/dist/wire.d.ts.map +1 -1
  228. package/dist/wire.js.map +1 -1
  229. package/package.json +56 -10
  230. package/schemas/holder-state-v1.schema.json +3880 -0
  231. package/dist/holder.d.ts.map +0 -1
  232. package/dist/holder.js.map +0 -1
  233. package/dist/probe/acks.d.ts +0 -27
  234. package/dist/probe/acks.d.ts.map +0 -1
  235. package/dist/probe/acks.js +0 -152
  236. package/dist/probe/acks.js.map +0 -1
  237. package/dist/probe/continuity.d.ts +0 -20
  238. package/dist/probe/continuity.d.ts.map +0 -1
  239. package/dist/probe/continuity.js +0 -805
  240. package/dist/probe/continuity.js.map +0 -1
  241. package/dist/probe/deps.d.ts +0 -61
  242. package/dist/probe/deps.d.ts.map +0 -1
  243. package/dist/probe/deps.js +0 -54
  244. package/dist/probe/deps.js.map +0 -1
  245. package/dist/probe/encounter.d.ts +0 -26
  246. package/dist/probe/encounter.d.ts.map +0 -1
  247. package/dist/probe/encounter.js +0 -938
  248. package/dist/probe/encounter.js.map +0 -1
  249. package/dist/probe/introduce.d.ts +0 -62
  250. package/dist/probe/introduce.d.ts.map +0 -1
  251. package/dist/probe/introduce.js +0 -306
  252. package/dist/probe/introduce.js.map +0 -1
  253. package/dist/probe/membership.d.ts +0 -96
  254. package/dist/probe/membership.d.ts.map +0 -1
  255. package/dist/probe/membership.js +0 -467
  256. package/dist/probe/membership.js.map +0 -1
  257. package/dist/probe/trust.d.ts +0 -156
  258. package/dist/probe/trust.d.ts.map +0 -1
  259. package/dist/probe/trust.js +0 -1233
  260. package/dist/probe/trust.js.map +0 -1
  261. package/dist/probe.d.ts +0 -7
  262. package/dist/probe.d.ts.map +0 -1
  263. package/dist/probe.js +0 -42
  264. package/dist/probe.js.map +0 -1
@@ -1 +0,0 @@
1
- {"version":3,"file":"introduce.js","sourceRoot":"","sources":["../../src/probe/introduce.ts"],"names":[],"mappings":"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","sourcesContent":["// introduce.mjs — the introduction act, PROBE for the §8 recast.\n// DOM-free, deterministic-capable, on rltp-core + rltp-crypto.\n//\n// THE MODEL (Anton's cuts, 25.08. — supersedes converged §8@1's\n// requester-initiated ferry):\n// 1. MEDIATOR-INITIATED: only M can point at both parties (a requester\n// has no in-app handle for the target; the verbal wish lives in real\n// life). M opens a contact, taps \"Vorstellen…\", picks the other.\n// 2. INDEPENDENT RELEASE (ceremony-parallel): both sides receive the\n// offer simultaneously; EACH consent releases that person's OWN\n// fresh card — one-sided outcomes stay first-class (◇), mutuality\n// arises when both have released (⇄).\n// 3. RENDEZVOUS DROP, not ferry: the offers carry a per-act secret;\n// consenting devices deposit their sealed card at a derived topic\n// and fetch the counterpart's — THE MEDIATOR IS NEVER NEEDED AGAIN\n// after the initiating act (airplane-mode scenario). The drop is a\n// PORT (put/get by derived topic, opaque blobs, TTL); relay-topic /\n// DHT / iroh node / M's device are adapters below it.\n// 4. The mediator VOUCHER binds the ACT, not the card (the drop model\n// makes card-digest vouchers impossible — M never sees the cards;\n// harvest finding for the recast). Each offer carries the voucher\n// FOR THE COUNTERPART, signed under M's channel anchor toward that\n// counterpart; the consenting side deposits it beside its card, so\n// the fetcher verifies \"this introduction came from MY M\".\n// Trust: M remains the authenticity anchor of the introduction either\n// way; the systemic control is the first real encounter (◇→✓,\n// continuity). Deniability/linkability hardening is RECAST WORK — this\n// probe signs plainly and says so.\nimport { jcs, makeValidator, tsec } from '../core.js'\nimport { SCHEMAS } from '../schemas.js'\nconst VAL = makeValidator(SCHEMAS)\nimport * as C from './deps.js'\nimport type { Person } from './deps.js'\nimport { snapshotPriors } from './continuity.js'\n\nconst te = new TextEncoder(), td = new TextDecoder()\nconst S = globalThis.crypto.subtle\n\n// ── people ──────────────────────────────────────────────────────────────\nexport function createPerson (name: string, rootIkm?: Uint8Array): Person {\n return {\n name,\n rootIkm: rootIkm ?? C.rand(64),\n contexts: new Map(), // anchor/keyAgreement -> pair ctx (fresh-always)\n contacts: new Map(), // counterpart anchor -> { name, card, provenance, state, channel }\n inbox: [], // received offers/invites awaiting the human\n groups: new Map(), // genesisDigest -> group state (Stage C, groups.mjs)\n online: true,\n queue: [], // actions deferred while offline (device ferry of ONESELF)\n log: [],\n // the demo community's genesis — a PROBE FIXTURE the person carries,\n // so the strict identity layer never needs a default\n communityGenesis: C.COMMUNITY_GENESIS,\n }\n}\nconst say = (p: Person, m: string) => p.log.push(m)\nexport async function freshCtx (p: Person, nonce?: Uint8Array) {\n const ctx = await C.pairContext(p.rootIkm, nonce ?? C.rand(32))\n p.contexts.set(ctx.anchor, ctx); p.contexts.set(ctx.keyAgreement, ctx)\n return ctx\n}\n\n// ── die Zeremonie in SCHRITTEN — die App-Choreografie (Encounter 5.2):\n// Code zeigen → scannen → BEIDE bestätigen bewusst; erst dann entsteht\n// das Enactment. Der gezeigte Anker ist immer frisch (4.4) und verrät\n// nichts — wer ihn wirklich trifft, klärt hinterher die §6a-Probe.\nexport async function ceremonyShow (p: Person, ent: any = {}) {\n const ctx = await freshCtx(p, ent.nonce)\n return { ctx, ch: C.challengeOf(ent.ch ?? C.rand(17)) }\n}\nexport async function ceremonyComplete (a: Person, sa: any, b: Person, sb: any, when: number) {\n const ctxA = sa.ctx, ctxB = sb.ctx, chA = sa.ch, chB = sb.ch\n const bind = await C.binding(C.CEREMONY, chA, chB)\n const iso = C.iso(when)\n const cardA = await C.signCard(ctxA, C.cardBody(ctxA, { name: a.name, challenge: { value: chA, issuedAt: iso } }), iso)\n const cardB = await C.signCard(ctxB, C.cardBody(ctxB, { name: b.name, challenge: { value: chB, issuedAt: iso } }), iso)\n const credA = await C.issueCredential(ctxA, ctxB.anchor, C.CEREMONY, chB, bind, iso)\n const credB = await C.issueCredential(ctxB, ctxA.anchor, C.CEREMONY, chA, bind, iso)\n const priorsA = snapshotPriors(a), priorsB = snapshotPriors(b) // Schnappschuss VOR dem frischen Tupel (6a)\n a.contacts.set(ctxB.anchor, { name: b.name, card: cardB, credential: credA, provenance: 'ceremony', state: '✓', since: iso, channel: { own: ctxA, counterpartKa: cardB.keyAgreement }, priorCands: priorsA })\n b.contacts.set(ctxA.anchor, { name: a.name, card: cardA, credential: credB, provenance: 'ceremony', state: '✓', since: iso, channel: { own: ctxB, counterpartKa: cardA.keyAgreement }, priorCands: priorsB })\n say(a, `Zeremonie mit ${b.name}: ✓ verifiziert (frisches Tupel)`)\n say(b, `Zeremonie mit ${a.name}: ✓ verifiziert (frisches Tupel)`)\n return { ctxA, ctxB, bind }\n}\n// Test-Shortcut: beide Schritte in einem Zug (Vorgeschichte in Szenarien)\nexport async function ceremony (a: Person, b: Person, when: number, ent: any = {}) {\n return ceremonyComplete(a, await ceremonyShow(a, { nonce: ent.nonceA, ch: ent.chA }),\n b, await ceremonyShow(b, { nonce: ent.nonceB, ch: ent.chB }), when)\n}\n\n// ── the rendezvous drop PORT: put/get by derived topic, opaque blobs ────\nexport function createDrop () {\n return {\n slots: new Map<string, string>(), // topic -> b64u blob\n log: [] as any[], // { n, op, topic, by }\n put (topic: string, blob: string, by: string) { this.slots.set(topic, blob); this.log.push({ n: this.log.length, op: 'put', topic: topic.slice(0, 16) + '…', by }) },\n get (topic: string, by: string) { this.log.push({ n: this.log.length, op: 'get', topic: topic.slice(0, 16) + '…', by }); return this.slots.get(topic) ?? null },\n }\n}\nconst dropTopic = async (secret: Uint8Array, dir: string) => C.b64uOf(await C.hkdf(secret, 'rltp/introduce/topic/' + dir))\nconst dropKey = async (secret: Uint8Array, dir: string) => S.importKey('raw', await C.hkdf(secret, 'rltp/introduce/key/' + dir), { name: 'AES-GCM' }, false, ['encrypt', 'decrypt'])\nasync function dropSeal (secret: Uint8Array, dir: string, obj: any, nonce: Uint8Array | undefined) {\n const n = nonce ?? C.rand(12)\n const ct = new Uint8Array(await S.encrypt({ name: 'AES-GCM', iv: n }, await dropKey(secret, dir), te.encode(jcs(obj))))\n return C.b64uOf(C.cat(n, ct))\n}\nasync function dropOpen (secret: Uint8Array, dir: string, blob: string) {\n try {\n const raw = C.fromB64u(blob)\n const pt = await S.decrypt({ name: 'AES-GCM', iv: raw.subarray(0, 12) }, await dropKey(secret, dir), raw.subarray(12))\n return JSON.parse(td.decode(new Uint8Array(pt)))\n } catch { return null }\n}\n\n// ── 1. the mediator's ONE act: \"Vorstellen…\" ────────────────────────────\n// Produces two sealed offers over the EXISTING channels. After this, the\n// mediator's device is done — nothing below ever touches it again.\n// Introducible are ✓ AND ⇄ contacts (Anton's cut, 24.08.) — but the offer\n// carries the mediator's OWN provenance toward the peer (met | introduced,\n// the vouch@2 vocabulary): the recipient decides informed, and a chain of\n// introductions never washes amber to blue — reach spreads, verification\n// does not. ◇ cannot mediate: no own channel context exists.\nexport async function introduce (m: Person, anchorA: string, anchorB: string, when: number, ent: any = {}) {\n const A = m.contacts.get(anchorA), B = m.contacts.get(anchorB)\n if (!A || !B) throw new Error('mediator does not hold both contacts')\n if (!A.channel?.own || !B.channel?.own) throw new Error('introducing needs a mutual channel to BOTH (◇ cannot mediate)')\n const secret = ent.secret ?? C.rand(32)\n const act = await C.digestBytes(secret) // act id: public handle, secret stays sealed\n const iso = C.iso(when)\n const provOf = (c: any) => c.provenance === 'ceremony' ? 'met' : 'introduced'\n const mk = async (mine: any, other: any, dir: string) => {\n // voucher FOR the counterpart, under M's channel anchor toward the counterpart;\n // it carries M's self-attested provenance toward the person it vouches for\n const voucher = await C.diSign(other.channel.own, { type: 'introduction-voucher@2', act, direction: dir, provenance: provOf(mine), issuedAt: iso }, iso)\n const offer = await C.diSign(mine.channel.own, {\n type: 'introduction-offer@2', act, direction: dir, issuedAt: iso,\n peer: { name: other.name, provenance: provOf(other) }, // M's LOCAL memory — words + honest basis, no anchors\n rendezvous: C.b64uOf(secret),\n voucherForCounterpart: voucher,\n }, iso)\n return C.seal(offer, mine.channel.counterpartKa, { ephSeed: ent.ephSeed, nonce: ent.sealNonce })\n }\n const envA = await mk(A, B, 'a')\n const envB = await mk(B, A, 'b')\n say(m, `Vorstellen: ${A.name} ⇠⇢ ${B.name} — zwei Angebote versiegelt, Akt ${act.slice(0, 12)}… · mein Gerät ist ab jetzt nicht mehr nötig`)\n return { act, offers: [{ to: anchorA, env: envA }, { to: anchorB, env: envB }] }\n}\n\n// ── 2. receiving the offer (each side, independently) ───────────────────\nexport async function receiveOffer (p: Person, env: any) {\n const opened = await C.openEnvelope(p, env) // Stufen 1–4, Cache-Lesung\n if (opened.duplicate) return { duplicate: true } // kein Fehler: der Effekt ist längst da\n if (opened.error) return { error: opened.error }\n const r = await receiveOfferInner(p, env, opened.doc)\n if (!(r as any).error) C.effectDone(p, opened.digest)\n return r\n}\nasync function receiveOfferInner (p: Person, env: any, offer: any) {\n // form BEFORE fields (M-3; value forms per review 9, P-B1): the offer\n // binds ITS artifact form before anything enters the inbox\n if (!C.shaped(offer, { type: 'string', act: 'string', direction: 'string', rendezvous: 'string', issuedAt: 'string', peer: 'object', proof: 'object' })\n || offer.type !== 'introduction-offer@2'\n || (offer.direction !== 'a' && offer.direction !== 'b')\n || !C.calOK(offer.issuedAt)\n || !C.shaped(offer.peer, { name: 'string', provenance: 'string' })\n || (offer.peer.provenance !== 'met' && offer.peer.provenance !== 'introduced')) return { error: 'malformed offer' }\n try { if (C.fromB64u(offer.rendezvous).length !== 32) return { error: 'malformed offer' } }\n catch { return { error: 'malformed offer' } }\n // der mitreisende Voucher ist Teil der Offer-Form (Review 10, P-B1-Rest):\n // er wird beim Consent unbesehen ins Drop-Paket übernommen\n const v = offer.voucherForCounterpart\n if (!C.shaped(v, { type: 'string', act: 'string', direction: 'string', provenance: 'string', issuedAt: 'string', proof: 'object' })\n || v.type !== 'introduction-voucher@2' || v.act !== offer.act || !C.calOK(v.issuedAt)) return { error: 'malformed offer' }\n const from = [...p.contacts.entries()].find(([anchor, c]) => c.channel && offer.proof?.verificationMethod?.startsWith(anchor))\n if (!from) return { error: 'offer not from a held contact' }\n if (!(await C.diVerify(offer, from[0]))) return { error: 'offer proof fails' }\n const entry = { offer, mediator: from[1].name, mediatorAnchor: from[0], decided: false }\n p.inbox.push(entry)\n say(p, `${from[1].name} möchte dich mit ${offer.peer.name} verbinden`)\n return { entry }\n}\n\n// ── 3. consent: release the OWN card — independent of the other side.\n// Releasing and receiving are SEPARATE (ceremony-parallel): consent only\n// controls the own card; the counterpart's card arrives via sync\n// (checkDrop) whether or not this side ever consents.\nexport async function consent (p: Person, entry: any, drop: any, when: number, ent: any = {}) {\n // the release happens once: a repeated consent keeps the released context\n // and card (a new pair would orphan the channel the counterpart holds);\n // a call while the release is in flight shares it (single-flight, #8)\n if (entry.released) return { ctx: entry.ownCtx, mutual: !!entry.counterpartAnchor }\n if (entry.releasing) return entry.releasing\n if (!p.online) { p.queue.push(() => consent(p, entry, drop, when, ent)); say(p, 'offline — Freigabe wartet auf Netz'); return { queued: true } }\n entry.releasing = release(p, entry, drop, when, ent).finally(() => { entry.releasing = null })\n return entry.releasing\n}\nasync function release (p: Person, entry: any, drop: any, when: number, ent: any) {\n const { offer } = entry\n const secret = C.fromB64u(offer.rendezvous)\n const myDir = offer.direction\n const ctx = await freshCtx(p, ent.nonce)\n const iso = C.iso(when)\n const card = await C.signCard(ctx, C.cardBody(ctx, { name: p.name, challenge: { value: C.challengeOf(ent.ch ?? C.rand(17)), issuedAt: iso } }), iso)\n drop.put(await dropTopic(secret, myDir), await dropSeal(secret, myDir, { card, voucher: offer.voucherForCounterpart }, ent.dropNonce), p.name)\n entry.decided = true\n entry.released = true\n entry.ownCtx = ctx\n entry.ownCard = card\n say(p, `Verbinden mit ${offer.peer.name}: eigene Karte freigegeben (◇ gesendet)`)\n // if the counterpart's card is already held, the relationship is mutual now\n if (entry.counterpartAnchor) {\n const c = p.contacts.get(entry.counterpartAnchor)\n if (c) { c.state = '⇄'; c.channel.own = ctx; say(p, `⇄ verbunden mit ${c.name} — beide Karten liegen vor`) }\n }\n const fetched = await checkDrop(p, entry, drop)\n return { ctx, mutual: !!(entry.released && entry.counterpartAnchor) }\n}\n\n// ── 4. sync: fetch the counterpart's card — PASSIVE receipt, independent\n// of the own decision (like a shared contact arriving; ignoring the offer\n// never blocks what the other side chose to release) ────────────────────\nexport async function checkDrop (p: Person, entry: any, drop: any) {\n if (!p.online || entry.done) return null\n const { offer } = entry\n const secret = C.fromB64u(offer.rendezvous)\n const otherDir = offer.direction === 'a' ? 'b' : 'a'\n const blob = drop.get(await dropTopic(secret, otherDir), p.name)\n if (!blob) return { mutual: false }\n const pkg = await dropOpen(secret, otherDir, blob)\n if (!pkg) { say(p, 'Drop-Blob unlesbar (falsches Geheimnis?)'); return { error: 'undecryptable' } }\n // form BEFORE fields (M-3), THEN the cryptography — and the card runs\n // through its CLOSED wire-0.25 schema, not an ad-hoc field list\n // (review 3, M-4: a valid signature binds a schema-violating card too)\n if (!C.shaped(pkg, { card: 'object', voucher: 'object' })\n || !C.shaped(pkg.voucher, { act: 'string' })) { say(p, 'Drop-Paket formwidrig'); return { error: 'malformed' } }\n {\n const s = SCHEMAS['contact-card.schema.json']\n const errs = VAL.validate(pkg.card, s, s)\n if (errs.length) { say(p, 'Karte schema-widrig: ' + errs[0]); return { error: 'card schema' } }\n }\n // the counterpart card: schema + DI; the voucher: signed by MY mediator\n if (!(await C.diVerify(pkg.card, pkg.card.anchor))) { say(p, 'Karte verifiziert nicht'); return { error: 'card' } }\n if (!(await C.diVerify(pkg.voucher, entry.mediatorAnchor)) || pkg.voucher.act !== offer.act) { say(p, 'Voucher verifiziert nicht unter meinem Vermittler'); return { error: 'voucher' } }\n entry.done = true\n entry.counterpartAnchor = pkg.card.anchor\n const mutual = !!entry.released\n const priors = snapshotPriors(p) // Schnappschuss VOR dem frischen Tupel (6a)\n p.contacts.set(pkg.card.anchor, {\n name: pkg.card.name, card: pkg.card, provenance: `introduced via ${entry.mediator}`, since: entry.offer.issuedAt,\n mediatorProvenance: entry.offer.peer.provenance ?? 'met', priorCands: priors,\n state: mutual ? '⇄' : '◇', channel: { own: entry.ownCtx ?? null, counterpartKa: pkg.card.keyAgreement },\n voucher: pkg.voucher,\n })\n say(p, mutual ? `⇄ verbunden mit ${pkg.card.name} — via ${entry.mediator} (Voucher geprüft)` : `◇ ${pkg.card.name} erhalten — vorgestellt via ${entry.mediator} (einseitig; du hast nichts freigegeben)`)\n return { mutual, card: pkg.card }\n}\n\n// ── device lifecycle ────────────────────────────────────────────────────\nexport async function setOnline (p: Person, online: boolean, drop: any) {\n p.online = online\n say(p, online ? 'online' : 'offline (Flugmodus)')\n if (online) {\n const q = p.queue.splice(0)\n for (const fn of q) await fn()\n for (const e of p.inbox) if (!e.kind) await checkDrop(p, e, drop) // nur Vorstellungs-Angebote haben einen Drop\n }\n}\n"]}
@@ -1,96 +0,0 @@
1
- import * as C from './deps.js';
2
- import type { Person } from './deps.js';
3
- export declare function memberContext(p: Person, genesisDigest: string): Promise<C.Context>;
4
- export declare function foundGroup(p: Person, label: string, when: number, ent?: any): Promise<any>;
5
- export declare function preludeRequest(p: Person, contactAnchor: string, genesisDigest: string, when: number, ent?: any): Promise<{
6
- to: any;
7
- env: C.Envelope;
8
- }>;
9
- export declare function receiveDoc(p: Person, env: any, when: number, ent?: any): Promise<{
10
- handled: boolean;
11
- prompt: {
12
- kind: string;
13
- doc: any;
14
- invite: any;
15
- from: any;
16
- fromAnchor: any;
17
- fromContact: any;
18
- myMemberCtx: C.Context;
19
- decided: boolean;
20
- };
21
- error?: undefined;
22
- } | {
23
- handled: boolean;
24
- idempotent: boolean;
25
- error?: undefined;
26
- admitted?: undefined;
27
- outbound?: undefined;
28
- } | {
29
- handled: boolean;
30
- admitted: any;
31
- outbound: {
32
- to: any;
33
- env: C.Envelope;
34
- }[];
35
- error?: undefined;
36
- idempotent?: undefined;
37
- } | {
38
- handled: boolean;
39
- idempotent: boolean;
40
- error?: undefined;
41
- joined?: undefined;
42
- } | {
43
- handled: boolean;
44
- joined: any;
45
- error?: undefined;
46
- idempotent?: undefined;
47
- } | {
48
- handled: boolean;
49
- idempotent: boolean;
50
- vouched?: undefined;
51
- fulfilled?: undefined;
52
- } | {
53
- handled: boolean;
54
- vouched: any;
55
- fulfilled: boolean;
56
- idempotent?: undefined;
57
- } | {
58
- handled: boolean;
59
- doc: any;
60
- error?: undefined;
61
- outbound?: undefined;
62
- } | {
63
- handled: boolean;
64
- error: string;
65
- doc?: undefined;
66
- outbound?: undefined;
67
- } | {
68
- handled: boolean;
69
- outbound: {
70
- to: any;
71
- env: C.Envelope;
72
- }[];
73
- doc?: undefined;
74
- error?: undefined;
75
- } | {
76
- handled: boolean;
77
- duplicate: boolean;
78
- } | {
79
- handled: boolean;
80
- duplicate?: undefined;
81
- }>;
82
- export declare function buildInvite(p: Person, g: any, contact: any, inviteeMemberAnchor: string, when: number, threadId: string, ent?: any): Promise<{
83
- to: any;
84
- env: C.Envelope;
85
- }>;
86
- export declare function acceptInvite(p: Person, entry: any, when: number, ent?: any): Promise<{
87
- to: any;
88
- env: C.Envelope;
89
- }>;
90
- export declare function vouchFor(p: Person, genesisDigest: string, candidateAnchor: string, provenance: any, when: number, ent?: any): Promise<{
91
- to: any;
92
- env: C.Envelope;
93
- } | {
94
- error: string;
95
- }>;
96
- //# sourceMappingURL=membership.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"membership.d.ts","sourceRoot":"","sources":["../../src/probe/membership.ts"],"names":[],"mappings":"AAiCA,OAAO,KAAK,CAAC,MAAM,WAAW,CAAA;AAC9B,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,WAAW,CAAA;AAYvC,wBAAsB,aAAa,CAAE,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,sBAKpE;AAKD,wBAAsB,UAAU,CAAE,CAAC,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,GAAG,GAAE,GAAQ,gBAoBtF;AAWD,wBAAsB,cAAc,CAAE,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,GAAG,GAAE,GAAQ;;;GAYzH;AAID,wBAAsB,UAAU,CAAE,CAAC,EAAE,MAAM,EAAE,GAAG,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,EAAE,GAAG,GAAE,GAAQ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAOjF;AAoDD,wBAAsB,WAAW,CAAE,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,GAAG,EAAE,OAAO,EAAE,GAAG,EAAE,mBAAmB,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,GAAG,GAAE,GAAQ;;;GAqB7I;AAyBD,wBAAsB,YAAY,CAAE,CAAC,EAAE,MAAM,EAAE,KAAK,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,EAAE,GAAG,GAAE,GAAQ;;;GAoBrF;AAkGD,wBAAsB,QAAQ,CAAE,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,MAAM,EAAE,eAAe,EAAE,MAAM,EAAE,UAAU,EAAE,GAAG,EAAE,IAAI,EAAE,MAAM,EAAE,GAAG,GAAE,GAAQ;;;;;GA2BtI"}
@@ -1,467 +0,0 @@
1
- // groups.mjs — Stage C: groups over the introduced channel. PROBE.
2
- // DOM-free, on rltp-core + rltp-crypto (+ the shipped schemas: the invite
3
- // IS the DTG InvitationCredential of membership-invite/0.2, the accept IS
4
- // membership-accept/0.2 — both schema-validated at issuance AND receipt).
5
- //
6
- // WHAT THIS PROBE EXERCISES (the converged Membership 0.16 / Access 0.30
7
- // semantics, instantiated live):
8
- // founding — the founder signs the genesis under a FOUNDING pair
9
- // context (Access 3.4.1: group/<digest> cannot exist
10
- // before the digest does); genesisDigest = multihash
11
- // over the proof-free genesis; the founder then derives
12
- // the member anchor group/<digest> and self-enrolls.
13
- // prelude — the inviter cannot derive the invitee's member anchor;
14
- // the invitee's app derives it from the genesisDigest
15
- // (canonical-u before the label, Access 5.1) and answers
16
- // over the EXISTING relationship channel (Membership 1.2).
17
- // invite — a conformant DTG InvitationCredential in a delivery
18
- // document WITHOUT a document proof (one carrier,
19
- // Membership 2); invitee re-derives and compares
20
- // (the prelude check, Membership 3.1).
21
- // accept — consent, task-proved under the subject; ref = the
22
- // CREDENTIAL digest (decoded-bytes equality).
23
- // admission — the inviter runs the Access 5.3 pair-internal checks
24
- // (path convention, time window incl. membership-skew,
25
- // size budget, card enclosure profile) and updates the
26
- // roster; a WELCOME (probe form) carries the roster to
27
- // members over their channels.
28
- // OUT OF PROBE SCOPE (named, not faked): the full access-operation
29
- // envelope (oid/prev/epochs), welcome seal + keydist/epoch keys, vouch
30
- // paths and candidacy surfacing, removal. That is the library's next
31
- // growth ring — the checks here are the real ones, the transport forms
32
- // marked @probe are not wire-normative.
33
- import { jcs, makeValidator, toU, sameDigest, tsec, calOK } from '../core.js';
34
- import * as C from './deps.js';
35
- import { SCHEMAS } from '../schemas.js';
36
- const V = makeValidator(SCHEMAS);
37
- const validOr = (data, file) => { const s = SCHEMAS[file]; const errs = V.validate(data, s, s); if (errs.length)
38
- throw new Error(file + ': ' + errs[0]); return data; };
39
- const MEMBERSHIP_SKEW = 300; // PT5M (Membership §5)
40
- const TT = 'https://real-life.org/trust-tasks/';
41
- const CTX3 = ['https://www.w3.org/ns/credentials/v2', 'https://firstperson.network/credentials/dtg/v1', 'https://real-life.org/rltp/v1'];
42
- const say = (p, m) => p.log.push(m);
43
- const uuid = (ent) => ent ?? globalThis.crypto.randomUUID();
44
- // member anchor: canonical-u re-encoding BEFORE the label (Access 5.1)
45
- export async function memberContext(p, genesisDigest) {
46
- const label = 'group/' + toU(genesisDigest);
47
- const ctx = await C.labeledContext(p.rootIkm, label);
48
- p.contexts.set(ctx.anchor, ctx);
49
- p.contexts.set(ctx.keyAgreement, ctx);
50
- return ctx;
51
- }
52
- const memberCard = async (ctx, name, whenIso) => validOr(await C.signCard(ctx, C.cardBody(ctx, { name }), whenIso), 'contact-card.schema.json');
53
- // ── founding ────────────────────────────────────────────────────────────
54
- export async function foundGroup(p, label, when, ent = {}) {
55
- const iso = C.iso(when);
56
- const founding = await C.pairContext(p.rootIkm, ent.foundingNonce ?? C.rand(32)); // pair class: the founding occasion
57
- const groupDid = C.anchorOfEd((await C.edFromSeed(ent.groupSeed ?? C.rand(32))).pubRaw); // group address (probe mint; Identity work)
58
- const genesisBody = { type: 'group-genesis@probe', group: groupDid, label, founder: founding.anchor, issuedAt: iso };
59
- const genesis = await C.diSign(founding, genesisBody, iso);
60
- const genesisDigest = await C.digestDoc(genesisBody); // proof-free signature input (Access 3.2)
61
- const my = await memberContext(p, genesisDigest);
62
- const card = await memberCard(my, p.name, iso);
63
- const g = {
64
- label, groupDid, genesisDigest, genesis, myMemberCtx: my, role: 'founder',
65
- vouchThreshold: ent.vouchThreshold ?? 1, // Bürgschaftsschwelle (Gruppenregel; UI zeigt sie nur > 1)
66
- vouchesReceived: new Map(), // Bürgschaften FÜR MICH (issuer -> vouch@2)
67
- myVouches: new Map(), // Bürgschaften VON MIR (candidate -> vouch@2)
68
- roster: new Map([[my.anchor, { name: p.name, card, addedAt: iso, founder: true }]]),
69
- threads: new Map(), // invitee member anchor -> { threadId, invite } (open invitations)
70
- };
71
- p.groups.set(genesisDigest, g);
72
- say(p, `Gruppe „${label}" gegründet — Genesis unter Gründungs-pair-Anker, Member-Anker ${my.anchor.slice(0, 20)}… abgeleitet`);
73
- return g;
74
- }
75
- // ── transport helper: sealed doc over an existing relationship channel ──
76
- async function sendDoc(p, contact, doc, ent = {}) {
77
- return { to: contact, env: await C.seal(doc, contact.channel.counterpartKa, ent) };
78
- }
79
- const channelCtxOf = (p, doc) => p.contexts.get(doc.recipient) ?? null;
80
- const contactByAnchor = (p, anchor) => p.contacts.get(anchor) ?? null;
81
- const contactOfIssuer = (p, issuer) => p.contacts.get(issuer) ?? null;
82
- // ── prelude (Membership 1.2/3.1: the invitee supplies the member anchor) ─
83
- export async function preludeRequest(p, contactAnchor, genesisDigest, when, ent = {}) {
84
- const contact = contactByAnchor(p, contactAnchor);
85
- const g = p.groups.get(genesisDigest);
86
- const body = {
87
- id: uuid(ent.id), type: TT + 'membership-prelude-request@probe',
88
- issuer: contact.channel.own.anchor, recipient: contactAnchor,
89
- threadId: uuid(ent.threadId), issuedAt: C.iso(when),
90
- payload: { genesisDigest, group: g.groupDid, label: g.label },
91
- };
92
- const doc = await C.diSign(contact.channel.own, body, C.iso(when));
93
- say(p, `Prelude an ${contact.name}: genesisDigest der Gruppe „${g.label}" über den Beziehungs-Kanal`);
94
- return sendDoc(p, contact, doc, ent);
95
- }
96
- // ── receive dispatch: every membership doc travels the channel sealed ───
97
- // Returns { handled, outbound?: [{to, env}], prompt?: entry }.
98
- export async function receiveDoc(p, env, when, ent = {}) {
99
- const opened = await C.openEnvelope(p, env); // Stufen 1–4, Cache-Lesung
100
- if (opened.duplicate)
101
- return { handled: true, duplicate: true };
102
- if (opened.error)
103
- return { handled: false };
104
- const r = await receiveDocInner(p, env, opened.doc, when, ent);
105
- if (r?.handled && !r.error)
106
- C.effectDone(p, opened.digest);
107
- return r;
108
- }
109
- async function receiveDocInner(p, env, doc, when, ent = {}) {
110
- const ctx = channelCtxOf(p, { recipient: env.rkid }) ?? p.contexts.get(env.rkid);
111
- if (!ctx)
112
- return { handled: false };
113
- if (typeof doc?.type !== 'string' || !doc.type.startsWith(TT + 'membership-'))
114
- return { handled: false, doc };
115
- // the sender is identified by the CHANNEL the envelope arrived on (rkid
116
- // names our own pair context of exactly one relationship) — membership
117
- // documents carry MEMBER anchors as issuer, which no contact key holds
118
- const from = [...p.contacts.values()].find((c) => c.channel?.own?.anchor === ctx.anchor) ?? contactOfIssuer(p, doc.issuer);
119
- switch (doc.type.slice((TT + 'membership-').length)) {
120
- case 'prelude-request@probe': {
121
- // form BEFORE fields (review 3, M-3): a valid signature binds
122
- // whatever was signed — payload.genesisDigest earns its type here
123
- if (!C.shaped(doc, { issuer: 'string', threadId: 'string', payload: 'object', proof: 'object' })
124
- || !C.shaped(doc.payload, { genesisDigest: 'string', group: 'string', label: 'string' }))
125
- return { handled: true, error: 'malformed prelude' };
126
- if (!from || !(await C.diVerify(doc, doc.issuer)))
127
- return { handled: true, error: 'prelude proof' };
128
- let my;
129
- try {
130
- my = await memberContext(p, doc.payload.genesisDigest);
131
- }
132
- catch {
133
- return { handled: true, error: 'genesisDigest not canonical' };
134
- }
135
- const body = {
136
- id: uuid(), type: TT + 'membership-prelude-reply@probe',
137
- issuer: from.channel.own.anchor, recipient: doc.issuer,
138
- threadId: doc.threadId, issuedAt: C.iso(when),
139
- payload: { genesisDigest: doc.payload.genesisDigest, memberAnchor: my.anchor },
140
- };
141
- const reply = await C.diSign(from.channel.own, body, C.iso(when));
142
- say(p, `Prelude von ${from.name}: Member-Anker für „${doc.payload.label}" abgeleitet und geantwortet`);
143
- return { handled: true, outbound: [await sendDoc(p, from, reply, ent)] };
144
- }
145
- case 'prelude-reply@probe': {
146
- if (!C.shaped(doc, { issuer: 'string', threadId: 'string', payload: 'object', proof: 'object' })
147
- || !C.shaped(doc.payload, { genesisDigest: 'string', memberAnchor: 'string' })
148
- || C.edRawOfAnchor(doc.payload.memberAnchor) === null)
149
- return { handled: true, error: 'malformed prelude-reply' };
150
- if (!from || !(await C.diVerify(doc, doc.issuer)))
151
- return { handled: true, error: 'prelude-reply proof' };
152
- const g = [...p.groups.values()].find((g) => g.genesisDigest === doc.payload.genesisDigest);
153
- if (!g)
154
- return { handled: true, error: 'unknown group' };
155
- // Log erst NACH dem gelungenen Bau; ein Schema-Throw aus
156
- // buildInvite verlässt die Empfangs-Promise nie (Review 9, P-B2)
157
- let inv;
158
- try {
159
- inv = await buildInvite(p, g, from, doc.payload.memberAnchor, when, doc.threadId, ent);
160
- }
161
- catch (e) {
162
- return { handled: true, error: 'invite build: ' + String(e?.message ?? e) };
163
- }
164
- say(p, `${from.name}s Member-Anker erhalten — Einladung wird ausgestellt`);
165
- return { handled: true, outbound: [inv] };
166
- }
167
- case 'invite/0.2': return handleInvite(p, doc, from, when);
168
- case 'accept/0.2': return handleAccept(p, doc, from, when, ent);
169
- case 'welcome@probe': return handleWelcome(p, doc, from);
170
- case 'vouch/0.1': return handleVouch(p, doc, from);
171
- }
172
- return { handled: false, doc };
173
- }
174
- // ── the invite: a conformant DTG InvitationCredential (one carrier) ─────
175
- export async function buildInvite(p, g, contact, inviteeMemberAnchor, when, threadId, ent = {}) {
176
- const iso = C.iso(when), until = C.iso(when + 24 * 3600 * 1000);
177
- const inviterCard = await memberCard(g.myMemberCtx, p.name, iso);
178
- const credBody = {
179
- '@context': CTX3,
180
- type: ['VerifiableCredential', 'DTGCredential', 'InvitationCredential', 'MembershipInvite'],
181
- issuer: g.myMemberCtx.anchor,
182
- credentialSubject: { id: inviteeMemberAnchor, group: g.groupDid, genesisDigest: g.genesisDigest, card: inviterCard, name: g.label },
183
- validFrom: iso, validUntil: until, taskContext: threadId,
184
- };
185
- const invite = await C.diSign(g.myMemberCtx, credBody, iso);
186
- validOr({ invite }, 'payload-membership-invite.schema.json');
187
- const doc = {
188
- id: uuid(ent.docId), type: TT + 'membership-invite/0.2',
189
- issuer: g.myMemberCtx.anchor, recipient: inviteeMemberAnchor,
190
- threadId, issuedAt: iso, payload: { invite },
191
- };
192
- validOr(doc, 'rltp-delivery-document.schema.json');
193
- g.threads.set(inviteeMemberAnchor, { threadId, invite, contactAnchor: [...p.contacts.entries()].find(([, c]) => c === contact)[0] });
194
- say(p, `Einladung (InvitationCredential) an ${contact.name} — Thread ${threadId.slice(0, 8)}…`);
195
- return sendDoc(p, contact, doc, ent);
196
- }
197
- async function handleInvite(p, doc, from, when) {
198
- if (!from)
199
- return { handled: true, error: 'invite not from a held contact' };
200
- const inv = doc.payload?.invite;
201
- try {
202
- validOr(doc.payload, 'payload-membership-invite.schema.json');
203
- validOr(doc, 'rltp-delivery-document.schema.json');
204
- }
205
- catch (e) {
206
- say(p, 'Einladung schema-ungültig: ' + e.message);
207
- return { handled: true, error: 'schema' };
208
- }
209
- if ('proof' in doc) {
210
- say(p, 'Einladung trägt Dokument-Proof — one carrier verletzt');
211
- return { handled: true, error: 'one-carrier' };
212
- }
213
- if (!(await C.diVerify(inv, inv.issuer)))
214
- return { handled: true, error: 'credential proof' };
215
- if (inv.issuer !== doc.issuer || inv.credentialSubject.id !== doc.recipient || inv.taskContext !== doc.threadId)
216
- return { handled: true, error: 'document bindings' };
217
- if (inv.credentialSubject.card.anchor !== inv.issuer || !(await C.diVerify(inv.credentialSubject.card, inv.issuer)))
218
- return { handled: true, error: 'card ownership' };
219
- const cardOK = !('sentTo' in inv.credentialSubject.card) && !('boundTo' in inv.credentialSubject.card) && !('deliveryHints' in inv.credentialSubject.card);
220
- if (!cardOK)
221
- return { handled: true, error: 'card enclosure profile' };
222
- if (![inv.validFrom, inv.validUntil, inv.proof.created].every(calOK) || tsec(inv.validUntil) < tsec(inv.validFrom))
223
- return { handled: true, error: 'validity' };
224
- // THE PRELUDE CHECK (Membership 3.1): my own derivation from the
225
- // genesisDigest must equal credentialSubject.id — a substituted anchor
226
- // dies here, whatever the prelude's path was
227
- const my = await memberContext(p, inv.credentialSubject.genesisDigest);
228
- if (my.anchor !== inv.credentialSubject.id) {
229
- say(p, 'Prelude-Check FEHLGESCHLAGEN: Einladung nennt nicht meine Ableitung');
230
- return { handled: true, error: 'prelude mismatch' };
231
- }
232
- const entry = { kind: 'invite', doc, invite: inv, from: from.name, fromAnchor: doc.issuer, fromContact: from, myMemberCtx: my, decided: false };
233
- p.inbox.push(entry);
234
- say(p, `${from.name} lädt dich in „${inv.credentialSubject.name ?? 'eine Gruppe'}" ein (Einladung geprüft, Prelude-Check bestanden)`);
235
- return { handled: true, prompt: entry };
236
- }
237
- // ── the accept: consent, task-proved, credential-digest ref ─────────────
238
- export async function acceptInvite(p, entry, when, ent = {}) {
239
- const inv = entry.invite;
240
- const iso = C.iso(when);
241
- const card = await memberCard(entry.myMemberCtx, p.name, iso);
242
- const payload = { accept: {
243
- group: inv.credentialSubject.group, subject: entry.myMemberCtx.anchor,
244
- ref: await C.digestDoc(inv), // the invitation identity: JCS over the COMPLETE credential incl. proof
245
- card, candidacy: ent.candidacy ?? false,
246
- } };
247
- validOr(payload, 'payload-membership-accept.schema.json');
248
- const body = {
249
- id: uuid(ent.docId), type: TT + 'membership-accept/0.2',
250
- issuer: entry.myMemberCtx.anchor, recipient: inv.issuer,
251
- threadId: inv.taskContext, issuedAt: iso, payload,
252
- };
253
- const doc = await C.diSign(entry.myMemberCtx, body, iso); // task proof under the subject (Membership 2)
254
- validOr(doc, 'rltp-delivery-document.schema.json');
255
- entry.decided = true;
256
- entry.accepted = true;
257
- say(p, `Beitritt zu „${inv.credentialSubject.name}" erklärt (Accept, ref = Credential-Digest)`);
258
- return sendDoc(p, entry.fromContact, doc, ent);
259
- }
260
- // ── admission: the Access 5.3 pair-internal checks, then roster + welcome ─
261
- async function handleAccept(p, doc, from, when, ent = {}) {
262
- const g = [...p.groups.values()].find((g) => g.threads.has(doc.issuer));
263
- if (!g)
264
- return { handled: true, error: 'no open invitation for this subject' };
265
- const th = g.threads.get(doc.issuer);
266
- const inv = th.invite, acc = doc.payload?.accept;
267
- const fail = async (why) => { say(p, `Admission abgelehnt: ${why}`); return { handled: true, error: why }; };
268
- try {
269
- validOr(doc.payload, 'payload-membership-accept.schema.json');
270
- validOr(doc, 'rltp-delivery-document.schema.json');
271
- }
272
- catch {
273
- return fail('schema');
274
- }
275
- if (!(await C.diVerify(doc, doc.issuer)))
276
- return fail('accept task proof');
277
- if (!sameDigest(acc.ref, await C.digestDoc(inv)))
278
- return fail('ref ≠ credential digest'); // decoded-bytes equality
279
- if (acc.subject !== inv.credentialSubject.id || acc.subject !== doc.issuer)
280
- return fail('subject binding');
281
- if (acc.group !== inv.credentialSubject.group || !sameDigest(inv.credentialSubject.genesisDigest, g.genesisDigest))
282
- return fail('group binding');
283
- if (doc.threadId !== inv.taskContext)
284
- return fail('thread binding');
285
- if (acc.card.anchor !== acc.subject || !(await C.diVerify(acc.card, acc.subject)))
286
- return fail('card ownership');
287
- if (('sentTo' in acc.card) || ('boundTo' in acc.card) || ('deliveryHints' in acc.card))
288
- return fail('card enclosure profile');
289
- if (![doc.issuedAt, doc.proof.created].every(calOK))
290
- return fail('calendar validity');
291
- if (tsec(doc.issuedAt) > tsec(inv.validUntil) + MEMBERSHIP_SKEW * 1000 || tsec(doc.proof.created) > tsec(inv.validUntil) + MEMBERSHIP_SKEW * 1000)
292
- return fail('accept after validUntil + membership-skew');
293
- if (Buffer_(jcs(doc)) > 16384 || Buffer_(jcs({ invite: inv })) > 16384)
294
- return fail('size budget');
295
- if (!g.roster.has(inv.issuer))
296
- return fail('inviter not a member');
297
- if (g.roster.has(acc.subject)) {
298
- say(p, 'Same-Subject-Admission: idempotent');
299
- return { handled: true, idempotent: true };
300
- }
301
- // ATOMICITY (review 3, B-2): every await that can fail — digest,
302
- // signing, sealing — happens BEFORE the first state mutation. If the
303
- // welcome cannot be built, the roster has not grown, the thread still
304
- // stands, and the SAME delivery can be retried cleanly.
305
- const newEntry = { name: acc.card.name, card: acc.card, addedAt: C.iso(when), candidacy: acc.candidacy === true,
306
- acceptDigest: await C.digestDoc(doc), contactAnchor: th.contactAnchor };
307
- const contact = contactByAnchor(p, th.contactAnchor);
308
- const rosterAfter = [...g.roster.entries(), [acc.subject, newEntry]];
309
- const wBody = {
310
- id: uuid(), type: TT + 'membership-welcome@probe',
311
- issuer: g.myMemberCtx.anchor, recipient: acc.subject,
312
- threadId: doc.threadId, issuedAt: C.iso(when),
313
- payload: { genesisDigest: g.genesisDigest, group: g.groupDid, label: g.label, genesis: g.genesis, vouchThreshold: g.vouchThreshold ?? 1,
314
- roster: rosterAfter.map(([anchor, m]) => ({ anchor, name: m.name, addedAt: m.addedAt, founder: !!m.founder, candidacy: !!m.candidacy, acceptDigest: m.acceptDigest ?? null })) },
315
- };
316
- const welcome = await sendDoc(p, contact, await C.diSign(g.myMemberCtx, wBody, C.iso(when)), ent);
317
- // — from here on, synchronous only —
318
- g.roster.set(acc.subject, newEntry);
319
- {
320
- const c = contactByAnchor(p, th.contactAnchor);
321
- if (c)
322
- (c.sharedGroups ??= []).push(g.genesisDigest);
323
- } // der Inviter WEISS, wer beigetreten ist
324
- g.threads.delete(doc.issuer);
325
- say(p, `${acc.card.name} ist Mitglied von „${g.label}" — Admission kanonisch, Consent konsumiert`);
326
- return { handled: true, admitted: acc.subject, outbound: [welcome] };
327
- }
328
- const Buffer_ = (s) => new TextEncoder().encode(s).length;
329
- async function handleWelcome(p, doc, from) {
330
- // form BEFORE fields (M-3): the roster travels as data and becomes
331
- // this person's map — every entry earns its shape before adoption
332
- if (!C.shaped(doc, { issuer: 'string', recipient: 'string', threadId: 'string', payload: 'object', proof: 'object' })
333
- || !C.shaped(doc.payload, { genesisDigest: 'string', group: 'string', label: 'string', roster: 'array' })
334
- || !doc.payload.roster.every((m) => C.shaped(m, { anchor: 'string', name: 'string', addedAt: 'string' })))
335
- return { handled: true, error: 'malformed welcome' };
336
- if (toU(doc.payload.genesisDigest) !== doc.payload.genesisDigest)
337
- return { handled: true, error: 'malformed welcome (genesisDigest)' };
338
- if (!(await C.diVerify(doc, doc.issuer)))
339
- return { handled: true, error: 'welcome proof' };
340
- const gd = doc.payload.genesisDigest;
341
- let my;
342
- try {
343
- my = await memberContext(p, gd);
344
- }
345
- catch {
346
- return { handled: true, error: 'genesisDigest not canonical' };
347
- }
348
- if (doc.recipient !== my.anchor)
349
- return { handled: true, error: 'welcome not for my member anchor' };
350
- // a held group is never rewritten by a later welcome
351
- if (p.groups.has(gd))
352
- return { handled: true, idempotent: true };
353
- // the welcome answers an invitation THIS device accepted (Membership
354
- // Tasks: it travels in the invite's thread, from the inviter, for the
355
- // accept's subject and the invited group) — a signed welcome from a held
356
- // contact without that binding adopts nothing
357
- const entry = p.inbox.find((e) => e.kind === 'invite' && e.accepted && !e.welcomed
358
- && e.invite.taskContext === doc.threadId && e.invite.issuer === doc.issuer
359
- && e.myMemberCtx.anchor === doc.recipient
360
- && e.invite.credentialSubject.genesisDigest === gd && e.invite.credentialSubject.group === doc.payload.group);
361
- if (!entry)
362
- return { handled: true, error: 'welcome without an accepted invitation' };
363
- const listed = new Set(doc.payload.roster.map((m) => m.anchor));
364
- if (!listed.has(doc.issuer) || !listed.has(my.anchor))
365
- return { handled: true, error: 'welcome roster omits its issuer or subject' };
366
- const g = {
367
- label: doc.payload.label, groupDid: doc.payload.group, genesisDigest: gd,
368
- genesis: doc.payload.genesis, myMemberCtx: my, role: 'member',
369
- vouchThreshold: doc.payload.vouchThreshold ?? 1,
370
- vouchesReceived: new Map(), myVouches: new Map(),
371
- roster: new Map(doc.payload.roster.map((m) => [m.anchor, m])),
372
- threads: new Map(),
373
- };
374
- g.myAcceptDigest = g.roster.get(my.anchor)?.acceptDigest ?? null;
375
- p.groups.set(gd, g);
376
- entry.welcomed = true;
377
- if (from)
378
- (from.sharedGroups ??= []).push(gd); // der Invitee WEISS, wer ihn eingeladen hat
379
- say(p, `Willkommen in „${g.label}" — Roster mit ${g.roster.size} Mitgliedern übernommen`);
380
- return { handled: true, joined: gd };
381
- }
382
- // ── die Bürgschaft (Task membership-vouch/0.1, Artefakt vouch@2) ────────
383
- // ein konformes DTG EndorsementCredential ──────────────────────────────
384
- // (AdmissionVouch, Access 4.2/4.3): genesisDigest bindet die Gruppe,
385
- // accept bindet die KONSENTIERTE Kandidatur (keine stehende Bürgschaft),
386
- // provenance ist selbst-attestiert (met | introduced). Signiert unter dem
387
- // MEMBER-Anker des Bürgen; schema-validiert bei Ausstellung UND Empfang.
388
- // Transport (probe): über den Beziehungs-Kanal zum KANDIDATEN — nur wer
389
- // einen Kanal zum Kandidaten hält, kann liefern (per-device-Wissen,
390
- // nichts wird erfunden); der Kandidat sammelt und zählt gegen die
391
- // Schwelle. Gruppenweite Sichtbarkeit der Zählung = Access-Envelope-Ring.
392
- export async function vouchFor(p, genesisDigest, candidateAnchor, provenance, when, ent = {}) {
393
- const g = p.groups.get(genesisDigest);
394
- const m = g?.roster.get(candidateAnchor);
395
- if (!g || !m)
396
- return { error: 'unbekannter Kandidat' };
397
- if (!m.candidacy)
398
- return { error: 'keine sichtbare Kandidatur (Opt-in fehlt)' };
399
- if (!m.acceptDigest)
400
- return { error: 'kein accept-Bezug — Bürgschaft wäre stehend' };
401
- if (!m.contactAnchor || !p.contacts.get(m.contactAnchor))
402
- return { error: 'kein Kanal zum Kandidaten' };
403
- if (g.myVouches.has(candidateAnchor))
404
- return { error: 'bereits gebürgt' };
405
- const iso = C.iso(when);
406
- const cred = await C.diSign(g.myMemberCtx, {
407
- '@context': CTX3,
408
- type: ['VerifiableCredential', 'DTGCredential', 'EndorsementCredential', 'AdmissionVouch'],
409
- issuer: g.myMemberCtx.anchor,
410
- validFrom: iso,
411
- credentialSubject: { id: candidateAnchor, endorsement: {
412
- type: 'AdmissionVouch', genesisDigest: toU(g.genesisDigest), accept: toU(m.acceptDigest), provenance
413
- } },
414
- }, iso);
415
- validOr(cred, 'access-vouch.schema.json');
416
- g.myVouches.set(candidateAnchor, cred);
417
- const contact = p.contacts.get(m.contactAnchor);
418
- const doc = {
419
- id: uuid(ent.docId), type: TT + 'membership-vouch/0.1',
420
- issuer: g.myMemberCtx.anchor, recipient: candidateAnchor,
421
- threadId: uuid(ent.threadId), issuedAt: iso, payload: { vouch: cred },
422
- };
423
- say(p, `Bürgschaft für ${m.name} in „${g.label}" ausgestellt (${provenance}, accept-gebunden)`);
424
- return sendDoc(p, contact, await C.diSign(g.myMemberCtx, doc, iso), ent);
425
- }
426
- // Kandidatenseite: jede Prüfung an ihrem Punkt, dann zählen
427
- async function handleVouch(p, doc, from) {
428
- const cred = doc.payload?.vouch;
429
- const g = [...p.groups.values()].find((g) => cred && sameDigest(cred.credentialSubject?.endorsement?.genesisDigest ?? '', g.genesisDigest));
430
- const fail = (why) => { say(p, `Bürgschaft verworfen: ${why}`); return { handled: true, error: why }; };
431
- if (!g)
432
- return fail('unbekannte Gruppe');
433
- try {
434
- validOr(cred, 'access-vouch.schema.json');
435
- }
436
- catch {
437
- return fail('schema');
438
- }
439
- if (!(await C.diVerify(cred, cred.issuer)) || !(await C.diVerify(doc, doc.issuer)))
440
- return fail('proof');
441
- if (cred.issuer !== doc.issuer)
442
- return fail('issuer binding');
443
- if (!g.roster.has(cred.issuer))
444
- return fail('Bürge ist kein Mitglied');
445
- if (cred.credentialSubject.id !== g.myMemberCtx.anchor)
446
- return fail('nicht für mich');
447
- if (!g.myAcceptDigest || !sameDigest(cred.credentialSubject.endorsement.accept, g.myAcceptDigest))
448
- return fail('accept-Bindung');
449
- if (g.vouchesReceived.has(cred.issuer)) {
450
- say(p, 'Bürgschaft doppelt — idempotent');
451
- return { handled: true, idempotent: true };
452
- }
453
- g.vouchesReceived.set(cred.issuer, cred);
454
- const n = g.vouchesReceived.size, need = g.vouchThreshold ?? 1;
455
- if (n >= need) {
456
- const me = g.roster.get(g.myMemberCtx.anchor);
457
- if (me)
458
- me.candidacy = false;
459
- g.candidacyFulfilled = true;
460
- say(p, `Bürgschaft von ${g.roster.get(cred.issuer)?.name ?? '?'} — Schwelle erreicht (${n}/${need}), Kandidatur erfüllt`);
461
- }
462
- else {
463
- say(p, `Bürgschaft von ${g.roster.get(cred.issuer)?.name ?? '?'} erhalten (${n}/${need})`);
464
- }
465
- return { handled: true, vouched: cred.issuer, fulfilled: n >= need };
466
- }
467
- //# sourceMappingURL=membership.js.map