@did-btcr2/method 0.36.0 → 0.37.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 (164) hide show
  1. package/dist/.tsbuildinfo +1 -1
  2. package/dist/browser.js +1371 -260
  3. package/dist/browser.mjs +1371 -260
  4. package/dist/cjs/index.js +1464 -343
  5. package/dist/esm/core/aggregation/beacon-strategy.js +19 -6
  6. package/dist/esm/core/aggregation/beacon-strategy.js.map +1 -1
  7. package/dist/esm/core/aggregation/cohort.js +142 -33
  8. package/dist/esm/core/aggregation/cohort.js.map +1 -1
  9. package/dist/esm/core/aggregation/conditions.js +27 -0
  10. package/dist/esm/core/aggregation/conditions.js.map +1 -1
  11. package/dist/esm/core/aggregation/fallback-spend.js +132 -0
  12. package/dist/esm/core/aggregation/fallback-spend.js.map +1 -0
  13. package/dist/esm/core/aggregation/messages/base.js.map +1 -1
  14. package/dist/esm/core/aggregation/messages/bodies.js +46 -1
  15. package/dist/esm/core/aggregation/messages/bodies.js.map +1 -1
  16. package/dist/esm/core/aggregation/messages/constants.js +11 -0
  17. package/dist/esm/core/aggregation/messages/constants.js.map +1 -1
  18. package/dist/esm/core/aggregation/messages/factories.js +27 -1
  19. package/dist/esm/core/aggregation/messages/factories.js.map +1 -1
  20. package/dist/esm/core/aggregation/messages/guards.js +4 -1
  21. package/dist/esm/core/aggregation/messages/guards.js.map +1 -1
  22. package/dist/esm/core/aggregation/participant.js +218 -18
  23. package/dist/esm/core/aggregation/participant.js.map +1 -1
  24. package/dist/esm/core/aggregation/phases.js +6 -0
  25. package/dist/esm/core/aggregation/phases.js.map +1 -1
  26. package/dist/esm/core/aggregation/recovery-policy.js +156 -0
  27. package/dist/esm/core/aggregation/recovery-policy.js.map +1 -0
  28. package/dist/esm/core/aggregation/recovery-spend.js +106 -0
  29. package/dist/esm/core/aggregation/recovery-spend.js.map +1 -0
  30. package/dist/esm/core/aggregation/runner/aggregation-runner.js +11 -3
  31. package/dist/esm/core/aggregation/runner/aggregation-runner.js.map +1 -1
  32. package/dist/esm/core/aggregation/runner/participant-runner.js +106 -19
  33. package/dist/esm/core/aggregation/runner/participant-runner.js.map +1 -1
  34. package/dist/esm/core/aggregation/runner/service-runner.js +409 -195
  35. package/dist/esm/core/aggregation/runner/service-runner.js.map +1 -1
  36. package/dist/esm/core/aggregation/service.js +221 -11
  37. package/dist/esm/core/aggregation/service.js.map +1 -1
  38. package/dist/esm/core/aggregation/signing-session.js +3 -3
  39. package/dist/esm/core/aggregation/signing-session.js.map +1 -1
  40. package/dist/esm/core/aggregation/transport/http/envelope.js +3 -3
  41. package/dist/esm/core/aggregation/transport/http/inbox-buffer.js +1 -1
  42. package/dist/esm/core/aggregation/transport/http/nonce-cache.js +1 -1
  43. package/dist/esm/core/aggregation/transport/http/rate-limiter.js +1 -1
  44. package/dist/esm/core/aggregation/transport/http/request-auth.js +1 -1
  45. package/dist/esm/core/aggregation/transport/http/server.js +1 -1
  46. package/dist/esm/core/aggregation/transport/http/sse-stream.js +1 -1
  47. package/dist/esm/core/aggregation/transport/http/sse-writer.js +1 -1
  48. package/dist/esm/core/aggregation/transport/in-memory.js +1 -1
  49. package/dist/esm/core/aggregation/transport/nostr.js +6 -6
  50. package/dist/esm/core/beacon/beacon.js +15 -10
  51. package/dist/esm/core/beacon/beacon.js.map +1 -1
  52. package/dist/esm/core/beacon/cas-beacon.js +6 -6
  53. package/dist/esm/core/beacon/cas-beacon.js.map +1 -1
  54. package/dist/esm/core/beacon/singleton-beacon.js +2 -2
  55. package/dist/esm/core/beacon/singleton-beacon.js.map +1 -1
  56. package/dist/esm/core/beacon/smt-beacon.js +3 -3
  57. package/dist/esm/core/beacon/smt-beacon.js.map +1 -1
  58. package/dist/esm/core/resolver.js +8 -8
  59. package/dist/esm/core/resolver.js.map +1 -1
  60. package/dist/esm/core/updater.js +6 -6
  61. package/dist/esm/core/updater.js.map +1 -1
  62. package/dist/esm/did-btcr2.js +2 -2
  63. package/dist/esm/index.js +3 -0
  64. package/dist/esm/index.js.map +1 -1
  65. package/dist/types/core/aggregation/beacon-strategy.d.ts +8 -4
  66. package/dist/types/core/aggregation/beacon-strategy.d.ts.map +1 -1
  67. package/dist/types/core/aggregation/cohort.d.ts +88 -17
  68. package/dist/types/core/aggregation/cohort.d.ts.map +1 -1
  69. package/dist/types/core/aggregation/conditions.d.ts +28 -0
  70. package/dist/types/core/aggregation/conditions.d.ts.map +1 -1
  71. package/dist/types/core/aggregation/fallback-spend.d.ts +94 -0
  72. package/dist/types/core/aggregation/fallback-spend.d.ts.map +1 -0
  73. package/dist/types/core/aggregation/logger.d.ts +1 -1
  74. package/dist/types/core/aggregation/messages/base.d.ts +6 -0
  75. package/dist/types/core/aggregation/messages/base.d.ts.map +1 -1
  76. package/dist/types/core/aggregation/messages/bodies.d.ts +50 -2
  77. package/dist/types/core/aggregation/messages/bodies.d.ts.map +1 -1
  78. package/dist/types/core/aggregation/messages/constants.d.ts +8 -0
  79. package/dist/types/core/aggregation/messages/constants.d.ts.map +1 -1
  80. package/dist/types/core/aggregation/messages/factories.d.ts +40 -0
  81. package/dist/types/core/aggregation/messages/factories.d.ts.map +1 -1
  82. package/dist/types/core/aggregation/messages/guards.d.ts.map +1 -1
  83. package/dist/types/core/aggregation/participant.d.ts +47 -4
  84. package/dist/types/core/aggregation/participant.d.ts.map +1 -1
  85. package/dist/types/core/aggregation/phases.d.ts +8 -2
  86. package/dist/types/core/aggregation/phases.d.ts.map +1 -1
  87. package/dist/types/core/aggregation/recovery-policy.d.ts +132 -0
  88. package/dist/types/core/aggregation/recovery-policy.d.ts.map +1 -0
  89. package/dist/types/core/aggregation/recovery-spend.d.ts +94 -0
  90. package/dist/types/core/aggregation/recovery-spend.d.ts.map +1 -0
  91. package/dist/types/core/aggregation/runner/aggregation-runner.d.ts +13 -3
  92. package/dist/types/core/aggregation/runner/aggregation-runner.d.ts.map +1 -1
  93. package/dist/types/core/aggregation/runner/events.d.ts +48 -16
  94. package/dist/types/core/aggregation/runner/events.d.ts.map +1 -1
  95. package/dist/types/core/aggregation/runner/participant-runner.d.ts +23 -14
  96. package/dist/types/core/aggregation/runner/participant-runner.d.ts.map +1 -1
  97. package/dist/types/core/aggregation/runner/service-runner.d.ts +102 -23
  98. package/dist/types/core/aggregation/runner/service-runner.d.ts.map +1 -1
  99. package/dist/types/core/aggregation/service.d.ts +26 -2
  100. package/dist/types/core/aggregation/service.d.ts.map +1 -1
  101. package/dist/types/core/aggregation/signing-session.d.ts +2 -2
  102. package/dist/types/core/aggregation/signing-session.d.ts.map +1 -1
  103. package/dist/types/core/aggregation/transport/http/envelope.d.ts +3 -3
  104. package/dist/types/core/aggregation/transport/http/inbox-buffer.d.ts +1 -1
  105. package/dist/types/core/aggregation/transport/http/nonce-cache.d.ts +1 -1
  106. package/dist/types/core/aggregation/transport/http/rate-limiter.d.ts +1 -1
  107. package/dist/types/core/aggregation/transport/http/request-auth.d.ts +1 -1
  108. package/dist/types/core/aggregation/transport/http/server.d.ts +1 -1
  109. package/dist/types/core/aggregation/transport/http/sse-stream.d.ts +2 -2
  110. package/dist/types/core/aggregation/transport/http/sse-writer.d.ts +1 -1
  111. package/dist/types/core/aggregation/transport/in-memory.d.ts +1 -1
  112. package/dist/types/core/aggregation/transport/nostr.d.ts +4 -4
  113. package/dist/types/core/aggregation/transport/transport.d.ts +4 -4
  114. package/dist/types/core/aggregation/transport/transport.d.ts.map +1 -1
  115. package/dist/types/core/beacon/beacon.d.ts +7 -7
  116. package/dist/types/core/beacon/beacon.d.ts.map +1 -1
  117. package/dist/types/core/beacon/cas-beacon.d.ts +2 -2
  118. package/dist/types/core/beacon/interfaces.d.ts +1 -1
  119. package/dist/types/core/resolver.d.ts +3 -3
  120. package/dist/types/core/updater.d.ts +4 -4
  121. package/dist/types/did-btcr2.d.ts +2 -2
  122. package/dist/types/index.d.ts +3 -0
  123. package/dist/types/index.d.ts.map +1 -1
  124. package/package.json +4 -4
  125. package/src/core/aggregation/beacon-strategy.ts +27 -9
  126. package/src/core/aggregation/cohort.ts +171 -35
  127. package/src/core/aggregation/conditions.ts +56 -0
  128. package/src/core/aggregation/fallback-spend.ts +223 -0
  129. package/src/core/aggregation/logger.ts +1 -1
  130. package/src/core/aggregation/messages/base.ts +6 -0
  131. package/src/core/aggregation/messages/bodies.ts +94 -1
  132. package/src/core/aggregation/messages/constants.ts +12 -0
  133. package/src/core/aggregation/messages/factories.ts +57 -0
  134. package/src/core/aggregation/messages/guards.ts +6 -0
  135. package/src/core/aggregation/participant.ts +264 -20
  136. package/src/core/aggregation/phases.ts +9 -0
  137. package/src/core/aggregation/recovery-policy.ts +237 -0
  138. package/src/core/aggregation/recovery-spend.ts +192 -0
  139. package/src/core/aggregation/runner/aggregation-runner.ts +27 -5
  140. package/src/core/aggregation/runner/events.ts +47 -19
  141. package/src/core/aggregation/runner/participant-runner.ts +113 -31
  142. package/src/core/aggregation/runner/service-runner.ts +484 -203
  143. package/src/core/aggregation/service.ts +260 -14
  144. package/src/core/aggregation/signing-session.ts +3 -3
  145. package/src/core/aggregation/transport/http/envelope.ts +3 -3
  146. package/src/core/aggregation/transport/http/inbox-buffer.ts +1 -1
  147. package/src/core/aggregation/transport/http/nonce-cache.ts +1 -1
  148. package/src/core/aggregation/transport/http/rate-limiter.ts +1 -1
  149. package/src/core/aggregation/transport/http/request-auth.ts +1 -1
  150. package/src/core/aggregation/transport/http/server.ts +1 -1
  151. package/src/core/aggregation/transport/http/sse-stream.ts +2 -2
  152. package/src/core/aggregation/transport/http/sse-writer.ts +1 -1
  153. package/src/core/aggregation/transport/in-memory.ts +1 -1
  154. package/src/core/aggregation/transport/nostr.ts +6 -6
  155. package/src/core/aggregation/transport/transport.ts +4 -4
  156. package/src/core/beacon/beacon.ts +16 -11
  157. package/src/core/beacon/cas-beacon.ts +7 -7
  158. package/src/core/beacon/interfaces.ts +1 -1
  159. package/src/core/beacon/singleton-beacon.ts +2 -2
  160. package/src/core/beacon/smt-beacon.ts +3 -3
  161. package/src/core/resolver.ts +8 -8
  162. package/src/core/updater.ts +6 -6
  163. package/src/did-btcr2.ts +2 -2
  164. package/src/index.ts +3 -0
