@interop/wallet-core 0.11.0 → 0.13.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.
- package/README.md +8 -2
- package/dist/enrollment/enrollment.d.ts +35 -1
- package/dist/enrollment/enrollment.d.ts.map +1 -1
- package/dist/enrollment/enrollment.js +31 -51
- package/dist/enrollment/enrollment.js.map +1 -1
- package/dist/keys/clientLabels.d.ts +85 -0
- package/dist/keys/clientLabels.d.ts.map +1 -0
- package/dist/keys/clientLabels.js +96 -0
- package/dist/keys/clientLabels.js.map +1 -0
- package/dist/keys/index.d.ts +13 -1
- package/dist/keys/index.d.ts.map +1 -1
- package/dist/keys/index.js +12 -1
- package/dist/keys/index.js.map +1 -1
- package/dist/keys/pukRoster.d.ts +65 -0
- package/dist/keys/pukRoster.d.ts.map +1 -1
- package/dist/keys/pukRoster.js +97 -0
- package/dist/keys/pukRoster.js.map +1 -1
- package/dist/keys/wasLabelsStore.d.ts +26 -0
- package/dist/keys/wasLabelsStore.d.ts.map +1 -0
- package/dist/keys/wasLabelsStore.js +27 -0
- package/dist/keys/wasLabelsStore.js.map +1 -0
- package/dist/space/collections.d.ts +10 -0
- package/dist/space/collections.d.ts.map +1 -1
- package/dist/space/collections.js +10 -0
- package/dist/space/collections.js.map +1 -1
- package/dist/space/index.d.ts +1 -1
- package/dist/space/index.d.ts.map +1 -1
- package/dist/space/index.js +1 -1
- package/dist/space/index.js.map +1 -1
- package/dist/webvh/didWebvh.d.ts +14 -0
- package/dist/webvh/didWebvh.d.ts.map +1 -1
- package/dist/webvh/didWebvh.js +25 -0
- package/dist/webvh/didWebvh.js.map +1 -1
- package/dist/webvh/index.d.ts +12 -0
- package/dist/webvh/index.d.ts.map +1 -1
- package/dist/webvh/index.js +11 -0
- package/dist/webvh/index.js.map +1 -1
- package/dist/webvh/listClients.d.ts +80 -0
- package/dist/webvh/listClients.d.ts.map +1 -0
- package/dist/webvh/listClients.js +114 -0
- package/dist/webvh/listClients.js.map +1 -0
- package/dist/webvh/revokeClient.d.ts +7 -1
- package/dist/webvh/revokeClient.d.ts.map +1 -1
- package/dist/webvh/revokeClient.js +8 -27
- package/dist/webvh/revokeClient.js.map +1 -1
- package/dist/webvh/verifyLog.d.ts +37 -0
- package/dist/webvh/verifyLog.d.ts.map +1 -0
- package/dist/webvh/verifyLog.js +75 -0
- package/dist/webvh/verifyLog.js.map +1 -0
- package/dist/webvh/wasIdStore.d.ts +34 -0
- package/dist/webvh/wasIdStore.d.ts.map +1 -0
- package/dist/webvh/wasIdStore.js +43 -0
- package/dist/webvh/wasIdStore.js.map +1 -0
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -65,7 +65,10 @@ The subpaths:
|
|
|
65
65
|
hosted DID log, its per-client update-key rotation, the client enrollment
|
|
66
66
|
entries, the one-entry client-revocation edit (verification methods, update
|
|
67
67
|
key, and standing commitments out in a single entry, the staged commitment
|
|
68
|
-
recovered by log attribution),
|
|
68
|
+
recovered by log attribution), the enrolled-client listing over a
|
|
69
|
+
caller-verified log (for a "your wallets" surface), the
|
|
70
|
+
fetch-and-verify-the-published-log step those ceremonies share, the WAS-backed
|
|
71
|
+
store they write through, and ZCap signing under the did:webvh
|
|
69
72
|
verification-method id.
|
|
70
73
|
|
|
71
74
|
- **`@interop/wallet-core/keys`** -- the per-user key (PUK) and its
|
|
@@ -74,7 +77,10 @@ The subpaths:
|
|
|
74
77
|
pin, the document-backed recipient resolver), the roster's compare-and-swap
|
|
75
78
|
descriptor store, and the PUK rotation cascade's per-collection op (re-epoch a
|
|
76
79
|
collection onto the roster's current PUK, staleness detected from durable
|
|
77
|
-
state alone, history escrowed -- also the completion sweep's building block)
|
|
80
|
+
state alone, history escrowed -- also the completion sweep's building block),
|
|
81
|
+
plus the detector that converges a roster left wrapping the current key to a
|
|
82
|
+
recipient the account document no longer keys. Also the enrolled-client
|
|
83
|
+
display labels (`key-map/client-labels.json`) and their WAS-backed store.
|
|
78
84
|
|
|
79
85
|
- **`@interop/wallet-core/descriptors`** -- collection encryption-descriptor
|
|
80
86
|
acquisition (fetch / cache / offline fallback) and the unknown-epoch refresh
|
|
@@ -1,3 +1,32 @@
|
|
|
1
|
+
/*!
|
|
2
|
+
* Copyright (c) 2026 Interop Alliance. All rights reserved.
|
|
3
|
+
*/
|
|
4
|
+
/**
|
|
5
|
+
* The client enrollment ceremony: connecting a second wallet client (a fresh
|
|
6
|
+
* browser profile, another app install) to an existing account without any
|
|
7
|
+
* secret ever leaving either side. The new client mints its whole key set
|
|
8
|
+
* locally -- client seed, did:webvh update-key seeds -- and only PUBLIC halves
|
|
9
|
+
* travel, as a compact "connect code" carried point-to-point (pasted between
|
|
10
|
+
* two browsers in the room today; the same payload renders as a QR for a
|
|
11
|
+
* camera-holding wallet). Nothing travels back over the channel: the account
|
|
12
|
+
* pointer comes out of the keyring (the enrollee holds the unlock secret), and
|
|
13
|
+
* the PUK comes back through the wrap-set roster.
|
|
14
|
+
*
|
|
15
|
+
* Push, not pull, in the recovery-anchor order (decryption material before
|
|
16
|
+
* authorization): the enrolling client wraps the PUK to the new client's
|
|
17
|
+
* key-agreement key in `key-map/puk.json` FIRST, then writes the two
|
|
18
|
+
* did:webvh log entries (commit, then add-VMs-and-update-key). No
|
|
19
|
+
* authorized-but-blind window exists at any point, and both tear points
|
|
20
|
+
* resume by re-running the ceremony with the same code -- a tear after the
|
|
21
|
+
* roster write leaves an orphan wrap (invisible to authorization), a tear
|
|
22
|
+
* between the log entries is detected from the published commitments.
|
|
23
|
+
*
|
|
24
|
+
* The new client's first roster read happens post-enrollment, signed with its
|
|
25
|
+
* `<did:webvh>#<multibase>` key -- the server authorizes it under the
|
|
26
|
+
* current-key-set rule the moment the add entry publishes. Persisting the key
|
|
27
|
+
* set under the app's own unlock layer is the caller's job: this module hands
|
|
28
|
+
* back the PUK and the roster epoch to pin, and stops there.
|
|
29
|
+
*/
|
|
1
30
|
import type { IKeyAgreementKey } from '@interop/data-integrity-core';
|
|
2
31
|
import type { EncryptionDescriptorStore } from '@interop/was-client/edv';
|
|
3
32
|
import type { ClientWebvhUpdateKeys, WebvhEnrollmentKeys, WebvhIdStore } from '../webvh/didWebvh.js';
|
|
@@ -98,7 +127,10 @@ export declare function mintEnrollmentRequest(): Promise<{
|
|
|
98
127
|
* @param options.pukRosterStore {EncryptionDescriptorStore} the account's
|
|
99
128
|
* `key-map/puk.json` descriptor store
|
|
100
129
|
* @param options.idStore {WebvhIdStore} the account's `id` collection
|
|
101
|
-
* @returns {Promise<
|
|
130
|
+
* @returns {Promise<object>} the account's did:webvh, plus the enrollee's
|
|
131
|
+
* own identity as this call already knows it: its did:key and its signing-key
|
|
132
|
+
* multibase (the key a label or a listing row is filed under), so the caller
|
|
133
|
+
* needs no second parse of the connect code
|
|
102
134
|
*/
|
|
103
135
|
export declare function approveEnrollment({ request, clientWebvhKeys, clientKeyAgreementKey, pukRosterStore, idStore }: {
|
|
104
136
|
request: EnrollmentRequest;
|
|
@@ -108,6 +140,8 @@ export declare function approveEnrollment({ request, clientWebvhKeys, clientKeyA
|
|
|
108
140
|
idStore: WebvhIdStore;
|
|
109
141
|
}): Promise<{
|
|
110
142
|
did: string;
|
|
143
|
+
clientDid: string;
|
|
144
|
+
signingKeyMultibase: string;
|
|
111
145
|
}>;
|
|
112
146
|
/**
|
|
113
147
|
* ENROLLEE, step two (after the other client approves): verifies the
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"enrollment.d.ts","sourceRoot":"","sources":["../../src/enrollment/enrollment.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"enrollment.d.ts","sourceRoot":"","sources":["../../src/enrollment/enrollment.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH;;;;;;;;;;;;;;;;;;;;;;;;;GAyBG;AACH,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,8BAA8B,CAAA;AACpE,OAAO,KAAK,EAAE,yBAAyB,EAAE,MAAM,yBAAyB,CAAA;AAQxE,OAAO,KAAK,EACV,qBAAqB,EACrB,mBAAmB,EACnB,YAAY,EACb,MAAM,sBAAsB,CAAA;AAU7B,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,gBAAgB,CAAA;AACzC,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAA;AAa1D;;;;GAIG;AACH,MAAM,MAAM,iBAAiB,GAAG,mBAAmB,CAAA;AAEnD;;;;GAIG;AACH,qBAAa,sBAAuB,SAAQ,KAAK;gBAE7C,OAAO,SAC+C;CAKzD;AASD;;;;;;GAMG;AACH,wBAAgB,uBAAuB,CAAC,EACtC,OAAO,EACR,EAAE;IACD,OAAO,EAAE,iBAAiB,CAAA;CAC3B,GAAG,MAAM,CAKT;AAED;;;;;;;;;GASG;AACH,wBAAgB,sBAAsB,CAAC,EACrC,IAAI,EACL,EAAE;IACD,IAAI,EAAE,MAAM,CAAA;CACb,GAAG,iBAAiB,CAwDpB;AAED;;;;;;;;GAQG;AACH,wBAAgB,mBAAmB,CAAC,EAClC,OAAO,EACR,EAAE;IACD,OAAO,EAAE,iBAAiB,CAAA;CAC3B,GAAG,MAAM,CAET;AAED;;;;;;;;;GASG;AACH,wBAAgB,sBAAsB,CAAC,EACrC,OAAO,EACR,EAAE;IACD,OAAO,EAAE,iBAAiB,CAAA;CAC3B,GAAG,MAAM,CAKT;AAED;;;;;;;;;GASG;AACH,wBAAsB,qBAAqB,IAAI,OAAO,CAAC;IACrD,UAAU,EAAE,UAAU,CAAA;IACtB,eAAe,EAAE,qBAAqB,CAAA;IACtC,IAAI,EAAE,MAAM,CAAA;IACZ,SAAS,EAAE,MAAM,CAAA;CAClB,CAAC,CA2BD;AAED;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,wBAAsB,iBAAiB,CAAC,EACtC,OAAO,EACP,eAAe,EACf,qBAAqB,EACrB,cAAc,EACd,OAAO,EACR,EAAE;IACD,OAAO,EAAE,iBAAiB,CAAA;IAC1B,eAAe,EAAE,qBAAqB,CAAA;IACtC,qBAAqB,EAAE,gBAAgB,CAAA;IACvC,cAAc,EAAE,yBAAyB,CAAA;IACzC,OAAO,EAAE,YAAY,CAAA;CACtB,GAAG,OAAO,CAAC;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,SAAS,EAAE,MAAM,CAAC;IAAC,mBAAmB,EAAE,MAAM,CAAA;CAAE,CAAC,CAsB3E;AAED;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AACH,wBAAsB,sBAAsB,CAAC,EAC3C,UAAU,EACV,eAAe,EACf,OAAO,EACR,EAAE;IACD,UAAU,EAAE,UAAU,CAAA;IACtB,eAAe,EAAE,qBAAqB,CAAA;IACtC,OAAO,EAAE,cAAc,CAAA;CACxB,GAAG,OAAO,CAAC;IAAE,GAAG,EAAE,GAAG,CAAC;IAAC,aAAa,EAAE,MAAM,CAAA;CAAE,CAAC,CA8D/C"}
|
|
@@ -1,40 +1,10 @@
|
|
|
1
|
-
/*!
|
|
2
|
-
* Copyright (c) 2026 Interop Alliance. All rights reserved.
|
|
3
|
-
*/
|
|
4
|
-
/**
|
|
5
|
-
* The client enrollment ceremony: connecting a second wallet client (a fresh
|
|
6
|
-
* browser profile, another app install) to an existing account without any
|
|
7
|
-
* secret ever leaving either side. The new client mints its whole key set
|
|
8
|
-
* locally -- client seed, did:webvh update-key seeds -- and only PUBLIC halves
|
|
9
|
-
* travel, as a compact "connect code" carried point-to-point (pasted between
|
|
10
|
-
* two browsers in the room today; the same payload renders as a QR for a
|
|
11
|
-
* camera-holding wallet). Nothing travels back over the channel: the account
|
|
12
|
-
* pointer comes out of the keyring (the enrollee holds the unlock secret), and
|
|
13
|
-
* the PUK comes back through the wrap-set roster.
|
|
14
|
-
*
|
|
15
|
-
* Push, not pull, in the recovery-anchor order (decryption material before
|
|
16
|
-
* authorization): the enrolling client wraps the PUK to the new client's
|
|
17
|
-
* key-agreement key in `key-map/puk.json` FIRST, then writes the two
|
|
18
|
-
* did:webvh log entries (commit, then add-VMs-and-update-key). No
|
|
19
|
-
* authorized-but-blind window exists at any point, and both tear points
|
|
20
|
-
* resume by re-running the ceremony with the same code -- a tear after the
|
|
21
|
-
* roster write leaves an orphan wrap (invisible to authorization), a tear
|
|
22
|
-
* between the log entries is detected from the published commitments.
|
|
23
|
-
*
|
|
24
|
-
* The new client's first roster read happens post-enrollment, signed with its
|
|
25
|
-
* `<did:webvh>#<multibase>` key -- the server authorizes it under the
|
|
26
|
-
* current-key-set rule the moment the add entry publishes. Persisting the key
|
|
27
|
-
* set under the app's own unlock layer is the caller's job: this module hands
|
|
28
|
-
* back the PUK and the roster epoch to pin, and stops there.
|
|
29
|
-
*/
|
|
30
|
-
import { readLogFromString, resolveDIDFromLog } from '@interop/did-method-webvh';
|
|
31
1
|
import { base64urlnopad } from '@scure/base';
|
|
32
2
|
import { agentsFromSeed } from '../identity/agents.js';
|
|
33
|
-
import { DID_LOG_RESOURCE, ID_COLLECTION } from '../space/collections.js';
|
|
34
3
|
import { enrollWebvhClient, mintClientWebvhUpdateKeys, updateKeyMultibase } from '../webvh/didWebvh.js';
|
|
35
4
|
import { clientSigningKeyMultibase, isWebvhDid, webvhZcapClient } from '../webvh/zcap.js';
|
|
5
|
+
import { AccountLogMissingError, verifyAccountLog } from '../webvh/verifyLog.js';
|
|
36
6
|
import { addPukRosterRecipient } from '../keys/pukRoster.js';
|
|
37
|
-
import { readPukRoster } from '../keys/pukRoster.js';
|
|
7
|
+
import { readPukRoster, rosterRecipientKid } from '../keys/pukRoster.js';
|
|
38
8
|
import { pukRosterDescriptorStore } from '../keys/rosterStore.js';
|
|
39
9
|
/**
|
|
40
10
|
* The connect-code prefix; the payload after it is base64url(JSON) of an
|
|
@@ -139,7 +109,10 @@ export function enrollmentClientDid({ request }) {
|
|
|
139
109
|
* @returns {string}
|
|
140
110
|
*/
|
|
141
111
|
export function enrollmentRecipientKid({ request }) {
|
|
142
|
-
return
|
|
112
|
+
return rosterRecipientKid({
|
|
113
|
+
signingKeyMultibase: request.signingKeyMultibase,
|
|
114
|
+
keyAgreementKeyMultibase: request.keyAgreementKeyMultibase
|
|
115
|
+
});
|
|
143
116
|
}
|
|
144
117
|
/**
|
|
145
118
|
* ENROLLEE, step one: mints the new client's whole key set locally and
|
|
@@ -195,7 +168,10 @@ export async function mintEnrollmentRequest() {
|
|
|
195
168
|
* @param options.pukRosterStore {EncryptionDescriptorStore} the account's
|
|
196
169
|
* `key-map/puk.json` descriptor store
|
|
197
170
|
* @param options.idStore {WebvhIdStore} the account's `id` collection
|
|
198
|
-
* @returns {Promise<
|
|
171
|
+
* @returns {Promise<object>} the account's did:webvh, plus the enrollee's
|
|
172
|
+
* own identity as this call already knows it: its did:key and its signing-key
|
|
173
|
+
* multibase (the key a label or a listing row is filed under), so the caller
|
|
174
|
+
* needs no second parse of the connect code
|
|
199
175
|
*/
|
|
200
176
|
export async function approveEnrollment({ request, clientWebvhKeys, clientKeyAgreementKey, pukRosterStore, idStore }) {
|
|
201
177
|
// Decryption material before authorization: the wrap lands first, so no
|
|
@@ -208,11 +184,16 @@ export async function approveEnrollment({ request, clientWebvhKeys, clientKeyAgr
|
|
|
208
184
|
},
|
|
209
185
|
ownerKeyAgreementKey: clientKeyAgreementKey
|
|
210
186
|
});
|
|
211
|
-
|
|
187
|
+
const { did } = await enrollWebvhClient({
|
|
212
188
|
idStore,
|
|
213
189
|
updateKeys: clientWebvhKeys,
|
|
214
190
|
newClient: request
|
|
215
191
|
});
|
|
192
|
+
return {
|
|
193
|
+
did,
|
|
194
|
+
clientDid: enrollmentClientDid({ request }),
|
|
195
|
+
signingKeyMultibase: request.signingKeyMultibase
|
|
196
|
+
};
|
|
216
197
|
}
|
|
217
198
|
/**
|
|
218
199
|
* ENROLLEE, step two (after the other client approves): verifies the
|
|
@@ -249,28 +230,27 @@ export async function completeEnrollmentCore({ clientSeed, webvhUpdateKeys, poin
|
|
|
249
230
|
});
|
|
250
231
|
// Verify the enrollment from the world-readable, self-certifying log: it
|
|
251
232
|
// must resolve to exactly the DID the account pointer names, and its
|
|
252
|
-
// document must list this client's keys -- the add entry has published.
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
const resolved = await resolveDIDFromLog(readLogFromString(await response.text()));
|
|
262
|
-
if (resolved.meta.error || !resolved.did || !resolved.doc) {
|
|
263
|
-
throw new Error(`The account's DID log failed to resolve (${resolved.meta.error}).`);
|
|
233
|
+
// document must list this client's keys -- the add entry has published. An
|
|
234
|
+
// absent log is the same "not yet" state as an unpublished add entry.
|
|
235
|
+
let verified;
|
|
236
|
+
try {
|
|
237
|
+
verified = await verifyAccountLog({
|
|
238
|
+
did,
|
|
239
|
+
spaceId: pointer.spaceId,
|
|
240
|
+
host: pointer.host
|
|
241
|
+
});
|
|
264
242
|
}
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
243
|
+
catch (err) {
|
|
244
|
+
if (err instanceof AccountLogMissingError) {
|
|
245
|
+
throw new EnrollmentPendingError();
|
|
246
|
+
}
|
|
247
|
+
throw err;
|
|
268
248
|
}
|
|
269
249
|
const signingMultibase = clientSigningKeyMultibase({ keyAgent });
|
|
270
250
|
const updateKey = await updateKeyMultibase({
|
|
271
251
|
seed: webvhUpdateKeys.updateSeed
|
|
272
252
|
});
|
|
273
|
-
const enrolled = (
|
|
253
|
+
const enrolled = (verified.doc.verificationMethod ?? []).some(method => method.publicKeyMultibase === signingMultibase) && verified.updateKeys.includes(updateKey);
|
|
274
254
|
if (!enrolled) {
|
|
275
255
|
throw new EnrollmentPendingError();
|
|
276
256
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"enrollment.js","sourceRoot":"","sources":["../../src/enrollment/enrollment.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"enrollment.js","sourceRoot":"","sources":["../../src/enrollment/enrollment.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
/*!
|
|
2
|
+
* Copyright (c) 2026 Interop Alliance. All rights reserved.
|
|
3
|
+
*/
|
|
4
|
+
/**
|
|
5
|
+
* Enrolled-client display labels: the `key-map/client-labels.json` record, a
|
|
6
|
+
* plain-JSON map from a client's signing-key multibase to the human-chosen
|
|
7
|
+
* label a "your wallets" surface shows. The did:webvh document is the roster
|
|
8
|
+
* of record and deliberately carries key material only, so labels live
|
|
9
|
+
* beside the account's other key-map resources instead -- private,
|
|
10
|
+
* capability-gated, and shared by every enrolled client (each wallet app
|
|
11
|
+
* reads and writes the same record).
|
|
12
|
+
*
|
|
13
|
+
* The record is display metadata with no authority: a missing or malformed
|
|
14
|
+
* record degrades to unlabeled rows, an entry whose key the document no
|
|
15
|
+
* longer lists is simply never shown, and writes are last-write-wins (a lost
|
|
16
|
+
* race costs at most a label). I/O runs through the two-method
|
|
17
|
+
* {@link ClientLabelsStore} seam a wallet app satisfies with its own
|
|
18
|
+
* remote-store class.
|
|
19
|
+
*/
|
|
20
|
+
/**
|
|
21
|
+
* The Space-side seam: the single `client-labels.json` resource in the
|
|
22
|
+
* private `key-map` collection.
|
|
23
|
+
*/
|
|
24
|
+
export interface ClientLabelsStore {
|
|
25
|
+
/**
|
|
26
|
+
* The parsed JSON body of `client-labels.json`, or `undefined` when it has
|
|
27
|
+
* never been written.
|
|
28
|
+
*/
|
|
29
|
+
get(): Promise<unknown>;
|
|
30
|
+
/**
|
|
31
|
+
* Writes (upserts) `client-labels.json`.
|
|
32
|
+
*/
|
|
33
|
+
put(options: {
|
|
34
|
+
content: object;
|
|
35
|
+
}): Promise<void>;
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* The version-1 labels record: signing-key multibase to label.
|
|
39
|
+
*/
|
|
40
|
+
export interface ClientLabelsRecord {
|
|
41
|
+
version: 1;
|
|
42
|
+
labels: Record<string, string>;
|
|
43
|
+
}
|
|
44
|
+
/**
|
|
45
|
+
* Reads the labels record, degrading to an empty record when it is missing
|
|
46
|
+
* or malformed (labels are display metadata; a broken record must never
|
|
47
|
+
* block a listing).
|
|
48
|
+
*
|
|
49
|
+
* @param options {object}
|
|
50
|
+
* @param options.store {ClientLabelsStore}
|
|
51
|
+
* @returns {Promise<ClientLabelsRecord>}
|
|
52
|
+
*/
|
|
53
|
+
export declare function readClientLabels({ store }: {
|
|
54
|
+
store: ClientLabelsStore;
|
|
55
|
+
}): Promise<ClientLabelsRecord>;
|
|
56
|
+
/**
|
|
57
|
+
* Sets (or renames) one client's label, read-modify-write over the stored
|
|
58
|
+
* record. A blank label removes the entry instead of storing whitespace.
|
|
59
|
+
*
|
|
60
|
+
* @param options {object}
|
|
61
|
+
* @param options.store {ClientLabelsStore}
|
|
62
|
+
* @param options.signingKeyMultibase {string}
|
|
63
|
+
* @param options.label {string}
|
|
64
|
+
* @returns {Promise<ClientLabelsRecord>} the record as written
|
|
65
|
+
*/
|
|
66
|
+
export declare function setClientLabel({ store, signingKeyMultibase, label }: {
|
|
67
|
+
store: ClientLabelsStore;
|
|
68
|
+
signingKeyMultibase: string;
|
|
69
|
+
label: string;
|
|
70
|
+
}): Promise<ClientLabelsRecord>;
|
|
71
|
+
/**
|
|
72
|
+
* Drops one client's label (revocation hygiene -- the label of a
|
|
73
|
+
* disconnected client points at nothing). A record without the entry is a
|
|
74
|
+
* no-op that writes nothing.
|
|
75
|
+
*
|
|
76
|
+
* @param options {object}
|
|
77
|
+
* @param options.store {ClientLabelsStore}
|
|
78
|
+
* @param options.signingKeyMultibase {string}
|
|
79
|
+
* @returns {Promise<ClientLabelsRecord>} the record as stored
|
|
80
|
+
*/
|
|
81
|
+
export declare function removeClientLabel({ store, signingKeyMultibase }: {
|
|
82
|
+
store: ClientLabelsStore;
|
|
83
|
+
signingKeyMultibase: string;
|
|
84
|
+
}): Promise<ClientLabelsRecord>;
|
|
85
|
+
//# sourceMappingURL=clientLabels.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"clientLabels.d.ts","sourceRoot":"","sources":["../../src/keys/clientLabels.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH;;;;;;;;;;;;;;;GAeG;AAEH;;;GAGG;AACH,MAAM,WAAW,iBAAiB;IAChC;;;OAGG;IACH,GAAG,IAAI,OAAO,CAAC,OAAO,CAAC,CAAA;IACvB;;OAEG;IACH,GAAG,CAAC,OAAO,EAAE;QAAE,OAAO,EAAE,MAAM,CAAA;KAAE,GAAG,OAAO,CAAC,IAAI,CAAC,CAAA;CACjD;AAED;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC,OAAO,EAAE,CAAC,CAAA;IACV,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAA;CAC/B;AAED;;;;;;;;GAQG;AACH,wBAAsB,gBAAgB,CAAC,EACrC,KAAK,EACN,EAAE;IACD,KAAK,EAAE,iBAAiB,CAAA;CACzB,GAAG,OAAO,CAAC,kBAAkB,CAAC,CAqB9B;AAED;;;;;;;;;GASG;AACH,wBAAsB,cAAc,CAAC,EACnC,KAAK,EACL,mBAAmB,EACnB,KAAK,EACN,EAAE;IACD,KAAK,EAAE,iBAAiB,CAAA;IACxB,mBAAmB,EAAE,MAAM,CAAA;IAC3B,KAAK,EAAE,MAAM,CAAA;CACd,GAAG,OAAO,CAAC,kBAAkB,CAAC,CAY9B;AAED;;;;;;;;;GASG;AACH,wBAAsB,iBAAiB,CAAC,EACtC,KAAK,EACL,mBAAmB,EACpB,EAAE;IACD,KAAK,EAAE,iBAAiB,CAAA;IACxB,mBAAmB,EAAE,MAAM,CAAA;CAC5B,GAAG,OAAO,CAAC,kBAAkB,CAAC,CAU9B"}
|
|
@@ -0,0 +1,96 @@
|
|
|
1
|
+
/*!
|
|
2
|
+
* Copyright (c) 2026 Interop Alliance. All rights reserved.
|
|
3
|
+
*/
|
|
4
|
+
/**
|
|
5
|
+
* Enrolled-client display labels: the `key-map/client-labels.json` record, a
|
|
6
|
+
* plain-JSON map from a client's signing-key multibase to the human-chosen
|
|
7
|
+
* label a "your wallets" surface shows. The did:webvh document is the roster
|
|
8
|
+
* of record and deliberately carries key material only, so labels live
|
|
9
|
+
* beside the account's other key-map resources instead -- private,
|
|
10
|
+
* capability-gated, and shared by every enrolled client (each wallet app
|
|
11
|
+
* reads and writes the same record).
|
|
12
|
+
*
|
|
13
|
+
* The record is display metadata with no authority: a missing or malformed
|
|
14
|
+
* record degrades to unlabeled rows, an entry whose key the document no
|
|
15
|
+
* longer lists is simply never shown, and writes are last-write-wins (a lost
|
|
16
|
+
* race costs at most a label). I/O runs through the two-method
|
|
17
|
+
* {@link ClientLabelsStore} seam a wallet app satisfies with its own
|
|
18
|
+
* remote-store class.
|
|
19
|
+
*/
|
|
20
|
+
/**
|
|
21
|
+
* Reads the labels record, degrading to an empty record when it is missing
|
|
22
|
+
* or malformed (labels are display metadata; a broken record must never
|
|
23
|
+
* block a listing).
|
|
24
|
+
*
|
|
25
|
+
* @param options {object}
|
|
26
|
+
* @param options.store {ClientLabelsStore}
|
|
27
|
+
* @returns {Promise<ClientLabelsRecord>}
|
|
28
|
+
*/
|
|
29
|
+
export async function readClientLabels({ store }) {
|
|
30
|
+
let body;
|
|
31
|
+
try {
|
|
32
|
+
body = await store.get();
|
|
33
|
+
}
|
|
34
|
+
catch {
|
|
35
|
+
return { version: 1, labels: {} };
|
|
36
|
+
}
|
|
37
|
+
if (body === null || typeof body !== 'object') {
|
|
38
|
+
return { version: 1, labels: {} };
|
|
39
|
+
}
|
|
40
|
+
const { version, labels } = body;
|
|
41
|
+
if (version !== 1 || labels === null || typeof labels !== 'object') {
|
|
42
|
+
return { version: 1, labels: {} };
|
|
43
|
+
}
|
|
44
|
+
const parsed = {};
|
|
45
|
+
for (const [key, value] of Object.entries(labels)) {
|
|
46
|
+
if (typeof value === 'string') {
|
|
47
|
+
parsed[key] = value;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
return { version: 1, labels: parsed };
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Sets (or renames) one client's label, read-modify-write over the stored
|
|
54
|
+
* record. A blank label removes the entry instead of storing whitespace.
|
|
55
|
+
*
|
|
56
|
+
* @param options {object}
|
|
57
|
+
* @param options.store {ClientLabelsStore}
|
|
58
|
+
* @param options.signingKeyMultibase {string}
|
|
59
|
+
* @param options.label {string}
|
|
60
|
+
* @returns {Promise<ClientLabelsRecord>} the record as written
|
|
61
|
+
*/
|
|
62
|
+
export async function setClientLabel({ store, signingKeyMultibase, label }) {
|
|
63
|
+
const trimmed = label.trim();
|
|
64
|
+
if (!trimmed) {
|
|
65
|
+
return removeClientLabel({ store, signingKeyMultibase });
|
|
66
|
+
}
|
|
67
|
+
const record = await readClientLabels({ store });
|
|
68
|
+
const updated = {
|
|
69
|
+
version: 1,
|
|
70
|
+
labels: { ...record.labels, [signingKeyMultibase]: trimmed }
|
|
71
|
+
};
|
|
72
|
+
await store.put({ content: updated });
|
|
73
|
+
return updated;
|
|
74
|
+
}
|
|
75
|
+
/**
|
|
76
|
+
* Drops one client's label (revocation hygiene -- the label of a
|
|
77
|
+
* disconnected client points at nothing). A record without the entry is a
|
|
78
|
+
* no-op that writes nothing.
|
|
79
|
+
*
|
|
80
|
+
* @param options {object}
|
|
81
|
+
* @param options.store {ClientLabelsStore}
|
|
82
|
+
* @param options.signingKeyMultibase {string}
|
|
83
|
+
* @returns {Promise<ClientLabelsRecord>} the record as stored
|
|
84
|
+
*/
|
|
85
|
+
export async function removeClientLabel({ store, signingKeyMultibase }) {
|
|
86
|
+
const record = await readClientLabels({ store });
|
|
87
|
+
if (!(signingKeyMultibase in record.labels)) {
|
|
88
|
+
return record;
|
|
89
|
+
}
|
|
90
|
+
const labels = { ...record.labels };
|
|
91
|
+
delete labels[signingKeyMultibase];
|
|
92
|
+
const updated = { version: 1, labels };
|
|
93
|
+
await store.put({ content: updated });
|
|
94
|
+
return updated;
|
|
95
|
+
}
|
|
96
|
+
//# sourceMappingURL=clientLabels.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"clientLabels.js","sourceRoot":"","sources":["../../src/keys/clientLabels.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH;;;;;;;;;;;;;;;GAeG;AA0BH;;;;;;;;GAQG;AACH,MAAM,CAAC,KAAK,UAAU,gBAAgB,CAAC,EACrC,KAAK,EAGN;IACC,IAAI,IAAa,CAAA;IACjB,IAAI,CAAC;QACH,IAAI,GAAG,MAAM,KAAK,CAAC,GAAG,EAAE,CAAA;IAC1B,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,MAAM,EAAE,EAAE,EAAE,CAAA;IACnC,CAAC;IACD,IAAI,IAAI,KAAK,IAAI,IAAI,OAAO,IAAI,KAAK,QAAQ,EAAE,CAAC;QAC9C,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,MAAM,EAAE,EAAE,EAAE,CAAA;IACnC,CAAC;IACD,MAAM,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,IAA+C,CAAA;IAC3E,IAAI,OAAO,KAAK,CAAC,IAAI,MAAM,KAAK,IAAI,IAAI,OAAO,MAAM,KAAK,QAAQ,EAAE,CAAC;QACnE,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,MAAM,EAAE,EAAE,EAAE,CAAA;IACnC,CAAC;IACD,MAAM,MAAM,GAA2B,EAAE,CAAA;IACzC,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC,EAAE,CAAC;QAClD,IAAI,OAAO,KAAK,KAAK,QAAQ,EAAE,CAAC;YAC9B,MAAM,CAAC,GAAG,CAAC,GAAG,KAAK,CAAA;QACrB,CAAC;IACH,CAAC;IACD,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,MAAM,EAAE,MAAM,EAAE,CAAA;AACvC,CAAC;AAED;;;;;;;;;GASG;AACH,MAAM,CAAC,KAAK,UAAU,cAAc,CAAC,EACnC,KAAK,EACL,mBAAmB,EACnB,KAAK,EAKN;IACC,MAAM,OAAO,GAAG,KAAK,CAAC,IAAI,EAAE,CAAA;IAC5B,IAAI,CAAC,OAAO,EAAE,CAAC;QACb,OAAO,iBAAiB,CAAC,EAAE,KAAK,EAAE,mBAAmB,EAAE,CAAC,CAAA;IAC1D,CAAC;IACD,MAAM,MAAM,GAAG,MAAM,gBAAgB,CAAC,EAAE,KAAK,EAAE,CAAC,CAAA;IAChD,MAAM,OAAO,GAAuB;QAClC,OAAO,EAAE,CAAC;QACV,MAAM,EAAE,EAAE,GAAG,MAAM,CAAC,MAAM,EAAE,CAAC,mBAAmB,CAAC,EAAE,OAAO,EAAE;KAC7D,CAAA;IACD,MAAM,KAAK,CAAC,GAAG,CAAC,EAAE,OAAO,EAAE,OAAO,EAAE,CAAC,CAAA;IACrC,OAAO,OAAO,CAAA;AAChB,CAAC;AAED;;;;;;;;;GASG;AACH,MAAM,CAAC,KAAK,UAAU,iBAAiB,CAAC,EACtC,KAAK,EACL,mBAAmB,EAIpB;IACC,MAAM,MAAM,GAAG,MAAM,gBAAgB,CAAC,EAAE,KAAK,EAAE,CAAC,CAAA;IAChD,IAAI,CAAC,CAAC,mBAAmB,IAAI,MAAM,CAAC,MAAM,CAAC,EAAE,CAAC;QAC5C,OAAO,MAAM,CAAA;IACf,CAAC;IACD,MAAM,MAAM,GAAG,EAAE,GAAG,MAAM,CAAC,MAAM,EAAE,CAAA;IACnC,OAAO,MAAM,CAAC,mBAAmB,CAAC,CAAA;IAClC,MAAM,OAAO,GAAuB,EAAE,OAAO,EAAE,CAAC,EAAE,MAAM,EAAE,CAAA;IAC1D,MAAM,KAAK,CAAC,GAAG,CAAC,EAAE,OAAO,EAAE,OAAO,EAAE,CAAC,CAAA;IACrC,OAAO,OAAO,CAAA;AAChB,CAAC"}
|
package/dist/keys/index.d.ts
CHANGED
|
@@ -16,6 +16,15 @@
|
|
|
16
16
|
* document).
|
|
17
17
|
* - `pukRosterDescriptorStore` -- that descriptor store, built from a bare
|
|
18
18
|
* signing client for the login-time direct read.
|
|
19
|
+
* - `rosterRecipientKid` -- the one builder of a client's roster kid, shared by
|
|
20
|
+
* the enrollment wrap, the roster read, and the rotation that retires it.
|
|
21
|
+
* - `convergePukRosterToDocument` -- the standing detector for a revocation
|
|
22
|
+
* cascade torn between the document edit and the roster rotation: a roster
|
|
23
|
+
* recipient the document no longer keys is rotated away from.
|
|
24
|
+
* - `readClientLabels` / `setClientLabel` / `removeClientLabel` /
|
|
25
|
+
* `wasClientLabelsStore` -- the enrolled-client display labels
|
|
26
|
+
* (`key-map/client-labels.json`), the record a "your wallets" surface names
|
|
27
|
+
* clients from, and the WAS-backed store they run through.
|
|
19
28
|
* - `rotatePukRoster` / `unwrapPukGenerations` / `rotateCollectionEpochsToPuk`
|
|
20
29
|
* / `cascadeCollectionsToPuk` / `pukAsRecipient` -- the PUK rotation
|
|
21
30
|
* cascade: the roster rotation off a revoked recipient, the per-collection
|
|
@@ -25,9 +34,12 @@
|
|
|
25
34
|
*/
|
|
26
35
|
export { mintPuk, pukVaultKeys } from './puk.js';
|
|
27
36
|
export type { Puk } from './puk.js';
|
|
28
|
-
export { addPukRosterRecipient, ensurePukRoster, PukRosterContinuityError, PukRosterIntegrityError, PukRosterUnwrapError, pukRosterRecipientResolver, readPukRoster, rotatePukRoster } from './pukRoster.js';
|
|
37
|
+
export { addPukRosterRecipient, convergePukRosterToDocument, ensurePukRoster, PukRosterContinuityError, PukRosterIntegrityError, PukRosterUnwrapError, pukRosterRecipientResolver, readPukRoster, rosterRecipientKid, rotatePukRoster } from './pukRoster.js';
|
|
29
38
|
export { cascadeCollectionsToPuk, pukAsRecipient, rotateCollectionEpochsToPuk, unwrapPukGenerations } from './pukCascade.js';
|
|
30
39
|
export type { CollectionPukRotationOutcome, PukCascadeResult } from './pukCascade.js';
|
|
31
40
|
export type { PukRosterReadResult, RosterRecipientDocument } from './pukRoster.js';
|
|
32
41
|
export { pukRosterDescriptorStore } from './rosterStore.js';
|
|
42
|
+
export { readClientLabels, removeClientLabel, setClientLabel } from './clientLabels.js';
|
|
43
|
+
export type { ClientLabelsRecord, ClientLabelsStore } from './clientLabels.js';
|
|
44
|
+
export { wasClientLabelsStore } from './wasLabelsStore.js';
|
|
33
45
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/keys/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/keys/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/keys/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AACH,OAAO,EAAE,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAA;AAChD,YAAY,EAAE,GAAG,EAAE,MAAM,UAAU,CAAA;AAEnC,OAAO,EACL,qBAAqB,EACrB,2BAA2B,EAC3B,eAAe,EACf,wBAAwB,EACxB,uBAAuB,EACvB,oBAAoB,EACpB,0BAA0B,EAC1B,aAAa,EACb,kBAAkB,EAClB,eAAe,EAChB,MAAM,gBAAgB,CAAA;AACvB,OAAO,EACL,uBAAuB,EACvB,cAAc,EACd,2BAA2B,EAC3B,oBAAoB,EACrB,MAAM,iBAAiB,CAAA;AACxB,YAAY,EACV,4BAA4B,EAC5B,gBAAgB,EACjB,MAAM,iBAAiB,CAAA;AACxB,YAAY,EACV,mBAAmB,EACnB,uBAAuB,EACxB,MAAM,gBAAgB,CAAA;AAEvB,OAAO,EAAE,wBAAwB,EAAE,MAAM,kBAAkB,CAAA;AAE3D,OAAO,EACL,gBAAgB,EAChB,iBAAiB,EACjB,cAAc,EACf,MAAM,mBAAmB,CAAA;AAC1B,YAAY,EAAE,kBAAkB,EAAE,iBAAiB,EAAE,MAAM,mBAAmB,CAAA;AAE9E,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAA"}
|
package/dist/keys/index.js
CHANGED
|
@@ -16,6 +16,15 @@
|
|
|
16
16
|
* document).
|
|
17
17
|
* - `pukRosterDescriptorStore` -- that descriptor store, built from a bare
|
|
18
18
|
* signing client for the login-time direct read.
|
|
19
|
+
* - `rosterRecipientKid` -- the one builder of a client's roster kid, shared by
|
|
20
|
+
* the enrollment wrap, the roster read, and the rotation that retires it.
|
|
21
|
+
* - `convergePukRosterToDocument` -- the standing detector for a revocation
|
|
22
|
+
* cascade torn between the document edit and the roster rotation: a roster
|
|
23
|
+
* recipient the document no longer keys is rotated away from.
|
|
24
|
+
* - `readClientLabels` / `setClientLabel` / `removeClientLabel` /
|
|
25
|
+
* `wasClientLabelsStore` -- the enrolled-client display labels
|
|
26
|
+
* (`key-map/client-labels.json`), the record a "your wallets" surface names
|
|
27
|
+
* clients from, and the WAS-backed store they run through.
|
|
19
28
|
* - `rotatePukRoster` / `unwrapPukGenerations` / `rotateCollectionEpochsToPuk`
|
|
20
29
|
* / `cascadeCollectionsToPuk` / `pukAsRecipient` -- the PUK rotation
|
|
21
30
|
* cascade: the roster rotation off a revoked recipient, the per-collection
|
|
@@ -24,7 +33,9 @@
|
|
|
24
33
|
* names (also the completion sweep's driver).
|
|
25
34
|
*/
|
|
26
35
|
export { mintPuk, pukVaultKeys } from './puk.js';
|
|
27
|
-
export { addPukRosterRecipient, ensurePukRoster, PukRosterContinuityError, PukRosterIntegrityError, PukRosterUnwrapError, pukRosterRecipientResolver, readPukRoster, rotatePukRoster } from './pukRoster.js';
|
|
36
|
+
export { addPukRosterRecipient, convergePukRosterToDocument, ensurePukRoster, PukRosterContinuityError, PukRosterIntegrityError, PukRosterUnwrapError, pukRosterRecipientResolver, readPukRoster, rosterRecipientKid, rotatePukRoster } from './pukRoster.js';
|
|
28
37
|
export { cascadeCollectionsToPuk, pukAsRecipient, rotateCollectionEpochsToPuk, unwrapPukGenerations } from './pukCascade.js';
|
|
29
38
|
export { pukRosterDescriptorStore } from './rosterStore.js';
|
|
39
|
+
export { readClientLabels, removeClientLabel, setClientLabel } from './clientLabels.js';
|
|
40
|
+
export { wasClientLabelsStore } from './wasLabelsStore.js';
|
|
30
41
|
//# sourceMappingURL=index.js.map
|
package/dist/keys/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/keys/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/keys/index.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AACH,OAAO,EAAE,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAA;AAGhD,OAAO,EACL,qBAAqB,EACrB,2BAA2B,EAC3B,eAAe,EACf,wBAAwB,EACxB,uBAAuB,EACvB,oBAAoB,EACpB,0BAA0B,EAC1B,aAAa,EACb,kBAAkB,EAClB,eAAe,EAChB,MAAM,gBAAgB,CAAA;AACvB,OAAO,EACL,uBAAuB,EACvB,cAAc,EACd,2BAA2B,EAC3B,oBAAoB,EACrB,MAAM,iBAAiB,CAAA;AAUxB,OAAO,EAAE,wBAAwB,EAAE,MAAM,kBAAkB,CAAA;AAE3D,OAAO,EACL,gBAAgB,EAChB,iBAAiB,EACjB,cAAc,EACf,MAAM,mBAAmB,CAAA;AAG1B,OAAO,EAAE,oBAAoB,EAAE,MAAM,qBAAqB,CAAA"}
|
package/dist/keys/pukRoster.d.ts
CHANGED
|
@@ -89,6 +89,24 @@ export interface RosterRecipientDocument {
|
|
|
89
89
|
publicKeyMultibase?: string;
|
|
90
90
|
}>;
|
|
91
91
|
}
|
|
92
|
+
/**
|
|
93
|
+
* A wallet client's roster kid: its key-agreement key's id exactly as
|
|
94
|
+
* `agentsFromSeed` derives it at the client's own logins
|
|
95
|
+
* (`did:key:<ed-multibase>#<x-multibase>`). One builder for the whole
|
|
96
|
+
* lifecycle -- the wrap the enrollment ceremony mints, the entry a roster read
|
|
97
|
+
* looks for, and the recipient a rotation retires are the same string by
|
|
98
|
+
* construction rather than by three copies agreeing.
|
|
99
|
+
*
|
|
100
|
+
* @param options {object}
|
|
101
|
+
* @param options.signingKeyMultibase {string} the client's Ed25519 signing
|
|
102
|
+
* key
|
|
103
|
+
* @param options.keyAgreementKeyMultibase {string} its X25519 twin
|
|
104
|
+
* @returns {string}
|
|
105
|
+
*/
|
|
106
|
+
export declare function rosterRecipientKid({ signingKeyMultibase, keyAgreementKeyMultibase }: {
|
|
107
|
+
signingKeyMultibase: string;
|
|
108
|
+
keyAgreementKeyMultibase: string;
|
|
109
|
+
}): string;
|
|
92
110
|
/**
|
|
93
111
|
* Builds the recipient resolver for roster rotations, backed by a locally
|
|
94
112
|
* verified did:webvh document -- the enforcement point for "the roster
|
|
@@ -185,6 +203,53 @@ export declare function rotatePukRoster({ store, document, retireRecipientId }:
|
|
|
185
203
|
document: RosterRecipientDocument;
|
|
186
204
|
retireRecipientId: string;
|
|
187
205
|
}): Promise<CollectionEncryption>;
|
|
206
|
+
/**
|
|
207
|
+
* Converges the roster onto the account document: the standing detector for a
|
|
208
|
+
* revocation cascade torn between its two halves. The cascade edits the
|
|
209
|
+
* document first and rotates the roster second, so a client that crashes in
|
|
210
|
+
* between leaves a roster that keeps wrapping the CURRENT per-user key to a
|
|
211
|
+
* recipient the document no longer keys -- durable, silent, and permanent,
|
|
212
|
+
* since the revoked client's document edit will never be re-run.
|
|
213
|
+
*
|
|
214
|
+
* The detection is pure durable state: a current-epoch recipient the
|
|
215
|
+
* document-backed resolver cannot answer for is exactly a recipient the
|
|
216
|
+
* document no longer keys, so a healthy account reads the descriptor and
|
|
217
|
+
* writes nothing. When any such recipient is found the roster is rotated away
|
|
218
|
+
* from ALL of them at once -- a single {@link rotatePukRoster} suffices,
|
|
219
|
+
* because the resolver drops every unbacked entry from the fresh epoch, not
|
|
220
|
+
* just the one named as retiring.
|
|
221
|
+
*
|
|
222
|
+
* Rotating onto nobody is refused: a current epoch in which NO recipient is
|
|
223
|
+
* backed by the document is a mismatched pair (a stale document, the wrong
|
|
224
|
+
* account), not a cascade to finish, and completing it would lock every
|
|
225
|
+
* client out of the account.
|
|
226
|
+
*
|
|
227
|
+
* The fresh per-user key itself is not returned: the caller adopts it the
|
|
228
|
+
* ordinary way, by re-reading the roster ({@link readPukRoster}) once
|
|
229
|
+
* `rotated` says there is something to adopt, and then runs the collection
|
|
230
|
+
* fan-out.
|
|
231
|
+
*
|
|
232
|
+
* @param options {object}
|
|
233
|
+
* @param options.store {EncryptionDescriptorStore} the roster's descriptor
|
|
234
|
+
* store
|
|
235
|
+
* @param options.document {RosterRecipientDocument} the locally verified
|
|
236
|
+
* did:webvh document -- the recipient source of record
|
|
237
|
+
* @param [options.descriptor] {CollectionEncryption} a descriptor the caller
|
|
238
|
+
* has just read (a login-time roster read), to save a re-read; omitted, the
|
|
239
|
+
* roster is read fresh
|
|
240
|
+
* @returns {Promise<object>} whether the roster rotated on this call, the
|
|
241
|
+
* stale recipient kids found, and the roster descriptor as it now stands
|
|
242
|
+
* (`null` when the account has no roster yet)
|
|
243
|
+
*/
|
|
244
|
+
export declare function convergePukRosterToDocument({ store, document, descriptor }: {
|
|
245
|
+
store: EncryptionDescriptorStore;
|
|
246
|
+
document: RosterRecipientDocument;
|
|
247
|
+
descriptor?: CollectionEncryption;
|
|
248
|
+
}): Promise<{
|
|
249
|
+
rotated: boolean;
|
|
250
|
+
staleRecipientIds: string[];
|
|
251
|
+
descriptor: CollectionEncryption | null;
|
|
252
|
+
}>;
|
|
188
253
|
/**
|
|
189
254
|
* What a roster read resolves to: the authenticated descriptor, the current
|
|
190
255
|
* PUK (the cached one confirmed current, or a fresh one unwrapped from a
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"pukRoster.d.ts","sourceRoot":"","sources":["../../src/keys/pukRoster.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"pukRoster.d.ts","sourceRoot":"","sources":["../../src/keys/pukRoster.ts"],"names":[],"mappings":"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"}
|