From 44dff1991f1ef4257c1d1283a531d48287ccbc9b Mon Sep 17 00:00:00 2001 From: Jeff Emmett Date: Wed, 11 Mar 2026 21:25:26 -0700 Subject: [PATCH] fix(rcart): recognize existing session without wallet + show username checkExistingSession() required a derived wallet address to set authenticated=true, causing a re-login prompt even with a valid session. Now authenticates on valid session and derives wallet lazily at payment generation time. Also extracts claims.username for display instead of showing raw did:key identifiers. Co-Authored-By: Claude Opus 4.6 --- .../rcart/components/folk-payment-request.ts | 66 +++++++++++++++---- 1 file changed, 53 insertions(+), 13 deletions(-) diff --git a/modules/rcart/components/folk-payment-request.ts b/modules/rcart/components/folk-payment-request.ts index f840148..f267de9 100644 --- a/modules/rcart/components/folk-payment-request.ts +++ b/modules/rcart/components/folk-payment-request.ts @@ -16,6 +16,7 @@ class FolkPaymentRequest extends HTMLElement { private authenticated = false; private walletAddress = ''; private did = ''; + private username = ''; private authError = ''; private authenticating = false; @@ -80,14 +81,18 @@ class FolkPaymentRequest extends HTMLElement { const hasSession = sm.isValid() || !!rstackSession; if (!hasSession) return; - // Get DID from either source - this.did = sm.getDID() || rstackSession?.claims?.did || rstackSession?.claims?.sub || ''; - - // Get wallet address from session claims + // Get identity from either source const smState = sm.getSession(); + this.did = sm.getDID() || rstackSession?.claims?.did || rstackSession?.claims?.sub || ''; + this.username = smState?.claims?.username || rstackSession?.claims?.username || ''; + + // Valid session = authenticated, regardless of wallet derivation + this.authenticated = true; + + // Try to get wallet address from session claims this.walletAddress = smState?.claims?.eid?.walletAddress || rstackSession?.claims?.eid?.walletAddress || ''; - // If session exists but no wallet address, try deriving from key manager + // If no wallet in claims, try deriving from key manager if (!this.walletAddress) { try { const { getKeyManager } = await import('../../../src/encryptid/key-derivation'); @@ -99,10 +104,7 @@ class FolkPaymentRequest extends HTMLElement { } catch { /* key manager not ready */ } } - if (this.walletAddress) { - this.authenticated = true; - this.render(); - } + this.render(); } catch { /* session module not available */ } } @@ -167,12 +169,37 @@ class FolkPaymentRequest extends HTMLElement { // ── Generate payment request ── private async generatePayment() { - if (!this.walletAddress || !this.description) return; + if (!this.description) return; if (!this.amountEditable && !this.amount) return; this.generating = true; + this.authError = ''; this.render(); + // Derive wallet on-demand if not yet available + if (!this.walletAddress) { + try { + const { getKeyManager } = await import('../../../src/encryptid/key-derivation'); + const km = getKeyManager(); + if (!km.isInitialized()) { + // Trigger passkey to initialize key manager + const identity = document.querySelector('rstack-identity') as any; + if (identity?.deriveKeys) await identity.deriveKeys(); + } + if (km.isInitialized()) { + const keys = await km.getKeys(); + if (keys.eoaAddress) this.walletAddress = keys.eoaAddress; + } + } catch { /* derivation failed */ } + + if (!this.walletAddress) { + this.authError = 'Could not derive wallet address. Please try signing in again.'; + this.generating = false; + this.render(); + return; + } + } + try { const { getSessionManager } = await import('../../../src/encryptid/session'); const { getSession: getRstackSession } = await import('../../../shared/components/rstack-identity'); @@ -283,13 +310,24 @@ class FolkPaymentRequest extends HTMLElement { `; } + private get displayName(): string { + return this.username || (this.did.length > 24 ? this.did.slice(0, 16) + '...' + this.did.slice(-6) : this.did); + } + private renderForm(): string { - return ` -
+ const walletBadge = this.walletAddress + ? `
Receiving wallet ${this.walletAddress.slice(0, 6)}...${this.walletAddress.slice(-4)} ${this.walletAddress} -
+
` + : `
+ Signed in as + ${this.esc(this.displayName)} + Wallet address not yet derived — it will be created when you generate a payment. +
`; + return ` + ${walletBadge}
@@ -539,6 +577,8 @@ class FolkPaymentRequest extends HTMLElement { .wallet-label { color: var(--rs-text-secondary); font-size: 0.75rem; font-weight: 600; text-transform: uppercase; letter-spacing: 0.05em; } .wallet-addr { color: var(--rs-text-primary); font-family: monospace; font-size: 0.9375rem; font-weight: 600; } .wallet-full { display: none; } + .wallet-badge--warn { flex-direction: column; align-items: flex-start; } + .wallet-hint { color: var(--rs-text-muted); font-size: 0.75rem; } .form { display: flex; flex-direction: column; gap: 1rem; } .field { display: flex; flex-direction: column; gap: 0.375rem; }