@@ -16,28 +16,28 @@ const DEFAULT_FEE_ESTIMATOR: FeeEstimator = new StaticFeeEstimator(5);
16
16
 
17
17
  /**
18
18
  * Singleton beacon script kinds. Per the did:btcr2 spec, deterministic DID documents
19
- * include three beacon services: P2PKH, P2WPKH, and P2TR (taproot key-path) all
19
+ * include three beacon services: P2PKH, P2WPKH, and P2TR (taproot key-path), all
20
20
  * derived from the genesis secp256k1 public key. The singleton broadcast path must
21
21
  * support signing for all three.
22
22
  */
23
23
  export type SingletonScriptKind = 'p2pkh' | 'p2wpkh' | 'p2tr';
24
24
 
25
25
  /**
26
- * Conservative vsize estimate for a 1-input P2TR key-path 1 P2TR change + 1 OP_RETURN(32) tx.
26
+ * Conservative vsize estimate for a 1-input P2TR key-path to 1 P2TR change + 1 OP_RETURN(32) tx.
27
27
  * Stripped 137 + witness ≈ 68 (marker + flag + stack-count + sig-len + 64 BIP-340 sig).
28
28
  * Weight = 137*4 + 68 = 616, vsize ≈ 154, rounded to 160 for headroom.
29
29
  */
