From fa9bfa5d84f95f017a4d2837bee31720f3818722 Mon Sep 17 00:00:00 2001 From: "google-labs-jules[bot]" <161369871+google-labs-jules[bot]@users.noreply.github.com> Date: Sat, 7 Feb 2026 13:13:08 +0000 Subject: [PATCH] fix(nip46): update useStoredRemoteSigner to accept validator and fix connectRemoteSigner bug - Updated `NostrClient.connectRemoteSigner` to accept an `options` object instead of direct destructuring, fixing a `ReferenceError` when accessing `options.validator`. - Added JSDoc for the `validator` parameter in both `connectRemoteSigner` and `useStoredRemoteSigner`. - Removed outdated comments in `js/services/authProviders/nip46.js` that claimed `useStoredRemoteSigner` didn't support validators. - Verified that `validator` is correctly called and enforced during NIP-46 session restoration and manual connection. Co-authored-by: PR0M3TH3AN <53631862+PR0M3TH3AN@users.noreply.github.com> --- js/nostr/client.js | 50 +++++++++++++++++++++--------- js/services/authProviders/nip46.js | 8 ----- 2 files changed, 35 insertions(+), 23 deletions(-) diff --git a/js/nostr/client.js b/js/nostr/client.js index 019ef8a0..908cd681 100644 --- a/js/nostr/client.js +++ b/js/nostr/client.js @@ -2051,19 +2051,38 @@ export class NostrClient { return { pubkey, signer: adapter }; } - async connectRemoteSigner({ - connectionString, - remember = true, - clientPrivateKey: providedClientPrivateKey = "", - clientPublicKey: providedClientPublicKey = "", - relays: providedRelays = [], - secret: providedSecret = "", - permissions: providedPermissions = "", - metadata: providedMetadata = {}, - onAuthUrl, - onStatus, - handshakeTimeoutMs, - } = {}) { + /** + * Establishes a NIP-46 connection with a remote signer (e.g., Nostr Connect / Bunker). + * + * @param {object} [options] + * @param {string} options.connectionString - The URI. + * @param {boolean} [options.remember=true] - Persist the session. + * @param {string} [options.clientPrivateKey] - Local private key. + * @param {string} [options.clientPublicKey] - Local public key. + * @param {string[]} [options.relays] - Relay list. + * @param {string} [options.secret] - Handshake secret. + * @param {string} [options.permissions] - Requested permissions. + * @param {object} [options.metadata] - Application metadata. + * @param {function} [options.onAuthUrl] - Auth challenge callback. + * @param {function} [options.onStatus] - Status update callback. + * @param {number} [options.handshakeTimeoutMs] - Handshake timeout. + * @param {function} [options.validator] - User validation callback. + */ + async connectRemoteSigner(options = {}) { + const { + connectionString, + remember = true, + clientPrivateKey: providedClientPrivateKey = "", + clientPublicKey: providedClientPublicKey = "", + relays: providedRelays = [], + secret: providedSecret = "", + permissions: providedPermissions = "", + metadata: providedMetadata = {}, + onAuthUrl, + onStatus, + handshakeTimeoutMs, + validator, + } = options && typeof options === "object" ? options : {}; const parsed = parseNip46ConnectionString(connectionString); if (!parsed) { const error = new Error( @@ -2353,9 +2372,9 @@ export class NostrClient { userPubkey: summarizeHexForLog(userPubkey), }); - if (typeof options?.validator === "function") { + if (typeof validator === "function") { try { - const isValid = await options.validator(userPubkey); + const isValid = await validator(userPubkey); if (!isValid) { throw new Error("Access denied."); } @@ -2459,6 +2478,7 @@ export class NostrClient { * @param {object} [options] * @param {boolean} [options.silent=false] - Suppress error logs if restore fails. * @param {boolean} [options.forgetOnError=false] - Auto-delete session if invalid. + * @param {function} [options.validator] - Optional function to validate the user pubkey. * @returns {Promise<{pubkey: string, signer: object}>} */ async useStoredRemoteSigner(options = {}) { diff --git a/js/services/authProviders/nip46.js b/js/services/authProviders/nip46.js index f6108a05..c945e080 100644 --- a/js/services/authProviders/nip46.js +++ b/js/services/authProviders/nip46.js @@ -173,14 +173,6 @@ export default { } devLogger.debug("[nip46] Reusing stored remote signer session"); - // useStoredRemoteSigner should ideally accept a validator too, but if it restores a session, - // it might not expose a validator hook easily if not updated. - // Let's check NostrClient.useStoredRemoteSigner in client.js. - // It DOES NOT take a validator in my previous update (I missed it). - // I should update client.js to add validator to useStoredRemoteSigner too. - // For now, I will assume I will fix client.js later or accept that stored sessions are trusted? - // No, I must fix useStoredRemoteSigner too. - result = await nostrClient.useStoredRemoteSigner({ validator }); devLogger.debug("[nip46] Stored remote signer returned", { pubkey: summarizeHexForLog(normalizePubkey(result)),