@unicitylabs/sphere-sdk 0.5.3 → 0.5.5
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 +2 -0
- package/dist/connect/index.cjs +145 -23
- package/dist/connect/index.cjs.map +1 -1
- package/dist/connect/index.d.cts +15 -2
- package/dist/connect/index.d.ts +15 -2
- package/dist/connect/index.js +145 -23
- package/dist/connect/index.js.map +1 -1
- package/dist/core/index.cjs +670 -473
- package/dist/core/index.cjs.map +1 -1
- package/dist/core/index.d.cts +123 -2
- package/dist/core/index.d.ts +123 -2
- package/dist/core/index.js +667 -473
- package/dist/core/index.js.map +1 -1
- package/dist/impl/browser/connect/index.cjs +119 -1
- package/dist/impl/browser/connect/index.cjs.map +1 -1
- package/dist/impl/browser/connect/index.d.cts +53 -1
- package/dist/impl/browser/connect/index.d.ts +53 -1
- package/dist/impl/browser/connect/index.js +119 -1
- package/dist/impl/browser/connect/index.js.map +1 -1
- package/dist/impl/browser/index.cjs +306 -193
- package/dist/impl/browser/index.cjs.map +1 -1
- package/dist/impl/browser/index.js +306 -193
- package/dist/impl/browser/index.js.map +1 -1
- package/dist/impl/browser/ipfs.cjs +134 -19
- package/dist/impl/browser/ipfs.cjs.map +1 -1
- package/dist/impl/browser/ipfs.js +134 -19
- package/dist/impl/browser/ipfs.js.map +1 -1
- package/dist/impl/nodejs/connect/index.cjs +101 -6
- package/dist/impl/nodejs/connect/index.cjs.map +1 -1
- package/dist/impl/nodejs/connect/index.d.cts +2 -0
- package/dist/impl/nodejs/connect/index.d.ts +2 -0
- package/dist/impl/nodejs/connect/index.js +101 -6
- package/dist/impl/nodejs/connect/index.js.map +1 -1
- package/dist/impl/nodejs/index.cjs +267 -152
- package/dist/impl/nodejs/index.cjs.map +1 -1
- package/dist/impl/nodejs/index.d.cts +2 -1
- package/dist/impl/nodejs/index.d.ts +2 -1
- package/dist/impl/nodejs/index.js +267 -152
- package/dist/impl/nodejs/index.js.map +1 -1
- package/dist/index.cjs +682 -493
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +124 -8
- package/dist/index.d.ts +124 -8
- package/dist/index.js +680 -493
- package/dist/index.js.map +1 -1
- package/dist/l1/index.cjs +139 -32
- package/dist/l1/index.cjs.map +1 -1
- package/dist/l1/index.js +139 -32
- package/dist/l1/index.js.map +1 -1
- package/package.json +1 -16
package/dist/connect/index.js
CHANGED
|
@@ -1,3 +1,107 @@
|
|
|
1
|
+
// core/logger.ts
|
|
2
|
+
var LOGGER_KEY = "__sphere_sdk_logger__";
|
|
3
|
+
function getState() {
|
|
4
|
+
const g = globalThis;
|
|
5
|
+
if (!g[LOGGER_KEY]) {
|
|
6
|
+
g[LOGGER_KEY] = { debug: false, tags: {}, handler: null };
|
|
7
|
+
}
|
|
8
|
+
return g[LOGGER_KEY];
|
|
9
|
+
}
|
|
10
|
+
function isEnabled(tag) {
|
|
11
|
+
const state = getState();
|
|
12
|
+
if (tag in state.tags) return state.tags[tag];
|
|
13
|
+
return state.debug;
|
|
14
|
+
}
|
|
15
|
+
var logger = {
|
|
16
|
+
/**
|
|
17
|
+
* Configure the logger. Can be called multiple times (last write wins).
|
|
18
|
+
* Typically called by createBrowserProviders(), createNodeProviders(), or Sphere.init().
|
|
19
|
+
*/
|
|
20
|
+
configure(config) {
|
|
21
|
+
const state = getState();
|
|
22
|
+
if (config.debug !== void 0) state.debug = config.debug;
|
|
23
|
+
if (config.handler !== void 0) state.handler = config.handler;
|
|
24
|
+
},
|
|
25
|
+
/**
|
|
26
|
+
* Enable/disable debug logging for a specific tag.
|
|
27
|
+
* Per-tag setting overrides the global debug flag.
|
|
28
|
+
*
|
|
29
|
+
* @example
|
|
30
|
+
* ```ts
|
|
31
|
+
* logger.setTagDebug('Nostr', true); // enable only Nostr logs
|
|
32
|
+
* logger.setTagDebug('Nostr', false); // disable Nostr logs even if global debug=true
|
|
33
|
+
* ```
|
|
34
|
+
*/
|
|
35
|
+
setTagDebug(tag, enabled) {
|
|
36
|
+
getState().tags[tag] = enabled;
|
|
37
|
+
},
|
|
38
|
+
/**
|
|
39
|
+
* Clear per-tag override, falling back to global debug flag.
|
|
40
|
+
*/
|
|
41
|
+
clearTagDebug(tag) {
|
|
42
|
+
delete getState().tags[tag];
|
|
43
|
+
},
|
|
44
|
+
/** Returns true if debug mode is enabled for the given tag (or globally). */
|
|
45
|
+
isDebugEnabled(tag) {
|
|
46
|
+
if (tag) return isEnabled(tag);
|
|
47
|
+
return getState().debug;
|
|
48
|
+
},
|
|
49
|
+
/**
|
|
50
|
+
* Debug-level log. Only shown when debug is enabled (globally or for this tag).
|
|
51
|
+
* Use for detailed operational information.
|
|
52
|
+
*/
|
|
53
|
+
debug(tag, message, ...args) {
|
|
54
|
+
if (!isEnabled(tag)) return;
|
|
55
|
+
const state = getState();
|
|
56
|
+
if (state.handler) {
|
|
57
|
+
state.handler("debug", tag, message, ...args);
|
|
58
|
+
} else {
|
|
59
|
+
console.log(`[${tag}]`, message, ...args);
|
|
60
|
+
}
|
|
61
|
+
},
|
|
62
|
+
/**
|
|
63
|
+
* Warning-level log. ALWAYS shown regardless of debug flag.
|
|
64
|
+
* Use for important but non-critical issues (timeouts, retries, degraded state).
|
|
65
|
+
*/
|
|
66
|
+
warn(tag, message, ...args) {
|
|
67
|
+
const state = getState();
|
|
68
|
+
if (state.handler) {
|
|
69
|
+
state.handler("warn", tag, message, ...args);
|
|
70
|
+
} else {
|
|
71
|
+
console.warn(`[${tag}]`, message, ...args);
|
|
72
|
+
}
|
|
73
|
+
},
|
|
74
|
+
/**
|
|
75
|
+
* Error-level log. ALWAYS shown regardless of debug flag.
|
|
76
|
+
* Use for critical failures that should never be silenced.
|
|
77
|
+
*/
|
|
78
|
+
error(tag, message, ...args) {
|
|
79
|
+
const state = getState();
|
|
80
|
+
if (state.handler) {
|
|
81
|
+
state.handler("error", tag, message, ...args);
|
|
82
|
+
} else {
|
|
83
|
+
console.error(`[${tag}]`, message, ...args);
|
|
84
|
+
}
|
|
85
|
+
},
|
|
86
|
+
/** Reset all logger state (debug flag, tags, handler). Primarily for tests. */
|
|
87
|
+
reset() {
|
|
88
|
+
const g = globalThis;
|
|
89
|
+
delete g[LOGGER_KEY];
|
|
90
|
+
}
|
|
91
|
+
};
|
|
92
|
+
|
|
93
|
+
// core/errors.ts
|
|
94
|
+
var SphereError = class extends Error {
|
|
95
|
+
code;
|
|
96
|
+
cause;
|
|
97
|
+
constructor(message, code, cause) {
|
|
98
|
+
super(message);
|
|
99
|
+
this.name = "SphereError";
|
|
100
|
+
this.code = code;
|
|
101
|
+
this.cause = cause;
|
|
102
|
+
}
|
|
103
|
+
};
|
|
104
|
+
|
|
1
105
|
// constants.ts
|
|
2
106
|
var STORAGE_KEYS_GLOBAL = {
|
|
3
107
|
/** Encrypted BIP39 mnemonic */
|
|
@@ -262,7 +366,7 @@ var ConnectHost = class {
|
|
|
262
366
|
return;
|
|
263
367
|
}
|
|
264
368
|
} catch (error) {
|
|
265
|
-
|
|
369
|
+
logger.warn("ConnectHost", "Error handling message:", error);
|
|
266
370
|
}
|
|
267
371
|
}
|
|
268
372
|
// ===========================================================================
|
|
@@ -274,10 +378,16 @@ var ConnectHost = class {
|
|
|
274
378
|
this.sendHandshakeResponse([], void 0, void 0);
|
|
275
379
|
return;
|
|
276
380
|
}
|
|
381
|
+
if (msg.sessionId && this.session?.active && this.session.id === msg.sessionId) {
|
|
382
|
+
const identity2 = this.getPublicIdentity();
|
|
383
|
+
this.sendHandshakeResponse([...this.grantedPermissions], this.session.id, identity2);
|
|
384
|
+
return;
|
|
385
|
+
}
|
|
277
386
|
const requestedPermissions = msg.permissions;
|
|
278
387
|
const { approved, grantedPermissions } = await this.config.onConnectionRequest(
|
|
279
388
|
dapp,
|
|
280
|
-
requestedPermissions
|
|
389
|
+
requestedPermissions,
|
|
390
|
+
msg.silent
|
|
281
391
|
);
|
|
282
392
|
if (!approved) {
|
|
283
393
|
this.sendHandshakeResponse([], void 0, void 0);
|
|
@@ -327,8 +437,12 @@ var ConnectHost = class {
|
|
|
327
437
|
return;
|
|
328
438
|
}
|
|
329
439
|
if (msg.method === RPC_METHODS.DISCONNECT) {
|
|
440
|
+
const disconnectedSession = this.session;
|
|
330
441
|
this.revokeSession();
|
|
331
442
|
this.sendResult(msg.id, { disconnected: true });
|
|
443
|
+
if (disconnectedSession && this.config.onDisconnect) {
|
|
444
|
+
Promise.resolve(this.config.onDisconnect(disconnectedSession)).catch((err) => logger.warn("Connect", "onDisconnect handler error", err));
|
|
445
|
+
}
|
|
332
446
|
return;
|
|
333
447
|
}
|
|
334
448
|
if (!hasMethodPermission(this.grantedPermissions, msg.method)) {
|
|
@@ -399,17 +513,17 @@ var ConnectHost = class {
|
|
|
399
513
|
return this.sphere.payments.getHistory();
|
|
400
514
|
case RPC_METHODS.L1_GET_BALANCE:
|
|
401
515
|
if (!this.sphere.payments.l1) {
|
|
402
|
-
throw new
|
|
516
|
+
throw new SphereError("L1 module not available", "MODULE_NOT_AVAILABLE");
|
|
403
517
|
}
|
|
404
518
|
return this.sphere.payments.l1.getBalance();
|
|
405
519
|
case RPC_METHODS.L1_GET_HISTORY:
|
|
406
520
|
if (!this.sphere.payments.l1) {
|
|
407
|
-
throw new
|
|
521
|
+
throw new SphereError("L1 module not available", "MODULE_NOT_AVAILABLE");
|
|
408
522
|
}
|
|
409
523
|
return this.sphere.payments.l1.getHistory(params.limit);
|
|
410
524
|
case RPC_METHODS.RESOLVE:
|
|
411
525
|
if (!params.identifier) {
|
|
412
|
-
throw new
|
|
526
|
+
throw new SphereError("Missing required parameter: identifier", "VALIDATION_ERROR");
|
|
413
527
|
}
|
|
414
528
|
return this.sphere.resolve(params.identifier);
|
|
415
529
|
case RPC_METHODS.SUBSCRIBE:
|
|
@@ -417,7 +531,7 @@ var ConnectHost = class {
|
|
|
417
531
|
case RPC_METHODS.UNSUBSCRIBE:
|
|
418
532
|
return this.handleUnsubscribe(params.event);
|
|
419
533
|
case RPC_METHODS.GET_CONVERSATIONS: {
|
|
420
|
-
if (!this.sphere.communications) throw new
|
|
534
|
+
if (!this.sphere.communications) throw new SphereError("Communications module not available", "MODULE_NOT_AVAILABLE");
|
|
421
535
|
const convos = this.sphere.communications.getConversations();
|
|
422
536
|
const result = [];
|
|
423
537
|
const needsResolve = [];
|
|
@@ -440,7 +554,10 @@ var ConnectHost = class {
|
|
|
440
554
|
if (needsResolve.length > 0) {
|
|
441
555
|
const resolved = await Promise.all(
|
|
442
556
|
needsResolve.map(
|
|
443
|
-
({ peerPubkey }) => this.sphere.communications.resolvePeerNametag(peerPubkey).catch(() =>
|
|
557
|
+
({ peerPubkey }) => this.sphere.communications.resolvePeerNametag(peerPubkey).catch((err) => {
|
|
558
|
+
logger.debug("Connect", "Peer nametag resolution failed", err);
|
|
559
|
+
return void 0;
|
|
560
|
+
})
|
|
444
561
|
)
|
|
445
562
|
);
|
|
446
563
|
for (let i = 0; i < needsResolve.length; i++) {
|
|
@@ -453,8 +570,8 @@ var ConnectHost = class {
|
|
|
453
570
|
return result;
|
|
454
571
|
}
|
|
455
572
|
case RPC_METHODS.GET_MESSAGES: {
|
|
456
|
-
if (!this.sphere.communications) throw new
|
|
457
|
-
if (!params.peerPubkey) throw new
|
|
573
|
+
if (!this.sphere.communications) throw new SphereError("Communications module not available", "MODULE_NOT_AVAILABLE");
|
|
574
|
+
if (!params.peerPubkey) throw new SphereError("Missing required parameter: peerPubkey", "VALIDATION_ERROR");
|
|
458
575
|
return this.sphere.communications.getConversationPage(
|
|
459
576
|
params.peerPubkey,
|
|
460
577
|
{
|
|
@@ -464,7 +581,7 @@ var ConnectHost = class {
|
|
|
464
581
|
);
|
|
465
582
|
}
|
|
466
583
|
case RPC_METHODS.GET_DM_UNREAD_COUNT: {
|
|
467
|
-
if (!this.sphere.communications) throw new
|
|
584
|
+
if (!this.sphere.communications) throw new SphereError("Communications module not available", "MODULE_NOT_AVAILABLE");
|
|
468
585
|
return {
|
|
469
586
|
unreadCount: this.sphere.communications.getUnreadCount(
|
|
470
587
|
params.peerPubkey
|
|
@@ -472,22 +589,22 @@ var ConnectHost = class {
|
|
|
472
589
|
};
|
|
473
590
|
}
|
|
474
591
|
case RPC_METHODS.MARK_AS_READ: {
|
|
475
|
-
if (!this.sphere.communications) throw new
|
|
592
|
+
if (!this.sphere.communications) throw new SphereError("Communications module not available", "MODULE_NOT_AVAILABLE");
|
|
476
593
|
if (!params.messageIds || !Array.isArray(params.messageIds)) {
|
|
477
|
-
throw new
|
|
594
|
+
throw new SphereError("Missing required parameter: messageIds (string[])", "VALIDATION_ERROR");
|
|
478
595
|
}
|
|
479
596
|
await this.sphere.communications.markAsRead(params.messageIds);
|
|
480
597
|
return { marked: true, count: params.messageIds.length };
|
|
481
598
|
}
|
|
482
599
|
default:
|
|
483
|
-
throw new
|
|
600
|
+
throw new SphereError(`Unknown method: ${method}`, "VALIDATION_ERROR");
|
|
484
601
|
}
|
|
485
602
|
}
|
|
486
603
|
// ===========================================================================
|
|
487
604
|
// Event Subscriptions
|
|
488
605
|
// ===========================================================================
|
|
489
606
|
handleSubscribe(eventName) {
|
|
490
|
-
if (!eventName) throw new
|
|
607
|
+
if (!eventName) throw new SphereError("Missing required parameter: event", "VALIDATION_ERROR");
|
|
491
608
|
if (this.eventSubscriptions.has(eventName)) {
|
|
492
609
|
return { subscribed: true, event: eventName };
|
|
493
610
|
}
|
|
@@ -504,7 +621,7 @@ var ConnectHost = class {
|
|
|
504
621
|
return { subscribed: true, event: eventName };
|
|
505
622
|
}
|
|
506
623
|
handleUnsubscribe(eventName) {
|
|
507
|
-
if (!eventName) throw new
|
|
624
|
+
if (!eventName) throw new SphereError("Missing required parameter: event", "VALIDATION_ERROR");
|
|
508
625
|
const unsub = this.eventSubscriptions.get(eventName);
|
|
509
626
|
if (unsub) {
|
|
510
627
|
unsub();
|
|
@@ -595,6 +712,8 @@ var ConnectClient = class {
|
|
|
595
712
|
requestedPermissions;
|
|
596
713
|
timeout;
|
|
597
714
|
intentTimeout;
|
|
715
|
+
resumeSessionId;
|
|
716
|
+
silent;
|
|
598
717
|
sessionId = null;
|
|
599
718
|
grantedPermissions = [];
|
|
600
719
|
identity = null;
|
|
@@ -610,6 +729,8 @@ var ConnectClient = class {
|
|
|
610
729
|
this.requestedPermissions = config.permissions ?? [...ALL_PERMISSIONS];
|
|
611
730
|
this.timeout = config.timeout ?? DEFAULT_TIMEOUT;
|
|
612
731
|
this.intentTimeout = config.intentTimeout ?? DEFAULT_INTENT_TIMEOUT;
|
|
732
|
+
this.resumeSessionId = config.resumeSessionId ?? null;
|
|
733
|
+
this.silent = config.silent ?? false;
|
|
613
734
|
}
|
|
614
735
|
// ===========================================================================
|
|
615
736
|
// Connection
|
|
@@ -629,7 +750,9 @@ var ConnectClient = class {
|
|
|
629
750
|
type: "handshake",
|
|
630
751
|
direction: "request",
|
|
631
752
|
permissions: this.requestedPermissions,
|
|
632
|
-
dapp: this.dapp
|
|
753
|
+
dapp: this.dapp,
|
|
754
|
+
...this.resumeSessionId ? { sessionId: this.resumeSessionId } : {},
|
|
755
|
+
...this.silent ? { silent: true } : {}
|
|
633
756
|
});
|
|
634
757
|
});
|
|
635
758
|
}
|
|
@@ -664,7 +787,7 @@ var ConnectClient = class {
|
|
|
664
787
|
// ===========================================================================
|
|
665
788
|
/** Send a query request and return the result */
|
|
666
789
|
async query(method, params) {
|
|
667
|
-
if (!this.connected) throw new
|
|
790
|
+
if (!this.connected) throw new SphereError("Not connected", "NOT_INITIALIZED");
|
|
668
791
|
const id = createRequestId();
|
|
669
792
|
return new Promise((resolve, reject) => {
|
|
670
793
|
const timer = setTimeout(() => {
|
|
@@ -691,7 +814,7 @@ var ConnectClient = class {
|
|
|
691
814
|
// ===========================================================================
|
|
692
815
|
/** Send an intent request. The wallet will open its UI for user confirmation. */
|
|
693
816
|
async intent(action, params) {
|
|
694
|
-
if (!this.connected) throw new
|
|
817
|
+
if (!this.connected) throw new SphereError("Not connected", "NOT_INITIALIZED");
|
|
695
818
|
const id = createRequestId();
|
|
696
819
|
return new Promise((resolve, reject) => {
|
|
697
820
|
const timer = setTimeout(() => {
|
|
@@ -721,8 +844,7 @@ var ConnectClient = class {
|
|
|
721
844
|
if (!this.eventHandlers.has(event)) {
|
|
722
845
|
this.eventHandlers.set(event, /* @__PURE__ */ new Set());
|
|
723
846
|
if (this.connected) {
|
|
724
|
-
this.query(RPC_METHODS.SUBSCRIBE, { event }).catch(() =>
|
|
725
|
-
});
|
|
847
|
+
this.query(RPC_METHODS.SUBSCRIBE, { event }).catch((err) => logger.debug("Connect", "Event subscription failed", err));
|
|
726
848
|
}
|
|
727
849
|
}
|
|
728
850
|
this.eventHandlers.get(event).add(handler);
|
|
@@ -733,8 +855,7 @@ var ConnectClient = class {
|
|
|
733
855
|
if (handlers.size === 0) {
|
|
734
856
|
this.eventHandlers.delete(event);
|
|
735
857
|
if (this.connected) {
|
|
736
|
-
this.query(RPC_METHODS.UNSUBSCRIBE, { event }).catch(() =>
|
|
737
|
-
});
|
|
858
|
+
this.query(RPC_METHODS.UNSUBSCRIBE, { event }).catch((err) => logger.debug("Connect", "Event unsubscription failed", err));
|
|
738
859
|
}
|
|
739
860
|
}
|
|
740
861
|
}
|
|
@@ -762,7 +883,8 @@ var ConnectClient = class {
|
|
|
762
883
|
for (const handler of handlers) {
|
|
763
884
|
try {
|
|
764
885
|
handler(msg.data);
|
|
765
|
-
} catch {
|
|
886
|
+
} catch (err) {
|
|
887
|
+
logger.debug("Connect", "Event handler error", err);
|
|
766
888
|
}
|
|
767
889
|
}
|
|
768
890
|
}
|