fix(rcart): use rstack-identity auth instead of separate passkey flow

folk-payment-request now triggers the rstack-identity auth modal
instead of its own passkey flow. This ensures the username displays
correctly in the identity badge and avoids duplicate session management.
Also checks both session sources for wallet address and access token.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Jeff Emmett 2026-03-11 20:21:18 -07:00
parent 841a5ff2b6
commit 911713e9aa
1 changed files with 42 additions and 60 deletions

View File

@ -71,75 +71,56 @@ class FolkPaymentRequest extends HTMLElement {
private async checkExistingSession() { private async checkExistingSession() {
try { try {
// Check both session managers (SessionManager + rstack-identity)
const { getSessionManager } = await import('../../../src/encryptid/session'); const { getSessionManager } = await import('../../../src/encryptid/session');
const session = getSessionManager(); const sm = getSessionManager();
if (session.isValid()) { const { getSession } = await import('../../../shared/components/rstack-identity');
this.did = session.getDID() || ''; const rstackSession = getSession();
const state = session.getSession();
this.walletAddress = state?.claims?.eid?.walletAddress || '';
// If session exists but no wallet address, try deriving from key manager const hasSession = sm.isValid() || !!rstackSession;
if (!this.walletAddress) { if (!hasSession) return;
try {
const { getKeyManager } = await import('../../../src/encryptid/key-derivation');
const km = getKeyManager();
if (km.isInitialized()) {
const keys = await km.getKeys();
if (keys.eoaAddress) this.walletAddress = keys.eoaAddress;
}
} catch { /* key manager not ready */ }
}
if (this.walletAddress) { // Get DID from either source
this.authenticated = true; this.did = sm.getDID() || rstackSession?.claims?.did || rstackSession?.claims?.sub || '';
this.render();
} // Get wallet address from session claims
const smState = sm.getSession();
this.walletAddress = smState?.claims?.eid?.walletAddress || rstackSession?.claims?.eid?.walletAddress || '';
// If session exists but no wallet address, try deriving from key manager
if (!this.walletAddress) {
try {
const { getKeyManager } = await import('../../../src/encryptid/key-derivation');
const km = getKeyManager();
if (km.isInitialized()) {
const keys = await km.getKeys();
if (keys.eoaAddress) this.walletAddress = keys.eoaAddress;
}
} catch { /* key manager not ready */ }
}
if (this.walletAddress) {
this.authenticated = true;
this.render();
}
} }
} catch { /* session module not available */ } } catch { /* session module not available */ }
} }
private async authenticate() { private async authenticate() {
this.authenticating = true; // Trigger the rstack-identity auth modal instead of a separate passkey flow
this.authError = ''; const identity = document.querySelector('rstack-identity') as any;
this.render(); if (identity?.showAuthModal) {
identity.showAuthModal({
try { onSuccess: () => {
const { authenticatePasskey } = await import('../../../src/encryptid/webauthn'); // Re-check session after auth completes
const { deriveEOAFromPRF } = await import('../../../src/encryptid/eoa-derivation'); this.checkExistingSession();
const { getSessionManager } = await import('../../../src/encryptid/session'); },
const { EncryptIDKeyManager } = await import('../../../src/encryptid/key-derivation');
const result = await authenticatePasskey();
if (!result.prfOutput) {
throw new Error('Your passkey does not support PRF — wallet address cannot be derived');
}
const eoa = deriveEOAFromPRF(new Uint8Array(result.prfOutput));
this.walletAddress = eoa.address;
// Initialize key manager for session
const km = new EncryptIDKeyManager();
await km.initFromPRF(result.prfOutput);
const keys = await km.getKeys();
this.did = keys.did;
// Create session
const session = getSessionManager();
await session.createSession(result, keys.did, {
encrypt: true,
sign: true,
wallet: true,
}); });
} else {
// Zero private key — we don't need to sign anything here this.authError = 'Identity component not available. Please sign in from the top-right menu.';
eoa.privateKey.fill(0); this.render();
this.authenticated = true;
} catch (e) {
this.authError = e instanceof Error ? e.message : String(e);
} }
this.authenticating = false;
this.render();
} }
// ── Load existing payment from URL ── // ── Load existing payment from URL ──
@ -195,8 +176,9 @@ class FolkPaymentRequest extends HTMLElement {
try { try {
const { getSessionManager } = await import('../../../src/encryptid/session'); const { getSessionManager } = await import('../../../src/encryptid/session');
const { getSession: getRstackSession } = await import('../../../shared/components/rstack-identity');
const session = getSessionManager(); const session = getSessionManager();
const accessToken = session.getSession()?.accessToken; const accessToken = session.getSession()?.accessToken || getRstackSession()?.accessToken;
const res = await fetch(`${this.getApiBase()}/api/payments`, { const res = await fetch(`${this.getApiBase()}/api/payments`, {
method: 'POST', method: 'POST',