@truly-you/trulyyou-web-sdk 0.1.19 → 0.1.21

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.
@@ -52,6 +52,7 @@ export declare class TrulyYouSDK {
52
52
  * Probe iframe to check if key exists in iframe's localStorage
53
53
  * Also checks backend to verify key exists and is active
54
54
  * REQUIRES authFlowId to be loaded first
55
+ * @param handoff - If true, probes for handoff keyId (with _handoff suffix)
55
56
  */
56
57
  private probeIframeForKey;
57
58
  /**
@@ -84,6 +85,7 @@ export declare class TrulyYouSDK {
84
85
  /**
85
86
  * Public method to probe for keyId - checks localStorage first, then probes TrulyYou frontend via iframe
86
87
  * Returns the keyId if found, null otherwise
88
+ * @param handoff - If true, probes for handoff keyId (with _handoff suffix)
87
89
  */
88
- probeForKeyId(): Promise<string | null>;
90
+ probeForKeyId(handoff?: boolean): Promise<string | null>;
89
91
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@truly-you/trulyyou-web-sdk",
3
- "version": "0.1.19",
3
+ "version": "0.1.21",
4
4
  "description": "TrulyYou Web SDK for secure authentication and payload signing",
5
5
  "type": "module",
6
6
  "main": "dist/index.esm.js",
@@ -8,7 +8,7 @@ export class TrulyYouSDK {
8
8
  private authAppId: string | undefined
9
9
  private invisible: boolean
10
10
  private targetElement: string | HTMLElement | undefined
11
- private brandingCache: { primary?: string; background?: string; secondary?: string; textColor?: string; icon?: string; name?: string; authFlowId?: string } | null = null
11
+ private brandingCache: { primary?: string; background?: string; secondary?: string; textColor?: string; icon?: string; name?: string; authFlowId?: string; pusher?: { realtimeUrl?: string; appKey?: string } } | null = null
12
12
  private realtimeUrl: string
13
13
  private mockMobileDevice: boolean
14
14
 
@@ -89,7 +89,13 @@ export class TrulyYouSDK {
89
89
  textColor: app.colors?.textColor,
90
90
  icon: app.icon,
91
91
  name: app.name,
92
- authFlowId: app.authFlowId
92
+ authFlowId: app.authFlowId,
93
+ ...(app.pusher && {
94
+ pusher: {
95
+ realtimeUrl: app.pusher.realtimeUrl,
96
+ appKey: app.pusher.appKey
97
+ }
98
+ })
93
99
  }
94
100
  console.log('[SDK]: Branding and authFlowId fetched and cached:', this.brandingCache)
95
101
  return !!app.authFlowId
@@ -308,8 +314,9 @@ export class TrulyYouSDK {
308
314
  * Probe iframe to check if key exists in iframe's localStorage
309
315
  * Also checks backend to verify key exists and is active
310
316
  * REQUIRES authFlowId to be loaded first
317
+ * @param handoff - If true, probes for handoff keyId (with _handoff suffix)
311
318
  */
312
- private async probeIframeForKey(): Promise<string | null> {
319
+ private async probeIframeForKey(handoff: boolean = false): Promise<string | null> {
313
320
  // Ensure authFlowId is loaded before probing
314
321
  await this.ensureAuthFlowIdLoaded()
315
322
 
@@ -332,7 +339,10 @@ export class TrulyYouSDK {
332
339
  // Add authFlowId (guaranteed to exist now after ensureAuthFlowIdLoaded)
333
340
  const authFlowId = this.brandingCache!.authFlowId!
334
341
  probeUrl.searchParams.set('authFlowId', authFlowId)
335
- console.log('[SDK-PROBE]: Adding authFlowId to probe:', authFlowId)
342
+ if (handoff) {
343
+ probeUrl.searchParams.set('handoff', 'true')
344
+ }
345
+ console.log(`[SDK-PROBE]: Adding authFlowId to probe: ${authFlowId}${handoff ? ' (handoff)' : ''}`)
336
346
 
337
347
  iframe.src = probeUrl.toString()
338
348
 
@@ -1012,6 +1022,11 @@ export class TrulyYouSDK {
1012
1022
  apiCallStructure: apiCallStructure
1013
1023
  }
1014
1024
 
1025
+ // Get Pusher config from branding cache (from API) or fall back to config/constructor values
1026
+ const pusherConfigFromBranding = this.brandingCache?.pusher
1027
+ const realtimeUrlToUse = pusherConfigFromBranding?.realtimeUrl || this.realtimeUrl
1028
+ const pusherAppKeyToUse = pusherConfigFromBranding?.appKey || this.config.pusherAppKey || 'app-key'
1029
+
1015
1030
  // Parse realtimeUrl to extract host/port for Pusher
1016
1031
  let pusherHost: string | undefined
1017
1032
  let pusherPort: number | undefined
@@ -1019,9 +1034,9 @@ export class TrulyYouSDK {
1019
1034
  let encrypted = true
1020
1035
 
1021
1036
  try {
1022
- const realtimeUrlObj = new URL(this.realtimeUrl.startsWith('ws://') || this.realtimeUrl.startsWith('wss://')
1023
- ? this.realtimeUrl
1024
- : this.realtimeUrl.replace(/^http:/, 'ws:').replace(/^https:/, 'wss:'))
1037
+ const realtimeUrlObj = new URL(realtimeUrlToUse.startsWith('ws://') || realtimeUrlToUse.startsWith('wss://')
1038
+ ? realtimeUrlToUse
1039
+ : realtimeUrlToUse.replace(/^http:/, 'ws:').replace(/^https:/, 'wss:'))
1025
1040
 
1026
1041
  pusherHost = realtimeUrlObj.hostname
1027
1042
  pusherPort = realtimeUrlObj.port ? parseInt(realtimeUrlObj.port, 10) : (realtimeUrlObj.protocol === 'wss:' ? 443 : 80)
@@ -1033,8 +1048,8 @@ export class TrulyYouSDK {
1033
1048
  pusherPort = 6001
1034
1049
  }
1035
1050
 
1036
- // Get Pusher app key from config or use default
1037
- const pusherAppKey = this.config.pusherAppKey || 'app-key'
1051
+ // Get Pusher app key from branding cache, config, or default
1052
+ const pusherAppKey = pusherAppKeyToUse
1038
1053
 
1039
1054
  // Merge custom Pusher config with parsed values
1040
1055
  // When using custom wsHost/wsPort, we need to set cluster to empty string to disable default cluster behavior
@@ -1049,6 +1064,8 @@ export class TrulyYouSDK {
1049
1064
  }
1050
1065
 
1051
1066
  console.log('[SDK]: Initializing Pusher with config:', pusherOptions)
1067
+ console.log('[SDK]: Pusher app key:', pusherAppKey ? `${pusherAppKey.substring(0, 10)}...` : 'not set')
1068
+ console.log('[SDK]: Pusher config source:', pusherConfigFromBranding ? 'branding API' : (this.config.pusherAppKey ? 'constructor config' : 'default'))
1052
1069
  const pusher = new Pusher(pusherAppKey, pusherOptions)
1053
1070
 
1054
1071
  // Use signatureId as the channel name (Soketi doesn't need 'public-' prefix)
@@ -1888,8 +1905,9 @@ export class TrulyYouSDK {
1888
1905
  /**
1889
1906
  * Public method to probe for keyId - checks localStorage first, then probes TrulyYou frontend via iframe
1890
1907
  * Returns the keyId if found, null otherwise
1908
+ * @param handoff - If true, probes for handoff keyId (with _handoff suffix)
1891
1909
  */
1892
- async probeForKeyId(): Promise<string | null> {
1910
+ async probeForKeyId(handoff: boolean = false): Promise<string | null> {
1893
1911
  // Ensure authFlowId is loaded first
1894
1912
  await this.ensureAuthFlowIdLoaded()
1895
1913
 
@@ -1901,15 +1919,17 @@ export class TrulyYouSDK {
1901
1919
  const authFlowId = this.brandingCache.authFlowId
1902
1920
 
1903
1921
  // First, check localStorage (same origin - this app's localStorage)
1904
- const keyIdFromStorage = this.getKeyIdByAuthFlowId(authFlowId)
1922
+ const storageKey = handoff ? `trulyYouKeyId_${authFlowId}_handoff` : `trulyYouKeyId_${authFlowId}`
1923
+ const keyIdFromStorage = typeof window !== 'undefined' ? localStorage.getItem(storageKey) : null
1924
+
1905
1925
  if (keyIdFromStorage) {
1906
- console.log('[SDK-PROBE]: Found keyId in same-origin localStorage')
1926
+ console.log(`[SDK-PROBE]: Found ${handoff ? 'handoff ' : ''}keyId in same-origin localStorage`)
1907
1927
  return keyIdFromStorage
1908
1928
  }
1909
1929
 
1910
1930
  // If not found in same-origin localStorage, probe TrulyYou frontend's localStorage via iframe
1911
- console.log('[SDK-PROBE]: KeyId not found in same-origin localStorage, probing TrulyYou frontend...')
1912
- return await this.probeIframeForKey()
1931
+ console.log(`[SDK-PROBE]: ${handoff ? 'Handoff ' : ''}KeyId not found in same-origin localStorage, probing TrulyYou frontend...`)
1932
+ return await this.probeIframeForKey(handoff)
1913
1933
  }
1914
1934
  }
1915
1935