@proveanything/smartlinks-auth-ui 0.1.11 → 0.1.13

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.
@@ -1 +1 @@
1
- {"version":3,"file":"SmartlinksAuthUI.d.ts","sourceRoot":"","sources":["../../src/components/SmartlinksAuthUI.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAuC,MAAM,OAAO,CAAC;AAW5D,OAAO,KAAK,EAAE,qBAAqB,EAAyC,MAAM,UAAU,CAAC;AA8E7F,eAAO,MAAM,gBAAgB,EAAE,KAAK,CAAC,EAAE,CAAC,qBAAqB,CA4gC5D,CAAC"}
1
+ {"version":3,"file":"SmartlinksAuthUI.d.ts","sourceRoot":"","sources":["../../src/components/SmartlinksAuthUI.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAuC,MAAM,OAAO,CAAC;AAW5D,OAAO,KAAK,EAAE,qBAAqB,EAAyC,MAAM,UAAU,CAAC;AA8E7F,eAAO,MAAM,gBAAgB,EAAE,KAAK,CAAC,EAAE,CAAC,qBAAqB,CAyhC5D,CAAC"}
@@ -7,6 +7,7 @@ interface AuthContextValue {
7
7
  accountInfo: Record<string, any> | null;
8
8
  isAuthenticated: boolean;
9
9
  isLoading: boolean;
10
+ proxyMode: boolean;
10
11
  login: (token: string, user: AuthUser, accountData?: Record<string, any>) => Promise<void>;
11
12
  logout: () => Promise<void>;
12
13
  getToken: () => Promise<string | null>;
@@ -18,6 +19,7 @@ interface AuthContextValue {
18
19
  }
19
20
  interface AuthProviderProps {
20
21
  children: React.ReactNode;
22
+ proxyMode?: boolean;
21
23
  accountCacheTTL?: number;
22
24
  preloadAccountInfo?: boolean;
23
25
  }
@@ -1 +1 @@
1
- {"version":3,"file":"AuthContext.d.ts","sourceRoot":"","sources":["../../src/context/AuthContext.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA8E,MAAM,OAAO,CAAC;AAInG,OAAO,KAAK,EAAE,QAAQ,EAAE,uBAAuB,EAAE,MAAM,UAAU,CAAC;AAElE,UAAU,gBAAgB;IACxB,IAAI,EAAE,QAAQ,GAAG,IAAI,CAAC;IACtB,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;IACrB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,CAAC;IACxC,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,CAAC;IACxC,eAAe,EAAE,OAAO,CAAC;IACzB,SAAS,EAAE,OAAO,CAAC;IACnB,KAAK,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAC3F,MAAM,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5B,QAAQ,EAAE,MAAM,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC;IACvC,YAAY,EAAE,MAAM,OAAO,CAAC,MAAM,CAAC,CAAC;IACpC,UAAU,EAAE,CAAC,YAAY,CAAC,EAAE,OAAO,KAAK,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC,CAAC;IACrE,cAAc,EAAE,MAAM,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC,CAAC;IACnD,iBAAiB,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IACvC,iBAAiB,EAAE,CAAC,QAAQ,EAAE,uBAAuB,KAAK,MAAM,IAAI,CAAC;CACtE;AAID,UAAU,iBAAiB;IACzB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB,kBAAkB,CAAC,EAAE,OAAO,CAAC;CAC9B;AAED,eAAO,MAAM,YAAY,EAAE,KAAK,CAAC,EAAE,CAAC,iBAAiB,CAiRpD,CAAC;AAEF,eAAO,MAAM,OAAO,QAAO,gBAM1B,CAAC"}
1
+ {"version":3,"file":"AuthContext.d.ts","sourceRoot":"","sources":["../../src/context/AuthContext.tsx"],"names":[],"mappings":"AAAA,OAAO,KAA8E,MAAM,OAAO,CAAC;AAInG,OAAO,KAAK,EAAE,QAAQ,EAAE,uBAAuB,EAAE,MAAM,UAAU,CAAC;AAElE,UAAU,gBAAgB;IACxB,IAAI,EAAE,QAAQ,GAAG,IAAI,CAAC;IACtB,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;IACrB,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,CAAC;IACxC,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GAAG,IAAI,CAAC;IACxC,eAAe,EAAE,OAAO,CAAC;IACzB,SAAS,EAAE,OAAO,CAAC;IACnB,SAAS,EAAE,OAAO,CAAC;IACnB,KAAK,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAC3F,MAAM,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5B,QAAQ,EAAE,MAAM,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC,CAAC;IACvC,YAAY,EAAE,MAAM,OAAO,CAAC,MAAM,CAAC,CAAC;IACpC,UAAU,EAAE,CAAC,YAAY,CAAC,EAAE,OAAO,KAAK,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC,CAAC;IACrE,cAAc,EAAE,MAAM,OAAO,CAAC,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC,CAAC;IACnD,iBAAiB,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAC;IACvC,iBAAiB,EAAE,CAAC,QAAQ,EAAE,uBAAuB,KAAK,MAAM,IAAI,CAAC;CACtE;AAID,UAAU,iBAAiB;IACzB,QAAQ,EAAE,KAAK,CAAC,SAAS,CAAC;IAC1B,SAAS,CAAC,EAAE,OAAO,CAAC;IACpB,eAAe,CAAC,EAAE,MAAM,CAAC;IACzB,kBAAkB,CAAC,EAAE,OAAO,CAAC;CAC9B;AAED,eAAO,MAAM,YAAY,EAAE,KAAK,CAAC,EAAE,CAAC,iBAAiB,CA+YpD,CAAC;AAEF,eAAO,MAAM,OAAO,QAAO,gBAM1B,CAAC"}
package/dist/index.esm.js CHANGED
@@ -11217,7 +11217,7 @@ const tokenStorage = {
11217
11217
  };
11218
11218
 
11219
11219
  const AuthContext = createContext(undefined);
11220
- const AuthProvider = ({ children, accountCacheTTL = 5 * 60 * 1000, preloadAccountInfo = false }) => {
11220
+ const AuthProvider = ({ children, proxyMode = false, accountCacheTTL = 5 * 60 * 1000, preloadAccountInfo = false }) => {
11221
11221
  const [user, setUser] = useState(null);
11222
11222
  const [token, setToken] = useState(null);
11223
11223
  const [accountData, setAccountData] = useState(null);
@@ -11241,10 +11241,45 @@ const AuthProvider = ({ children, accountCacheTTL = 5 * 60 * 1000, preloadAccoun
11241
11241
  }
11242
11242
  });
11243
11243
  }, []);
11244
- // Initialize auth state from persistent storage
11244
+ // Initialize auth state - different behavior for proxy mode vs standalone mode
11245
11245
  useEffect(() => {
11246
11246
  const initializeAuth = async () => {
11247
11247
  try {
11248
+ if (proxyMode) {
11249
+ // PROXY MODE: Initialize from URL params and parent via SDK
11250
+ const params = new URLSearchParams(window.location.search);
11251
+ const userId = params.get('userId');
11252
+ if (userId) {
11253
+ console.log('[AuthContext] Proxy mode: userId detected, fetching account from parent');
11254
+ try {
11255
+ // Fetch account details from parent via proxied API call
11256
+ const accountResponse = await smartlinks.auth.getAccount();
11257
+ // Build user object from account response
11258
+ const accountAny = accountResponse;
11259
+ const userFromAccount = {
11260
+ uid: userId,
11261
+ email: accountAny?.email,
11262
+ displayName: accountAny?.displayName || accountAny?.name,
11263
+ phoneNumber: accountAny?.phoneNumber,
11264
+ };
11265
+ setUser(userFromAccount);
11266
+ setAccountData(accountResponse);
11267
+ setAccountInfo(accountResponse);
11268
+ console.log('[AuthContext] Proxy mode: initialized from parent account');
11269
+ notifyAuthStateChange('LOGIN', userFromAccount, null, accountResponse, accountResponse);
11270
+ }
11271
+ catch (error) {
11272
+ console.warn('[AuthContext] Proxy mode: failed to fetch account from parent:', error);
11273
+ // No session - that's ok, user may need to login
11274
+ }
11275
+ }
11276
+ else {
11277
+ console.log('[AuthContext] Proxy mode: no userId in URL, awaiting login');
11278
+ }
11279
+ setIsLoading(false);
11280
+ return;
11281
+ }
11282
+ // STANDALONE MODE: Load from persistent storage
11248
11283
  const storedToken = await tokenStorage.getToken();
11249
11284
  const storedUser = await tokenStorage.getUser();
11250
11285
  const storedAccountData = await tokenStorage.getAccountData();
@@ -11271,9 +11306,49 @@ const AuthProvider = ({ children, accountCacheTTL = 5 * 60 * 1000, preloadAccoun
11271
11306
  }
11272
11307
  };
11273
11308
  initializeAuth();
11274
- }, []);
11275
- // Cross-tab synchronization - listen for auth changes in other tabs
11309
+ }, [proxyMode, notifyAuthStateChange]);
11310
+ // Listen for parent auth state changes (proxy mode only)
11311
+ useEffect(() => {
11312
+ if (!proxyMode)
11313
+ return;
11314
+ console.log('[AuthContext] Proxy mode: setting up parent message listener');
11315
+ const handleParentMessage = (event) => {
11316
+ // Handle auth state pushed from parent
11317
+ if (event.data?.type === 'smartlinks:authkit:state') {
11318
+ const { user: parentUser, accountData: parentAccountData, authenticated } = event.data.payload || {};
11319
+ console.log('[AuthContext] Proxy mode: received state from parent:', { authenticated });
11320
+ if (authenticated && parentUser) {
11321
+ const userObj = {
11322
+ uid: parentUser.uid || parentUser.id,
11323
+ email: parentUser.email,
11324
+ displayName: parentUser.displayName || parentUser.name,
11325
+ phoneNumber: parentUser.phoneNumber,
11326
+ };
11327
+ setUser(userObj);
11328
+ setAccountData(parentAccountData || null);
11329
+ setAccountInfo(parentAccountData || null);
11330
+ notifyAuthStateChange('CROSS_TAB_SYNC', userObj, null, parentAccountData || null, parentAccountData || null);
11331
+ }
11332
+ else {
11333
+ // Parent indicates no session / logged out
11334
+ setUser(null);
11335
+ setToken(null);
11336
+ setAccountData(null);
11337
+ setAccountInfo(null);
11338
+ notifyAuthStateChange('LOGOUT', null, null, null, null);
11339
+ }
11340
+ }
11341
+ };
11342
+ window.addEventListener('message', handleParentMessage);
11343
+ return () => {
11344
+ console.log('[AuthContext] Proxy mode: cleaning up parent message listener');
11345
+ window.removeEventListener('message', handleParentMessage);
11346
+ };
11347
+ }, [proxyMode, notifyAuthStateChange]);
11348
+ // Cross-tab synchronization - standalone mode only
11276
11349
  useEffect(() => {
11350
+ if (proxyMode)
11351
+ return; // Skip cross-tab sync in proxy mode
11277
11352
  console.log('[AuthContext] Setting up cross-tab synchronization');
11278
11353
  const unsubscribe = onStorageChange(async (event) => {
11279
11354
  console.log('[AuthContext] Cross-tab storage event:', event.type, event.key);
@@ -11332,27 +11407,38 @@ const AuthProvider = ({ children, accountCacheTTL = 5 * 60 * 1000, preloadAccoun
11332
11407
  console.log('[AuthContext] Cleaning up cross-tab synchronization');
11333
11408
  unsubscribe();
11334
11409
  };
11335
- }, [notifyAuthStateChange]);
11410
+ }, [proxyMode, notifyAuthStateChange]);
11336
11411
  const login = useCallback(async (authToken, authUser, authAccountData) => {
11337
11412
  try {
11338
- // Store token, user, and account data
11339
- await tokenStorage.saveToken(authToken);
11340
- await tokenStorage.saveUser(authUser);
11341
- if (authAccountData) {
11342
- await tokenStorage.saveAccountData(authAccountData);
11413
+ // Only persist to storage in standalone mode
11414
+ if (!proxyMode) {
11415
+ await tokenStorage.saveToken(authToken);
11416
+ await tokenStorage.saveUser(authUser);
11417
+ if (authAccountData) {
11418
+ await tokenStorage.saveAccountData(authAccountData);
11419
+ }
11420
+ // Set bearer token in global Smartlinks SDK via auth.verifyToken
11421
+ smartlinks.auth.verifyToken(authToken).catch(err => {
11422
+ console.warn('Failed to set bearer token on login:', err);
11423
+ });
11343
11424
  }
11425
+ // Always update memory state
11344
11426
  setToken(authToken);
11345
11427
  setUser(authUser);
11346
11428
  setAccountData(authAccountData || null);
11347
- // Set bearer token in global Smartlinks SDK via auth.verifyToken
11348
- // This both validates the token and sets it for future API calls
11349
- smartlinks.auth.verifyToken(authToken).catch(err => {
11350
- console.warn('Failed to set bearer token on login:', err);
11351
- });
11429
+ // Cross-iframe auth state synchronization
11430
+ // Always notify parent frame of login (both modes, but especially important in proxy mode)
11431
+ const sdk = smartlinks;
11432
+ if (sdk.iframe?.isIframe?.()) {
11433
+ sdk.iframe.sendParentCustom('smartlinks:authkit:login', {
11434
+ token: authToken,
11435
+ user: authUser,
11436
+ accountData: authAccountData || null
11437
+ });
11438
+ }
11352
11439
  notifyAuthStateChange('LOGIN', authUser, authToken, authAccountData || null);
11353
- // Optionally preload account info on login
11354
- if (preloadAccountInfo) {
11355
- // Preload after login completes (non-blocking)
11440
+ // Optionally preload account info on login (standalone mode only)
11441
+ if (!proxyMode && preloadAccountInfo) {
11356
11442
  getAccount(true).catch(error => {
11357
11443
  console.warn('[AuthContext] Failed to preload account info:', error);
11358
11444
  });
@@ -11362,34 +11448,55 @@ const AuthProvider = ({ children, accountCacheTTL = 5 * 60 * 1000, preloadAccoun
11362
11448
  console.error('Failed to save auth data to storage:', error);
11363
11449
  throw error;
11364
11450
  }
11365
- }, [notifyAuthStateChange, preloadAccountInfo]);
11451
+ }, [proxyMode, notifyAuthStateChange, preloadAccountInfo]);
11366
11452
  const logout = useCallback(async () => {
11367
11453
  try {
11368
- // Clear persistent storage
11369
- await tokenStorage.clearAll();
11454
+ // Only clear persistent storage in standalone mode
11455
+ if (!proxyMode) {
11456
+ await tokenStorage.clearAll();
11457
+ smartlinks.auth.logout();
11458
+ }
11459
+ // Always clear memory state
11370
11460
  setToken(null);
11371
11461
  setUser(null);
11372
11462
  setAccountData(null);
11373
11463
  setAccountInfo(null);
11374
- // Clear bearer token from global Smartlinks SDK
11375
- smartlinks.auth.logout();
11464
+ // Cross-iframe auth state synchronization
11465
+ // Always notify parent frame of logout
11466
+ const sdk = smartlinks;
11467
+ if (sdk.iframe?.isIframe?.()) {
11468
+ sdk.iframe.sendParentCustom('smartlinks:authkit:logout', {});
11469
+ }
11376
11470
  notifyAuthStateChange('LOGOUT', null, null, null);
11377
11471
  }
11378
11472
  catch (error) {
11379
11473
  console.error('Failed to clear auth data from storage:', error);
11380
11474
  }
11381
- }, [notifyAuthStateChange]);
11475
+ }, [proxyMode, notifyAuthStateChange]);
11382
11476
  const getToken = useCallback(async () => {
11477
+ if (proxyMode) {
11478
+ // In proxy mode, token is managed by parent - return memory state
11479
+ return token;
11480
+ }
11383
11481
  const storedToken = await tokenStorage.getToken();
11384
11482
  return storedToken ? storedToken.token : null;
11385
- }, []);
11483
+ }, [proxyMode, token]);
11386
11484
  const refreshToken = useCallback(async () => {
11387
11485
  throw new Error('Token refresh must be implemented via your backend API');
11388
11486
  }, []);
11389
- // Get account with intelligent caching
11487
+ // Get account with intelligent caching (or direct parent fetch in proxy mode)
11390
11488
  const getAccount = useCallback(async (forceRefresh = false) => {
11391
11489
  try {
11392
- // Check if user is authenticated
11490
+ if (proxyMode) {
11491
+ // PROXY MODE: Always fetch from parent via proxied API, no local cache
11492
+ console.log('[AuthContext] Proxy mode: fetching account from parent');
11493
+ const freshAccountInfo = await smartlinks.auth.getAccount();
11494
+ setAccountInfo(freshAccountInfo);
11495
+ setAccountData(freshAccountInfo);
11496
+ notifyAuthStateChange('ACCOUNT_REFRESH', user, token, freshAccountInfo, freshAccountInfo);
11497
+ return freshAccountInfo;
11498
+ }
11499
+ // STANDALONE MODE: Use caching
11393
11500
  if (!token) {
11394
11501
  throw new Error('Not authenticated. Please login first.');
11395
11502
  }
@@ -11412,24 +11519,28 @@ const AuthProvider = ({ children, accountCacheTTL = 5 * 60 * 1000, preloadAccoun
11412
11519
  }
11413
11520
  catch (error) {
11414
11521
  console.error('[AuthContext] Failed to get account info:', error);
11415
- // Fallback to stale cache if API fails
11416
- const cached = await tokenStorage.getAccountInfo();
11417
- if (cached) {
11418
- console.warn('[AuthContext] Returning stale cached data due to API error');
11419
- return cached.data;
11522
+ // Fallback to stale cache if API fails (standalone mode only)
11523
+ if (!proxyMode) {
11524
+ const cached = await tokenStorage.getAccountInfo();
11525
+ if (cached) {
11526
+ console.warn('[AuthContext] Returning stale cached data due to API error');
11527
+ return cached.data;
11528
+ }
11420
11529
  }
11421
11530
  throw error;
11422
11531
  }
11423
- }, [token, accountCacheTTL, user, accountData, notifyAuthStateChange]);
11532
+ }, [proxyMode, token, accountCacheTTL, user, accountData, notifyAuthStateChange]);
11424
11533
  // Convenience method for explicit refresh
11425
11534
  const refreshAccount = useCallback(async () => {
11426
11535
  return await getAccount(true);
11427
11536
  }, [getAccount]);
11428
- // Clear account cache
11537
+ // Clear account cache (no-op in proxy mode)
11429
11538
  const clearAccountCache = useCallback(async () => {
11430
- await tokenStorage.clearAccountInfo();
11539
+ if (!proxyMode) {
11540
+ await tokenStorage.clearAccountInfo();
11541
+ }
11431
11542
  setAccountInfo(null);
11432
- }, []);
11543
+ }, [proxyMode]);
11433
11544
  const onAuthStateChange = useCallback((callback) => {
11434
11545
  callbacksRef.current.add(callback);
11435
11546
  // Return unsubscribe function
@@ -11442,8 +11553,9 @@ const AuthProvider = ({ children, accountCacheTTL = 5 * 60 * 1000, preloadAccoun
11442
11553
  token,
11443
11554
  accountData,
11444
11555
  accountInfo,
11445
- isAuthenticated: !!token && !!user,
11556
+ isAuthenticated: !!user,
11446
11557
  isLoading,
11558
+ proxyMode,
11447
11559
  login,
11448
11560
  logout,
11449
11561
  getToken,
@@ -11533,7 +11645,7 @@ const getFriendlyErrorMessage = (errorMessage) => {
11533
11645
  // Return original message if no pattern matches
11534
11646
  return errorMessage;
11535
11647
  };
11536
- const SmartlinksAuthUI = ({ apiEndpoint, clientId, clientName, accountData, onAuthSuccess, onAuthError, enabledProviders = ['email', 'google', 'phone'], initialMode = 'login', redirectUrl, theme = 'auto', className, customization, skipConfigFetch = false, minimal = false, logger, }) => {
11648
+ const SmartlinksAuthUI = ({ apiEndpoint, clientId, clientName, accountData, onAuthSuccess, onAuthError, enabledProviders = ['email', 'google', 'phone'], initialMode = 'login', redirectUrl, theme = 'auto', className, customization, skipConfigFetch = false, minimal = false, logger, proxyMode = false, }) => {
11537
11649
  const [mode, setMode] = useState(initialMode);
11538
11650
  const [loading, setLoading] = useState(false);
11539
11651
  const [error, setError] = useState();
@@ -11566,25 +11678,25 @@ const SmartlinksAuthUI = ({ apiEndpoint, clientId, clientName, accountData, onAu
11566
11678
  mediaQuery.addEventListener('change', updateTheme);
11567
11679
  return () => mediaQuery.removeEventListener('change', updateTheme);
11568
11680
  }, [theme]);
11569
- // Reinitialize Smartlinks SDK when apiEndpoint changes (for test/dev scenarios)
11681
+ // Reinitialize Smartlinks SDK when apiEndpoint or proxyMode changes
11570
11682
  // IMPORTANT: Preserve bearer token during reinitialization
11571
11683
  useEffect(() => {
11572
- log.log('SDK reinitialize useEffect triggered', { apiEndpoint });
11684
+ log.log('SDK reinitialize useEffect triggered', { apiEndpoint, proxyMode });
11573
11685
  setSdkReady(false); // Mark SDK as not ready during reinitialization
11574
11686
  const reinitializeWithToken = async () => {
11575
11687
  if (apiEndpoint) {
11576
- log.log('Reinitializing SDK with baseURL:', apiEndpoint);
11577
- // Get current token before reinitializing
11578
- const currentToken = await auth.getToken();
11688
+ log.log('Reinitializing SDK with baseURL:', apiEndpoint, 'proxyMode:', proxyMode);
11689
+ // Get current token before reinitializing (only in standalone mode)
11690
+ const currentToken = !proxyMode ? await auth.getToken() : null;
11579
11691
  smartlinks.initializeApi({
11580
11692
  baseURL: apiEndpoint,
11581
- proxyMode: false, // Direct API calls when custom endpoint is provided
11693
+ proxyMode: proxyMode, // Use prop value
11582
11694
  ngrokSkipBrowserWarning: true,
11583
11695
  logger: logger, // Pass logger to SDK for verbose SDK logging
11584
11696
  });
11585
11697
  log.log('SDK reinitialized successfully');
11586
- // Restore bearer token after reinitialization using auth.verifyToken
11587
- if (currentToken) {
11698
+ // Restore bearer token after reinitialization using auth.verifyToken (standalone mode only)
11699
+ if (currentToken && !proxyMode) {
11588
11700
  smartlinks.auth.verifyToken(currentToken).catch(err => {
11589
11701
  log.warn('Failed to restore bearer token after reinit:', err);
11590
11702
  });
@@ -11592,6 +11704,11 @@ const SmartlinksAuthUI = ({ apiEndpoint, clientId, clientName, accountData, onAu
11592
11704
  // Mark SDK as ready
11593
11705
  setSdkReady(true);
11594
11706
  }
11707
+ else if (proxyMode) {
11708
+ // In proxy mode without custom endpoint, SDK should already be initialized by parent
11709
+ log.log('Proxy mode without apiEndpoint, SDK already initialized by parent');
11710
+ setSdkReady(true);
11711
+ }
11595
11712
  else {
11596
11713
  log.log('No apiEndpoint, SDK already initialized by App');
11597
11714
  // SDK was initialized by App component, mark as ready
@@ -11599,7 +11716,7 @@ const SmartlinksAuthUI = ({ apiEndpoint, clientId, clientName, accountData, onAu
11599
11716
  }
11600
11717
  };
11601
11718
  reinitializeWithToken();
11602
- }, [apiEndpoint, auth, logger, log]);
11719
+ }, [apiEndpoint, proxyMode, auth, logger, log]);
11603
11720
  // Get the effective redirect URL (use prop or default to current page)
11604
11721
  const getRedirectUrl = () => {
11605
11722
  if (redirectUrl)
@@ -12113,11 +12230,18 @@ const SmartlinksAuthUI = ({ apiEndpoint, clientId, clientName, accountData, onAu
12113
12230
  },
12114
12231
  auto_select: false,
12115
12232
  cancel_on_tap_outside: true,
12233
+ // Note: use_fedcm_for_prompt omitted - requires Permissions-Policy header on hosting server
12234
+ // Will be needed when FedCM becomes mandatory in the future
12116
12235
  });
12117
- google.accounts.id.prompt((notification) => {
12118
- if (notification.isNotDisplayed() || notification.isSkippedMoment()) {
12119
- setLoading(false);
12120
- }
12236
+ // Use timeout fallback instead of deprecated notification methods
12237
+ // (isNotDisplayed/isSkippedMoment will stop working when FedCM becomes mandatory)
12238
+ const promptTimeout = setTimeout(() => {
12239
+ setLoading(false);
12240
+ }, 5000);
12241
+ google.accounts.id.prompt(() => {
12242
+ // Clear timeout if prompt interaction occurs
12243
+ clearTimeout(promptTimeout);
12244
+ setLoading(false);
12121
12245
  });
12122
12246
  }
12123
12247
  }