30
30
  export const P2TR_BEACON_TX_VSIZE = 160;
31
31
 
32
32
  /**
33
- * Conservative vsize estimate for a 1-input P2WPKH 1 P2WPKH change + 1 OP_RETURN(32) tx.
33
+ * Conservative vsize estimate for a 1-input P2WPKH to 1 P2WPKH change + 1 OP_RETURN(32) tx.
34
34
  * Stripped 125 + witness ≈ 110 (worst-case DER ECDSA sig 72 + sighash byte + 33 pubkey + framing).
35
35
  * vsize = ceil((125*4 + 110) / 4) ≈ 153, rounded to 155.
36
36
  */
37
37
  export const P2WPKH_BEACON_TX_VSIZE = 155;
38
38
 
39
39
  /**
40
- * Conservative vsize estimate for a 1-input P2PKH 1 P2PKH change + 1 OP_RETURN(32) tx.
40
+ * Conservative vsize estimate for a 1-input P2PKH to 1 P2PKH change + 1 OP_RETURN(32) tx.
41
41
  * Legacy (non-segwit): scriptSig carries the full sig+pubkey (~108 bytes), no witness
42
42
  * discount. Stripped ≈ 4 nVer + 1 vin-count + (32+4+1+108+4) input + 1 vout-count +
43
43
  * 34 P2PKH-change + 43 OP_RETURN + 4 nLockTime ≈ 236 bytes. vsize = 236, rounded to 240.
@@ -169,7 +169,7 @@ async function fetchSpendableUtxo(
169
169
  * signing session consumes (via {@link SigningTxData}).
170
170
  *
171
171
  * This is the reusable counterpart to {@link SinglePartyBeacon.buildSignAndBroadcast}'s internal
172
- * construction step the aggregation path must produce an unsigned tx because the
172
+ * construction step: the aggregation path must produce an unsigned tx because the
173
173
  * signature comes from a MuSig2 round, not a local secret key.
174
174
  *
175
175
  * @param opts Parameters including the cohort's aggregate internal pubkey.
@@ -192,8 +192,13 @@ export async function buildAggregationBeaconTx(opts: {
192
192
  const feeEstimator = opts.feeEstimator ?? DEFAULT_FEE_ESTIMATOR;
193
193
  const { utxo, prevTxBytes } = await fetchSpendableUtxo(opts.beaconAddress, opts.bitcoin);
194
194
 
195
- const tapOut = p2tr(opts.internalPubkey, undefined, opts.network);
196
- const witnessScript = tapOut.script;
195
+ // The funded beacon output is a Taproot script-tree output: key path is the
196
+ // MuSig2 aggregate, script path is the k-of-n fallback + CSV recovery leaves
197
+ // (see cohort.ts and ADR 042). Derive the witnessUtxo scriptPubKey from the
198
+ // funded address itself; recomputing a key-path-only p2tr(internalPubkey) here
199
+ // would not match the script-tree UTXO on chain and would invalidate both the
200
+ // key-path sighash and the fallback script-path sighash.
201
+ const witnessScript = OutScript.encode(Address(opts.network).decode(opts.beaconAddress));
197
202
 
198
203
  // Fee cannot be probe-measured (no secret key for MuSig2 round). Use fixed P2TR vsize.
199
204
  const feeSats = await feeEstimator.estimateFee(P2TR_BEACON_TX_VSIZE);
@@ -258,7 +263,7 @@ async function signSingletonInput(
258
263
  // directly. We need only the sighash bytes so an external Signer can produce
259
264
  // the signature, so we reach through the type system here. If scure ever
260
265
  // renames this method, the P2PKH path tests fail loudly.
261
- // TODO: track https://github.com/paulmillr/scure-btc-signer/issues/142
266
+ // TODO: track https://github.com/paulmillr/scure-btc-signer/issues/142 -
262
267
  // drop the cast once a public preimage (e.g. `preimageP2PKH`) lands upstream.
263
268
  const sighashType = SigHash.ALL;
264
269
  const sighash = (tx as unknown as {
@@ -302,7 +307,7 @@ async function signSingletonInput(
302
307
  // `d' = taprootTweakPrivKey(d, merkleRoot)`; the verifier checks against the
303
308
  // tweaked output internal key `Q = P + tG`. The tweak lives inside the Signer
304
309
  // (it needs the secret key), so we use scheme 'bip341' rather than the raw
305
- // 'bip340' scheme. No script tree on singleton beacons no merkleRoot.
310
+ // 'bip340' scheme. No script tree on singleton beacons, no merkleRoot.
306
311
  const sighash = tx.preimageWitnessV1(inputIdx, [prevOutScript], SigHash.DEFAULT, [amount]);
307
312
  const sig = signer.sign(sighash, 'bip341');
308
313
  tx.updateInput(inputIdx, { tapKeySig: sig });
@@ -377,7 +382,7 @@ export abstract class SinglePartyBeacon {
377
382
  *
378
383
  * Composed from the three extracted phases ({@link buildSinglePartyTx},
379
384
  * {@link signSinglePartyTx}, {@link broadcastRawTx}) so each piece can be exercised
380
- * in isolation. Aggregation beacons use {@link buildAggregationBeaconTx} instead
385
+ * in isolation. Aggregation beacons use {@link buildAggregationBeaconTx} instead:
381
386
  * the multi-party path can't share the signing phase, but the tx-construction
382
387
  * plumbing (UTXO fetch + OP_RETURN output + change output) is shared.
383
388
  *
@@ -409,7 +414,7 @@ export abstract class SinglePartyBeacon {
409
414
  *
410
415
  * Detects the beacon address script kind (P2PKH / P2WPKH / P2TR) and configures
411
416
  * the input accordingly. Validates that the signer's pubkey produces the beacon
412
- * address under that script kind without this check, a misconfigured caller
417
+ * address under that script kind: without this check, a misconfigured caller
413
418
  * would burn a real UTXO on a tx that fails at broadcast. Fees are computed from
414
419
  * the per-kind {@link SINGLETON_BEACON_TX_VSIZE} constant, avoiding any probe-sign
415
420
  * round-trip.
@@ -9,7 +9,7 @@ import { SinglePartyBeacon } from './beacon.js';
9
9
  import type { BeaconService, BeaconSignal, BlockMetadata, CasPublishFn } from './interfaces.js';
10
10
 
11
11
  /**
12
- * CAS-specific broadcast options extends {@link BroadcastOptions} with an optional
12
+ * CAS-specific broadcast options: extends {@link BroadcastOptions} with an optional
13
13
  * `casPublish` callback used to publish the CAS Announcement off-chain after the
14
14
  * OP_RETURN signal is broadcast.
15
15
  */
