@pooflabs/core 0.0.47 → 0.0.48

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/index.js CHANGED
@@ -396,6 +396,28 @@ class WebSessionManager {
396
396
  static async storeSession(address, accessToken, idToken, refreshToken) {
397
397
  if (typeof window === "undefined")
398
398
  return;
399
+ // JWT-wallet binding: refuse to store a session whose idToken is bound
400
+ // to a different wallet than `address`. Prevents races that would otherwise
401
+ // leave localStorage with mismatched address/token state.
402
+ try {
403
+ const payloadB64 = idToken.split(".")[1];
404
+ if (payloadB64) {
405
+ const payload = JSON.parse(this.decodeBase64Url(payloadB64));
406
+ const tokenWallet = payload["custom:walletAddress"];
407
+ if (tokenWallet && tokenWallet !== address) {
408
+ throw new Error(`[WebSessionManager] Refusing to store session: address (${address}) does not match idToken custom:walletAddress (${tokenWallet})`);
409
+ }
410
+ if (!tokenWallet) {
411
+ console.warn("[WebSessionManager] storeSession: idToken has no custom:walletAddress claim — writing without validation");
412
+ }
413
+ }
414
+ }
415
+ catch (err) {
416
+ if (typeof (err === null || err === void 0 ? void 0 : err.message) === "string" && err.message.includes("Refusing to store session")) {
417
+ throw err;
418
+ }
419
+ console.warn("[WebSessionManager] storeSession: failed to decode idToken for validation:", err);
420
+ }
399
421
  const config = await getConfig();
400
422
  const currentAppId = config.appId;
401
423
  localStorage.setItem(this.TAROBASE_SESSION_STORAGE_KEY, JSON.stringify({
@@ -5314,6 +5336,28 @@ class ReactNativeSessionManager {
5314
5336
  /* STORE */
5315
5337
  /* ------------------------------------------------------------------ */
5316
5338
  static async storeSession(address, accessToken, idToken, refreshToken) {
5339
+ // JWT-wallet binding: refuse to store a session whose idToken is bound
5340
+ // to a different wallet than `address`. Prevents races that would otherwise
5341
+ // leave storage with mismatched address/token state.
5342
+ try {
5343
+ const payloadB64 = idToken.split(".")[1];
5344
+ if (payloadB64) {
5345
+ const payload = JSON.parse(this.decodeBase64Url(payloadB64));
5346
+ const tokenWallet = payload["custom:walletAddress"];
5347
+ if (tokenWallet && tokenWallet !== address) {
5348
+ throw new Error(`[ReactNativeSessionManager] Refusing to store session: address (${address}) does not match idToken custom:walletAddress (${tokenWallet})`);
5349
+ }
5350
+ if (!tokenWallet) {
5351
+ console.warn("[ReactNativeSessionManager] storeSession: idToken has no custom:walletAddress claim — writing without validation");
5352
+ }
5353
+ }
5354
+ }
5355
+ catch (err) {
5356
+ if (typeof (err === null || err === void 0 ? void 0 : err.message) === "string" && err.message.includes("Refusing to store session")) {
5357
+ throw err;
5358
+ }
5359
+ console.warn("[ReactNativeSessionManager] storeSession: failed to decode idToken for validation:", err);
5360
+ }
5317
5361
  const config = await getConfig();
5318
5362
  const currentAppId = config.appId;
5319
5363
  this.getStorage().setItem(this.TAROBASE_SESSION_STORAGE_KEY, JSON.stringify({