@calimero-network/mero-js 26.4.1 → 26.5.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/dist/account/index.d.ts +2 -2
- package/dist/account/index.js +1 -1
- package/dist/account/session.d.ts +34 -2
- package/dist/account/session.js +56 -14
- package/dist/index.browser.mjs +2 -2
- package/dist/index.browser.mjs.map +3 -3
- package/dist/index.cjs +45 -8
- package/dist/index.cjs.map +2 -2
- package/dist/index.d.ts +2 -2
- package/dist/index.js +1 -1
- package/dist/index.mjs +45 -8
- package/dist/index.mjs.map +2 -2
- package/package.json +1 -1
package/dist/account/index.d.ts
CHANGED
|
@@ -4,8 +4,8 @@ export { resolveRoot } from './account.js';
|
|
|
4
4
|
export type { RootSource } from './account.js';
|
|
5
5
|
export { resolveRootPair } from './account.js';
|
|
6
6
|
export type { ResolvedRoot } from './account.js';
|
|
7
|
-
export type { DelegatedCredential, DelegatedSession as DelegatedAccountSession, RelayMap, RelayNodeKeyAttempt } from './session.js';
|
|
8
|
-
export { readDelegatedSession, saveDelegatedSession, clearDelegatedSession, readDelegatedCredential, saveDelegatedCredential, clearDelegatedCredential, persistedNonces, markContextNonceSpent, pinRelayNodeKey, readPinnedRelayNodeKey, attemptRelayNodeKey, resolveRelayNodeKey, learnRelayNodeKey, RELAY_NODE_KEY_RETRY_MS, forgetMethodKinds, forgetRelaySealing, relayTransportFetch, buildDelegatedClient, readRelayMap, rememberRelay, relayForContext, carryExecutorAccount, knownRelays, listDelegatedContexts, listDelegatedNamespaces, } from './session.js';
|
|
7
|
+
export type { DelegatedCredential, DelegatedSession as DelegatedAccountSession, RelayMap, RelayNodeKeyAttempt, RelayListingFailure } from './session.js';
|
|
8
|
+
export { readDelegatedSession, saveDelegatedSession, clearDelegatedSession, readDelegatedCredential, saveDelegatedCredential, clearDelegatedCredential, persistedNonces, markContextNonceSpent, pinRelayNodeKey, readPinnedRelayNodeKey, attemptRelayNodeKey, resolveRelayNodeKey, learnRelayNodeKey, RELAY_NODE_KEY_RETRY_MS, forgetMethodKinds, forgetRelaySealing, relayTransportFetch, buildDelegatedClient, readRelayMap, rememberRelay, relayForContext, carryExecutorAccount, knownRelays, listDelegatedContexts, listDelegatedNamespaces, RelaysUnavailableError, } from './session.js';
|
|
9
9
|
export { resolveRelayFromInvitation, normaliseAccount } from './relay-from-invitation.js';
|
|
10
10
|
export type { RelayResolutionStep, RelayResolutionFailure, ResolvedInvitationRelay, ResolveRelayResult, ResolveRelayFromInvitationInput, } from './relay-from-invitation.js';
|
|
11
11
|
export { joinWithNode } from './join-with-node.js';
|
package/dist/account/index.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
export { generateAccountRoot, accountRootFromPhrase, accountRootFromSecret, createAccountRootSigner, accountRootSignerFromPhrase, signAccountLink, signAccountLogin, } from './account.js';
|
|
3
3
|
export { resolveRoot } from './account.js';
|
|
4
4
|
export { resolveRootPair } from './account.js';
|
|
5
|
-
export { readDelegatedSession, saveDelegatedSession, clearDelegatedSession, readDelegatedCredential, saveDelegatedCredential, clearDelegatedCredential, persistedNonces, markContextNonceSpent, pinRelayNodeKey, readPinnedRelayNodeKey, attemptRelayNodeKey, resolveRelayNodeKey, learnRelayNodeKey, RELAY_NODE_KEY_RETRY_MS, forgetMethodKinds, forgetRelaySealing, relayTransportFetch, buildDelegatedClient, readRelayMap, rememberRelay, relayForContext, carryExecutorAccount, knownRelays, listDelegatedContexts, listDelegatedNamespaces, } from './session.js';
|
|
5
|
+
export { readDelegatedSession, saveDelegatedSession, clearDelegatedSession, readDelegatedCredential, saveDelegatedCredential, clearDelegatedCredential, persistedNonces, markContextNonceSpent, pinRelayNodeKey, readPinnedRelayNodeKey, attemptRelayNodeKey, resolveRelayNodeKey, learnRelayNodeKey, RELAY_NODE_KEY_RETRY_MS, forgetMethodKinds, forgetRelaySealing, relayTransportFetch, buildDelegatedClient, readRelayMap, rememberRelay, relayForContext, carryExecutorAccount, knownRelays, listDelegatedContexts, listDelegatedNamespaces, RelaysUnavailableError, } from './session.js';
|
|
6
6
|
export { resolveRelayFromInvitation, normaliseAccount } from './relay-from-invitation.js';
|
|
7
7
|
export { joinWithNode } from './join-with-node.js';
|
|
8
8
|
export { bootstrapFromInvitation } from './bootstrap-from-invitation.js';
|
|
@@ -209,6 +209,36 @@ export declare function relayForContext(account: string, contextId: string): str
|
|
|
209
209
|
export declare function carryExecutorAccount(prev: DelegatedSession | null, next: DelegatedSession): DelegatedSession;
|
|
210
210
|
/** Every relay this account is known to use: the session's, and each in the map. */
|
|
211
211
|
export declare function knownRelays(s: DelegatedSession): string[];
|
|
212
|
+
/**
|
|
213
|
+
* Thrown by {@link listDelegatedContexts} and {@link listDelegatedNamespaces}
|
|
214
|
+
* when the account knows relays and **none** of them answered.
|
|
215
|
+
*
|
|
216
|
+
* One relay down is skipped, as before: the others still answer for what they
|
|
217
|
+
* serve. Every relay down is different. Returning `[]` then reads as "a member
|
|
218
|
+
* of nothing", and an app renders an empty account, with no error, for what is
|
|
219
|
+
* really "could not ask". A relay whose hostname no longer resolves (a node
|
|
220
|
+
* rebuilt or deleted in the cloud) did exactly that.
|
|
221
|
+
*/
|
|
222
|
+
/**
|
|
223
|
+
* Why one relay did not answer a listing.
|
|
224
|
+
*
|
|
225
|
+
* `refused`: its attestation did not verify (an untrusted image, a release
|
|
226
|
+
* below the floor). Asking again cannot change that, and it may be worth a
|
|
227
|
+
* closer look. `unavailable`: something on the way did not answer, or the
|
|
228
|
+
* relay refused the request itself; trying again later may.
|
|
229
|
+
*/
|
|
230
|
+
export interface RelayListingFailure {
|
|
231
|
+
relayUrl: string;
|
|
232
|
+
kind: 'refused' | 'unavailable';
|
|
233
|
+
error: unknown;
|
|
234
|
+
}
|
|
235
|
+
export declare class RelaysUnavailableError extends Error {
|
|
236
|
+
readonly failures: readonly RelayListingFailure[];
|
|
237
|
+
readonly relays: readonly string[];
|
|
238
|
+
constructor(failures: readonly RelayListingFailure[]);
|
|
239
|
+
/** Every relay refused its attestation: retrying will not help. */
|
|
240
|
+
get refused(): boolean;
|
|
241
|
+
}
|
|
212
242
|
type ListedContext = Awaited<ReturnType<MeroClient['admin']['getContexts']>>['contexts'][number];
|
|
213
243
|
/**
|
|
214
244
|
* This account's contexts on every relay it knows, each tagged with the relay
|
|
@@ -216,7 +246,8 @@ type ListedContext = Awaited<ReturnType<MeroClient['admin']['getContexts']>>['co
|
|
|
216
246
|
*
|
|
217
247
|
* Each relay answers only for itself and only for this caller, so the union is
|
|
218
248
|
* exactly the account's contexts across relays. A relay that cannot be reached
|
|
219
|
-
* or logged in to is skipped (its contexts simply do not appear), not fatal
|
|
249
|
+
* or logged in to is skipped (its contexts simply do not appear), not fatal,
|
|
250
|
+
* unless it is every relay: then {@link RelaysUnavailableError}.
|
|
220
251
|
*/
|
|
221
252
|
export declare function listDelegatedContexts(s: DelegatedSession): Promise<Array<ListedContext & {
|
|
222
253
|
relayUrl: string;
|
|
@@ -226,7 +257,8 @@ type ListedNamespace = Awaited<ReturnType<MeroClient['admin']['listNamespaces']>
|
|
|
226
257
|
* This account's namespaces on every relay it knows, each tagged with the relay
|
|
227
258
|
* that listed it and recorded as that namespace's relay. Same rules as
|
|
228
259
|
* {@link listDelegatedContexts}: each relay answers for itself and this caller
|
|
229
|
-
* only (`namespace:list-own`); an unreachable relay is skipped
|
|
260
|
+
* only (`namespace:list-own`); an unreachable relay is skipped, and every
|
|
261
|
+
* relay unreachable is {@link RelaysUnavailableError}.
|
|
230
262
|
*/
|
|
231
263
|
export declare function listDelegatedNamespaces(s: DelegatedSession): Promise<Array<ListedNamespace & {
|
|
232
264
|
relayUrl: string;
|
package/dist/account/session.js
CHANGED
|
@@ -804,24 +804,56 @@ export function knownRelays(s) {
|
|
|
804
804
|
.map(relayOrigin);
|
|
805
805
|
return [...new Set(all)];
|
|
806
806
|
}
|
|
807
|
+
export class RelaysUnavailableError extends Error {
|
|
808
|
+
constructor(failures) {
|
|
809
|
+
super(`none of this account's relays answered: ${failures.map((f) => `${f.relayUrl} (${f.kind})`).join(', ')}`);
|
|
810
|
+
this.failures = failures;
|
|
811
|
+
this.name = 'RelaysUnavailableError';
|
|
812
|
+
this.relays = failures.map((f) => f.relayUrl);
|
|
813
|
+
}
|
|
814
|
+
/** Every relay refused its attestation: retrying will not help. */
|
|
815
|
+
get refused() {
|
|
816
|
+
return this.failures.every((f) => f.kind === 'refused');
|
|
817
|
+
}
|
|
818
|
+
}
|
|
819
|
+
/**
|
|
820
|
+
* One relay's client for a listing, or the failure that stopped it. The key's
|
|
821
|
+
* own outcome is kept, so a refused attestation is not reported as a relay
|
|
822
|
+
* that merely did not answer.
|
|
823
|
+
*/
|
|
824
|
+
async function listingClient(s, relayUrl) {
|
|
825
|
+
const key = await attemptRelayNodeKey(relayUrl);
|
|
826
|
+
if (key.kind !== 'learned') {
|
|
827
|
+
console.warn('[mero-js] could not learn the relay node key from its attestation', key.error);
|
|
828
|
+
return { failure: { relayUrl, kind: key.kind, error: key.error } };
|
|
829
|
+
}
|
|
830
|
+
const client = buildDelegatedClient({ ...s, relayUrl }, null);
|
|
831
|
+
if (!client)
|
|
832
|
+
return { failure: { relayUrl, kind: 'unavailable', error: new Error(`no client for ${relayUrl}`) } };
|
|
833
|
+
return { client };
|
|
834
|
+
}
|
|
807
835
|
/**
|
|
808
836
|
* This account's contexts on every relay it knows, each tagged with the relay
|
|
809
837
|
* that listed it — and that relay recorded as the one serving it.
|
|
810
838
|
*
|
|
811
839
|
* Each relay answers only for itself and only for this caller, so the union is
|
|
812
840
|
* exactly the account's contexts across relays. A relay that cannot be reached
|
|
813
|
-
* or logged in to is skipped (its contexts simply do not appear), not fatal
|
|
841
|
+
* or logged in to is skipped (its contexts simply do not appear), not fatal,
|
|
842
|
+
* unless it is every relay: then {@link RelaysUnavailableError}.
|
|
814
843
|
*/
|
|
815
844
|
export async function listDelegatedContexts(s) {
|
|
816
845
|
const out = [];
|
|
817
846
|
const map = readRelayMap(s.account);
|
|
818
|
-
|
|
847
|
+
const relays = knownRelays(s);
|
|
848
|
+
const failures = [];
|
|
849
|
+
for (const relayUrl of relays) {
|
|
850
|
+
const got = await listingClient(s, relayUrl);
|
|
851
|
+
if ('failure' in got) {
|
|
852
|
+
failures.push(got.failure);
|
|
853
|
+
continue;
|
|
854
|
+
}
|
|
855
|
+
const { client } = got;
|
|
819
856
|
try {
|
|
820
|
-
if (!(await resolveRelayNodeKey(relayUrl)))
|
|
821
|
-
continue;
|
|
822
|
-
const client = buildDelegatedClient({ ...s, relayUrl }, null);
|
|
823
|
-
if (!client)
|
|
824
|
-
continue;
|
|
825
857
|
const { contexts } = await client.admin.getContexts();
|
|
826
858
|
for (const c of contexts ?? []) {
|
|
827
859
|
out.push({ ...c, relayUrl });
|
|
@@ -829,30 +861,37 @@ export async function listDelegatedContexts(s) {
|
|
|
829
861
|
}
|
|
830
862
|
}
|
|
831
863
|
catch (e) {
|
|
864
|
+
failures.push({ relayUrl, kind: 'unavailable', error: e });
|
|
832
865
|
console.warn(`[mero-js] could not list contexts on ${relayUrl}`, e);
|
|
833
866
|
}
|
|
834
867
|
}
|
|
835
868
|
writeRelayMap(s.account, map);
|
|
869
|
+
if (relays.length > 0 && failures.length === relays.length)
|
|
870
|
+
throw new RelaysUnavailableError(failures);
|
|
836
871
|
return out;
|
|
837
872
|
}
|
|
838
873
|
/**
|
|
839
874
|
* This account's namespaces on every relay it knows, each tagged with the relay
|
|
840
875
|
* that listed it and recorded as that namespace's relay. Same rules as
|
|
841
876
|
* {@link listDelegatedContexts}: each relay answers for itself and this caller
|
|
842
|
-
* only (`namespace:list-own`); an unreachable relay is skipped
|
|
877
|
+
* only (`namespace:list-own`); an unreachable relay is skipped, and every
|
|
878
|
+
* relay unreachable is {@link RelaysUnavailableError}.
|
|
843
879
|
*/
|
|
844
880
|
export async function listDelegatedNamespaces(s) {
|
|
845
881
|
var _a, _b;
|
|
846
882
|
const out = [];
|
|
847
883
|
const seen = new Set();
|
|
848
884
|
const map = readRelayMap(s.account);
|
|
849
|
-
|
|
885
|
+
const relays = knownRelays(s);
|
|
886
|
+
const failures = [];
|
|
887
|
+
for (const relayUrl of relays) {
|
|
888
|
+
const got = await listingClient(s, relayUrl);
|
|
889
|
+
if ('failure' in got) {
|
|
890
|
+
failures.push(got.failure);
|
|
891
|
+
continue;
|
|
892
|
+
}
|
|
893
|
+
const { client } = got;
|
|
850
894
|
try {
|
|
851
|
-
if (!(await resolveRelayNodeKey(relayUrl)))
|
|
852
|
-
continue;
|
|
853
|
-
const client = buildDelegatedClient({ ...s, relayUrl }, null);
|
|
854
|
-
if (!client)
|
|
855
|
-
continue;
|
|
856
895
|
for (const ns of await client.admin.listNamespaces()) {
|
|
857
896
|
if (seen.has(ns.namespaceId))
|
|
858
897
|
continue;
|
|
@@ -862,9 +901,12 @@ export async function listDelegatedNamespaces(s) {
|
|
|
862
901
|
}
|
|
863
902
|
}
|
|
864
903
|
catch (e) {
|
|
904
|
+
failures.push({ relayUrl, kind: 'unavailable', error: e });
|
|
865
905
|
console.warn(`[mero-js] could not list namespaces on ${relayUrl}`, e);
|
|
866
906
|
}
|
|
867
907
|
}
|
|
868
908
|
writeRelayMap(s.account, map);
|
|
909
|
+
if (relays.length > 0 && failures.length === relays.length)
|
|
910
|
+
throw new RelaysUnavailableError(failures);
|
|
869
911
|
return out;
|
|
870
912
|
}
|