@@ -21,7 +21,7 @@ export interface CASBroadcastOptions extends BroadcastOptions {
21
21
  * Implements {@link https://dcdpr.github.io/did-btcr2/terminology.html#cas-beacon | CAS Beacon}.
22
22
  *
23
23
  * A CAS (Content-Addressed Store) Beacon aggregates updates for multiple DIDs
24
- * into a single CAS Announcement a mapping of DIDs to their update hashes.
24
+ * into a single CAS Announcement: a mapping of DIDs to their update hashes.
25
25
  * The hash of the CAS Announcement is broadcast on-chain via OP_RETURN.
26
26
  * During resolution, the CAS Announcement is retrieved from the sidecar (or CAS)
27
27
  * and used to look up the individual signed update for the DID being resolved.
@@ -63,14 +63,14 @@ export class CASBeacon extends SinglePartyBeacon {
63
63
  const did = this.service.id.split('#')[0];
64
64
 
65
65
  for(const signal of signals) {
66
- // Signal bytes are hex matches hex-keyed sidecar maps directly
66
+ // Signal bytes are hex, matches hex-keyed sidecar maps directly
67
67
  const announcementHash = signal.signalBytes;
68
68
 
69
69
  // Look up the CAS Announcement in sidecar casMap
70
70
  const casAnnouncement = sidecar.casMap.get(announcementHash);
71
71
 
72
72
  if(!casAnnouncement) {
73
- // CAS Announcement not available emit a need
73
+ // CAS Announcement not available, emit a need
74
74
  needs.push({
75
75
  kind : 'NeedCASAnnouncement',
76
76
  announcementHash,
@@ -80,10 +80,10 @@ export class CASBeacon extends SinglePartyBeacon {
80
80
  }
81
81
 
82
82
  // Look up this DID's update hash in the CAS Announcement
83
- // Announcement values are base64urlnopad per spec convert to hex for map lookup
83
+ // Announcement values are base64urlnopad per spec, convert to hex for map lookup
84
84
  const updateHashEncoded = casAnnouncement[did];
85
85
 
86
- // If no entry for this DID, this announcement doesn't contain an update for us skip
86
+ // If no entry for this DID, this announcement doesn't contain an update for us, skip
87
87
  if(!updateHashEncoded) {
88
88
  continue;
89
89
  }
@@ -94,7 +94,7 @@ export class CASBeacon extends SinglePartyBeacon {
94
94
  const signedUpdate = sidecar.updateMap.get(updateHash);
95
95
 
96
96
  if(!signedUpdate) {
97
- // Signed update not available emit a need
97
+ // Signed update not available, emit a need
98
98
  needs.push({
99
99
  kind : 'NeedSignedUpdate',
100
100
  updateHash,
@@ -71,6 +71,6 @@ export interface BeaconSignal {
71
71
  * The method package defines this type; the api layer provides the implementation
72
72
  * (e.g., via CasApi.publish backed by IPFS/Helia).
73
73
  *
74
- * @param announcement The CAS Announcement object (DID update hash mapping).
74
+ * @param announcement The CAS Announcement object (DID to update hash mapping).
75
75
  */
76
76
  export type CasPublishFn = (announcement: Record<string, string>) => Promise<void>;
@@ -38,14 +38,14 @@ export class SingletonBeacon extends SinglePartyBeacon {
38
38
  const needs = new Array<DataNeed>();
39
39
 
40
40
  for(const signal of signals) {
41
- // Signal bytes are hex matches hex-keyed sidecar maps directly
41
+ // Signal bytes are hex, matches hex-keyed sidecar maps directly
42
42
  const updateHash = signal.signalBytes;
43
43
 
44
44
  // Look up the signed update in sidecar updateMap
45
45
  const signedUpdate = sidecar.updateMap.get(updateHash);
46
46
 
47
47
  if(!signedUpdate) {
48
- // Data not available emit a need instead of throwing
48
+ // Data not available, emit a need instead of throwing
49
49
  needs.push({
50
50
  kind : 'NeedSignedUpdate',
51
51
  updateHash,
@@ -60,7 +60,7 @@ export class SMTBeacon extends SinglePartyBeacon {
60
60
  const smtProof = sidecar.smtMap.get(signal.signalBytes);
61
61
 
62
62
  if(!smtProof) {
63
- // SMT Proof not available emit a need
63
+ // SMT Proof not available, emit a need
64
64
  needs.push({
65
65
  kind : 'NeedSMTProof',
66
66
  smtRootHash : signal.signalBytes,
@@ -95,7 +95,7 @@ export class SMTBeacon extends SinglePartyBeacon {
95
95
  );
96
96
  }
97
97
 
98
- // Non-inclusion proof verified no update for this DID this epoch, skip.
98
+ // Non-inclusion proof verified: no update for this DID this epoch, skip.
99
99
  if(!smtProof.updateId) {
100
100
  continue;
101
101
  }
@@ -106,7 +106,7 @@ export class SMTBeacon extends SinglePartyBeacon {
106
106
  const signedUpdate = sidecar.updateMap.get(updateHashHex);
107
107
 
108
108
  if(!signedUpdate) {
109
- // Signed update not available emit a need
109
+ // Signed update not available, emit a need
110
110
  needs.push({
111
111
  kind : 'NeedSignedUpdate',
112
112
  updateHash : updateHashHex,
@@ -164,7 +164,7 @@ export class Resolver {
164
164
  #resolvedResponse: DidResolutionResponse | null = null;
165
165
 
166
166
  /**
167
- * @internal Use {@link DidBtcr2.resolve} to create instances.
167
+ * @internal Use {@link DidBtcr2.resolve} to create instances.
168
168
  */
169
169
  constructor(
170
170
  didComponents: DidComponents,
@@ -540,13 +540,13 @@ export class Resolver {
540
540
 
541
541
  /**
542
542
  * Advance the state machine. Returns either:
543
- * - `{ status: 'action-required', needs }` caller must provide data via {@link provide}
544
- * - `{ status: 'resolved', result }` resolution complete
543
+ * - `{ status: 'action-required', needs }` - caller must provide data via {@link provide}
544
+ * - `{ status: 'resolved', result }` - resolution complete
545
545
  *
546
546
  * Analogous to Rust's `Resolver::resolve()`.
547
547
  */
548
548
  resolve(): ResolverState {
549
- // Internal loop keeps advancing through phases until data is needed or done
549
+ // Internal loop: keeps advancing through phases until data is needed or done
550
550
  while(true) {
551
551
  switch(this.#phase) {
552
552
 
@@ -554,7 +554,7 @@ export class Resolver {
554
554
  // Only entered for EXTERNAL (x HRP) identifiers when genesis doc was not in sidecar.
555
555
  case ResolverPhase.GenesisDocument: {
556
556
  if(this.#providedGenesisDocument) {
557
- // Genesis doc was provided establish the current document
557
+ // Genesis doc was provided, establish the current document
558
558
  this.#currentDocument = Resolver.external(
559
559
  this.#didComponents, this.#providedGenesisDocument
560
560
  );
@@ -595,7 +595,7 @@ export class Resolver {
595
595
  };
596
596
  }
597
597
 
598
- // No new beacon services to query move to processing
598
+ // No new beacon services to query, move to processing
599
599
  this.#phase = ResolverPhase.BeaconProcess;
600
600
  continue;
601
601
  }
@@ -614,10 +614,10 @@ export class Resolver {
614
614
  const result = beacon.processSignals(signals, this.#sidecarData);
615
615
 
616
616
  if(result.needs.length > 0) {
617
- // This service has unmet data needs collect them
617
+ // This service has unmet data needs, collect them
618
618
  allNeeds.push(...result.needs);
619
619
  } else {
620
- // All signals for this service resolved collect updates, mark processed
620
+ // All signals for this service resolved, collect updates, mark processed
621
621
  this.#unsortedUpdates.push(...result.updates);
622
622
  this.#processedServices.add(service.id);
623
623
  }
@@ -116,7 +116,7 @@ export interface UpdaterParams {
116
116
  }
117
117
 
118
118
  /**
119
- * Sans-I/O state machine for did:btcr2 updates the counterpart to {@link Resolver}.
119
+ * Sans-I/O state machine for did:btcr2 updates: the counterpart to {@link Resolver}.
120
120
  *
121
121
  * Created by {@link DidBtcr2.update} (the factory). The caller drives the update by
122
122
  * repeatedly calling {@link advance} and {@link provide}:
@@ -168,7 +168,7 @@ export class Updater {
168
168
  readonly #beaconService: BeaconService;
169
169
 
170
170
  /**
171
- * @internal Use {@link DidBtcr2.update} to create instances.
171
+ * @internal Use {@link DidBtcr2.update} to create instances.
172
172
  */
173
173
  constructor(params: UpdaterParams) {
174
174
  this.#sourceDocument = params.sourceDocument;
@@ -216,7 +216,7 @@ export class Updater {
216
216
  // checks W3C conformance but not this equality, so it's enforced explicitly here.
217
217
  if(targetDocument.id !== sourceDocument.id) {
218
218
  throw new UpdateError(
219
- `Patches must not change the DID document id (source "${sourceDocument.id}" target "${targetDocument.id}").`,
219
+ `Patches must not change the DID document id (source "${sourceDocument.id}" to target "${targetDocument.id}").`,
220
220
  INVALID_DID_UPDATE, { sourceId: sourceDocument.id, targetId: targetDocument.id }
221
221
  );
222
222
  }
@@ -315,8 +315,8 @@ export class Updater {
315
315
 
316
316
  /**
317
317
  * Advance the state machine. Returns either:
318
- * - `{ status: 'action-required', needs }` caller must provide data via {@link provide}
319
- * - `{ status: 'complete', result }` update is signed and broadcast
318
+ * - `{ status: 'action-required', needs }` caller must provide data via {@link provide}
319
+ * - `{ status: 'complete', result }` update is signed and broadcast
320
320
  */
321
321
  advance(): UpdaterState {
322
322
  while(true) {
@@ -331,7 +331,7 @@ export class Updater {
331
331
  }
332
332
 
333
333
  // Phase: Sign
334
- // Emit NeedSigningKey the caller supplies the secret key (or a KMS signature).
334
+ // Emit NeedSigningKey: the caller supplies the secret key (or a KMS signature).
335
335
  case 'Sign': {
336
336
  return {
337
337
  status : 'action-required',
package/src/did-btcr2.ts CHANGED
@@ -135,8 +135,8 @@ export class DidBtcr2 implements DidMethod {
135
135
  *
136
136
  * Factory method that validates the update parameters and returns a sans-I/O
137
137
  * {@link Updater} state machine. The caller drives the updater through its
138
- * phases (Construct Sign Broadcast Complete) by calling `advance()` and
139
- * `provide()`. The method package performs **zero I/O** signing key retrieval
138
+ * phases (Construct -> Sign -> Broadcast -> Complete) by calling `advance()` and
139
+ * `provide()`. The method package performs **zero I/O**: signing key retrieval
140
140
  * (or KMS delegation) and the on-chain broadcast are the caller's responsibility.
141
141
  *
142
142
  * For a fully-wired version with Bitcoin broadcast and key handling, see
package/src/index.ts CHANGED
@@ -3,6 +3,9 @@ export * from './core/aggregation/service.js';
3
3
  export * from './core/aggregation/participant.js';
4
4
  export * from './core/aggregation/signer.js';
5
5
  export * from './core/aggregation/conditions.js';
6
+ export * from './core/aggregation/recovery-policy.js';
7
+ export * from './core/aggregation/recovery-spend.js';
8
+ export * from './core/aggregation/fallback-spend.js';
6
9
  export * from './core/aggregation/cohort.js';
7
10
  export * from './core/aggregation/signing-session.js';
8
11
  export * from './core/aggregation/phases.js';