@quiltt/react 4.5.1 → 5.0.1

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.
Files changed (91) hide show
  1. package/CHANGELOG.md +32 -0
  2. package/README.md +15 -3
  3. package/dist/components/QuilttProviderRender-12s-pvnc98Lj.cjs +6 -0
  4. package/dist/components/QuilttSettings-12s-cLPT_GLC.cjs +6 -0
  5. package/dist/components/index.cjs +211 -0
  6. package/dist/components/index.d.ts +55 -0
  7. package/dist/components/index.js +208 -0
  8. package/dist/components/useQuilttConnector-12s-BLTzI3gE.cjs +174 -0
  9. package/dist/components/useQuilttConnector-12s-UQQcvQrO.js +174 -0
  10. package/dist/components/useQuilttRenderGuard-12s-D9WbRzZO.cjs +36 -0
  11. package/dist/components/useQuilttSession-12s-BjyJL1qZ.cjs +133 -0
  12. package/dist/components/useQuilttSession-12s-VOH0S5zh.js +133 -0
  13. package/dist/components/useQuilttSettings-12s-aDLXY6z3.cjs +10 -0
  14. package/dist/components/useScript-12s-CMIDUHrx.cjs +92 -0
  15. package/dist/{useSession-12s-7GOn4sUn.js → components/useSession-12s-BNPsfKY-.js} +28 -7
  16. package/dist/components/useSession-12s-BNotXj5T.cjs +90 -0
  17. package/dist/{useStorage-12s-DHcq3Kuh.js → components/useStorage-12s-CpG6X57D.js} +7 -17
  18. package/dist/components/useStorage-12s-D7nllsrI.cjs +61 -0
  19. package/dist/contexts/QuilttSettings-12s-BK-0SQME.js +6 -0
  20. package/dist/contexts/QuilttSettings-12s-cLPT_GLC.cjs +6 -0
  21. package/dist/contexts/index.cjs +7 -0
  22. package/dist/contexts/index.d.ts +8 -0
  23. package/dist/contexts/index.js +1 -0
  24. package/dist/hooks/QuilttProviderRender-12s-DtQtubjL.js +6 -0
  25. package/dist/hooks/QuilttProviderRender-12s-pvnc98Lj.cjs +6 -0
  26. package/dist/hooks/QuilttSettings-12s-BK-0SQME.js +6 -0
  27. package/dist/hooks/QuilttSettings-12s-cLPT_GLC.cjs +6 -0
  28. package/dist/hooks/index.cjs +31 -0
  29. package/dist/hooks/index.d.ts +142 -0
  30. package/dist/hooks/index.js +11 -0
  31. package/dist/hooks/useEventListener-12s-CV8cLxWu.cjs +34 -0
  32. package/dist/hooks/useIsomorphicLayoutEffect-12s-B8KjaroI.cjs +9 -0
  33. package/dist/{useQuilttClient-12s-CAAUait1.js → hooks/useQuilttClient-12s-Dj_MtYTU.js} +1 -1
  34. package/dist/hooks/useQuilttClient-12s-flQYSVdG.cjs +6 -0
  35. package/dist/{useQuilttConnector-12s-D8VedbrT.js → hooks/useQuilttConnector-12s-C0KJHuZN.js} +5 -4
  36. package/dist/hooks/useQuilttConnector-12s-D51PZPgm.cjs +175 -0
  37. package/dist/hooks/useQuilttInstitutions-12s-D_Kr43s3.cjs +82 -0
  38. package/dist/{useQuilttInstitutions-12s-DExzPnfb.js → hooks/useQuilttInstitutions-12s-rgLHD9ye.js} +6 -16
  39. package/dist/hooks/useQuilttRenderGuard-12s-CsS2Ma6Q.js +36 -0
  40. package/dist/hooks/useQuilttRenderGuard-12s-D9WbRzZO.cjs +36 -0
  41. package/dist/{useQuilttResolvable-12s-C0BV3AvR.js → hooks/useQuilttResolvable-12s-BUDeH696.js} +6 -16
  42. package/dist/hooks/useQuilttResolvable-12s-D8wnfNBt.cjs +76 -0
  43. package/dist/hooks/useQuilttSession-12s-C8kq5S2Y.cjs +139 -0
  44. package/dist/hooks/useQuilttSession-12s-DQFfjmob.js +135 -0
  45. package/dist/hooks/useQuilttSettings-12s--rCJoNHD.js +10 -0
  46. package/dist/hooks/useQuilttSettings-12s-aDLXY6z3.cjs +10 -0
  47. package/dist/hooks/useScript-12s-CMIDUHrx.cjs +92 -0
  48. package/dist/hooks/useScript-12s-JCgaTW9n.js +92 -0
  49. package/dist/hooks/useSession-12s-BNPsfKY-.js +90 -0
  50. package/dist/hooks/useSession-12s-BNotXj5T.cjs +90 -0
  51. package/dist/hooks/useStorage-12s-CpG6X57D.js +61 -0
  52. package/dist/hooks/useStorage-12s-D7nllsrI.cjs +61 -0
  53. package/dist/index.cjs +149 -0
  54. package/dist/index.d.ts +7 -216
  55. package/dist/index.js +7 -191
  56. package/dist/providers/QuilttAuthProvider-12s-CDgQbarX.js +60 -0
  57. package/dist/providers/QuilttAuthProvider-12s-D__FY1Qn.cjs +60 -0
  58. package/dist/providers/QuilttProviderRender-12s-DtQtubjL.js +6 -0
  59. package/dist/providers/QuilttProviderRender-12s-pvnc98Lj.cjs +6 -0
  60. package/dist/providers/QuilttSettings-12s-BK-0SQME.js +6 -0
  61. package/dist/providers/QuilttSettings-12s-cLPT_GLC.cjs +6 -0
  62. package/dist/providers/QuilttSettingsProvider-12s-D7e8dsOE.cjs +19 -0
  63. package/dist/{QuilttSettingsProvider-12s-ZcmFmOiZ.js → providers/QuilttSettingsProvider-12s-DND2gPQm.js} +8 -5
  64. package/dist/providers/index.cjs +34 -0
  65. package/dist/providers/index.d.ts +28 -0
  66. package/dist/providers/index.js +30 -0
  67. package/dist/utils/index.cjs +89 -0
  68. package/dist/utils/index.d.ts +31 -0
  69. package/dist/utils/index.js +77 -0
  70. package/package.json +38 -12
  71. package/src/hooks/useQuilttClient.ts +1 -1
  72. package/src/hooks/useQuilttConnector.ts +3 -2
  73. package/src/hooks/useQuilttInstitutions.ts +8 -23
  74. package/src/hooks/useQuilttResolvable.ts +8 -23
  75. package/src/hooks/useSession.ts +32 -6
  76. package/src/hooks/useStorage.ts +7 -15
  77. package/src/index.ts +61 -0
  78. package/src/providers/QuilttAuthProvider.tsx +12 -5
  79. package/src/providers/QuilttProvider.tsx +5 -1
  80. package/src/providers/QuilttSettingsProvider.tsx +4 -5
  81. package/src/utils/index.ts +1 -0
  82. package/src/utils/telemetry.ts +33 -0
  83. package/dist/QuilttAuthProvider-12s-DE-ePRo_.js +0 -205
  84. package/dist/useQuilttSession-12s-sRvULtJv.js +0 -39
  85. /package/dist/{QuilttProviderRender-12s-DtQtubjL.js → components/QuilttProviderRender-12s-DtQtubjL.js} +0 -0
  86. /package/dist/{QuilttSettings-12s-BK-0SQME.js → components/QuilttSettings-12s-BK-0SQME.js} +0 -0
  87. /package/dist/{useQuilttRenderGuard-12s-CsS2Ma6Q.js → components/useQuilttRenderGuard-12s-CsS2Ma6Q.js} +0 -0
  88. /package/dist/{useQuilttSettings-12s--rCJoNHD.js → components/useQuilttSettings-12s--rCJoNHD.js} +0 -0
  89. /package/dist/{useScript-12s-JCgaTW9n.js → components/useScript-12s-JCgaTW9n.js} +0 -0
  90. /package/dist/{useEventListener-12s-D_-6QIXa.js → hooks/useEventListener-12s-D_-6QIXa.js} +0 -0
  91. /package/dist/{useIsomorphicLayoutEffect-12s-DeTHOKz1.js → hooks/useIsomorphicLayoutEffect-12s-DeTHOKz1.js} +0 -0
@@ -42,13 +42,39 @@ export const useSession = (storageKey = 'session'): [Maybe<QuilttJWT> | undefine
42
42
  const expirationMS = session.claims.exp * 1000
43
43
  const expire = () => setToken(null)
44
44
 
45
+ const checkExpiration = () => {
46
+ if (Date.now() >= expirationMS) {
47
+ expire()
48
+ return true
49
+ }
50
+ return false
51
+ }
52
+
45
53
  // Clear immediately if already expired
46
- if (Date.now() >= expirationMS) {
47
- expire()
48
- } else {
49
- // Set timer to clear session at expiration time
50
- sessionTimer.set(expire, expirationMS - Date.now())
51
- return () => sessionTimer.clear(expire)
54
+ if (checkExpiration()) {
55
+ return
56
+ }
57
+
58
+ // Set timer to clear session at expiration time
59
+ sessionTimer.set(expire, expirationMS - Date.now())
60
+
61
+ // Also check expiration when tab becomes visible (handles idle sessions)
62
+ const handleVisibilityChange = () => {
63
+ if (!document.hidden) {
64
+ checkExpiration()
65
+ }
66
+ }
67
+
68
+ // Only add listener in browser environment
69
+ if (typeof document !== 'undefined') {
70
+ document.addEventListener('visibilitychange', handleVisibilityChange)
71
+ }
72
+
73
+ return () => {
74
+ sessionTimer.clear(expire)
75
+ if (typeof document !== 'undefined') {
76
+ document.removeEventListener('visibilitychange', handleVisibilityChange)
77
+ }
52
78
  }
53
79
  }, [session, setToken])
54
80
 
@@ -52,23 +52,15 @@ export const useStorage = <T>(
52
52
  )
53
53
 
54
54
  useEffect(() => {
55
- // Subscribe to storage changes and ensure state is synchronized
56
- // Reruns when key or state changes to maintain consistency
57
- GlobalStorage.subscribe(key, (newValue) => {
58
- // Only update if the value is different from current state
59
- if (newValue !== hookState) {
60
- setHookState(newValue)
61
- }
62
- })
63
-
64
- // Initial sync
65
- const initialValue = getStorage()
66
- if (initialValue !== hookState) {
67
- setHookState(initialValue)
55
+ // Subscribe to storage changes from other sources (e.g., other hook instances, browser tabs)
56
+ const handleStorageChange = (newValue: Maybe<T> | undefined) => {
57
+ setHookState(newValue)
68
58
  }
69
59
 
70
- return () => GlobalStorage.unsubscribe(key, setHookState)
71
- }, [key, hookState, getStorage])
60
+ GlobalStorage.subscribe(key, handleStorageChange)
61
+
62
+ return () => GlobalStorage.unsubscribe(key, handleStorageChange)
63
+ }, [key])
72
64
 
73
65
  return [hookState, setStorage]
74
66
  }
package/src/index.ts CHANGED
@@ -1,3 +1,64 @@
1
+ // ============================================================================
2
+ // Core Module - Apollo Client core functionality
3
+ // ============================================================================
4
+ export type {
5
+ ApolloQueryResult,
6
+ DocumentNode,
7
+ ErrorPolicy,
8
+ FetchPolicy,
9
+ NormalizedCacheObject,
10
+ OperationVariables,
11
+ TypedDocumentNode,
12
+ WatchQueryFetchPolicy,
13
+ } from '@apollo/client'
14
+ export {
15
+ ApolloClient,
16
+ gql,
17
+ InMemoryCache,
18
+ NetworkStatus,
19
+ ObservableQuery,
20
+ } from '@apollo/client'
21
+ // ============================================================================
22
+ // Errors Module - Error handling utilities
23
+ // ============================================================================
24
+ export {
25
+ CombinedGraphQLErrors,
26
+ CombinedProtocolErrors,
27
+ LinkError,
28
+ LocalStateError,
29
+ ServerError,
30
+ ServerParseError,
31
+ UnconventionalError,
32
+ } from '@apollo/client/errors'
33
+ // ============================================================================
34
+ // React Module - React hooks and components
35
+ // ============================================================================
36
+ export type {
37
+ MutationHookOptions,
38
+ MutationResult,
39
+ QueryHookOptions,
40
+ QueryResult,
41
+ SubscriptionHookOptions,
42
+ SubscriptionResult,
43
+ } from '@apollo/client/react'
44
+ export {
45
+ ApolloProvider,
46
+ createQueryPreloader,
47
+ skipToken,
48
+ useApolloClient,
49
+ useBackgroundQuery,
50
+ useFragment,
51
+ useLazyQuery,
52
+ useLoadableQuery,
53
+ useMutation,
54
+ useQuery,
55
+ useQueryRefHandlers,
56
+ useReactiveVar,
57
+ useReadQuery,
58
+ useSubscription,
59
+ useSuspenseQuery,
60
+ } from '@apollo/client/react'
61
+ export { MockedProvider } from '@apollo/client/testing/react'
1
62
  export * from '@quiltt/core'
2
63
 
3
64
  export * from './components'
@@ -3,11 +3,11 @@
3
3
  import type { FC, PropsWithChildren } from 'react'
4
4
  import { useEffect, useMemo, useRef } from 'react'
5
5
 
6
- import { ApolloProvider } from '@apollo/client/react/context/ApolloProvider.js'
7
- import { InMemoryCache, QuilttClient } from '@quiltt/core'
6
+ import { ApolloProvider } from '@apollo/client/react'
7
+ import { createVersionLink, InMemoryCache, QuilttClient } from '@quiltt/core'
8
8
 
9
9
  import { useQuilttSession } from '@/hooks'
10
- import { isDeepEqual } from '@/utils'
10
+ import { getPlatformInfo, isDeepEqual } from '@/utils'
11
11
 
12
12
  export type QuilttAuthProviderProps = PropsWithChildren & {
13
13
  /** A custom QuilttClient instance to use instead of the default */
@@ -30,6 +30,12 @@ export const QuilttAuthProvider: FC<QuilttAuthProviderProps> = ({
30
30
  const { session, importSession } = useQuilttSession()
31
31
  const previousSessionRef = useRef(session)
32
32
  const previousTokenRef = useRef<string | undefined>(undefined)
33
+ const importSessionRef = useRef(importSession)
34
+
35
+ // Keep importSession ref up to date
36
+ useEffect(() => {
37
+ importSessionRef.current = importSession
38
+ }, [importSession])
33
39
 
34
40
  // Memoize the client to avoid unnecessary re-renders
35
41
  const apolloClient = useMemo(
@@ -37,6 +43,7 @@ export const QuilttAuthProvider: FC<QuilttAuthProviderProps> = ({
37
43
  graphqlClient ||
38
44
  new QuilttClient({
39
45
  cache: new InMemoryCache(),
46
+ versionLink: createVersionLink(getPlatformInfo()),
40
47
  }),
41
48
  [graphqlClient]
42
49
  )
@@ -44,13 +51,13 @@ export const QuilttAuthProvider: FC<QuilttAuthProviderProps> = ({
44
51
  // Import passed in token (only if value has changed)
45
52
  useEffect(() => {
46
53
  if (token && token !== previousTokenRef.current) {
47
- importSession(token)
54
+ importSessionRef.current(token)
48
55
  previousTokenRef.current = token
49
56
  } else if (!token) {
50
57
  // Reset ref when token becomes undefined to allow re-import of same token later
51
58
  previousTokenRef.current = undefined
52
59
  }
53
- }, [token, importSession])
60
+ }, [token])
54
61
 
55
62
  // Reset Client Store when session changes (using deep comparison)
56
63
  useEffect(() => {
@@ -1,4 +1,5 @@
1
1
  import type { FC } from 'react'
2
+ import { useMemo } from 'react'
2
3
 
3
4
  import { QuilttProviderRender } from '@/contexts/QuilttProviderRender'
4
5
 
@@ -20,8 +21,11 @@ export const QuilttProvider: FC<QuilttProviderProps> = ({
20
21
  // Will produce false positives for valid patterns like: <QuilttProvider><MyPage /></QuilttProvider>
21
22
  // where MyPage renders SDK components (which is correct usage).
22
23
  // The flag-based approach is simple but imprecise - a proper solution would require render stack tracking.
24
+ // Memoize context value to prevent unnecessary re-renders
25
+ const renderContextValue = useMemo(() => ({ isRenderingProvider: true }), [])
26
+
23
27
  return (
24
- <QuilttProviderRender.Provider value={{ isRenderingProvider: true }}>
28
+ <QuilttProviderRender.Provider value={renderContextValue}>
25
29
  <QuilttSettingsProvider clientId={clientId}>
26
30
  <QuilttAuthProvider token={token} graphqlClient={graphqlClient}>
27
31
  {children}
@@ -1,7 +1,7 @@
1
1
  'use client'
2
2
 
3
3
  import type { FC, PropsWithChildren } from 'react'
4
- import { useState } from 'react'
4
+ import { useMemo } from 'react'
5
5
 
6
6
  import { QuilttSettings } from '@/contexts/QuilttSettings'
7
7
 
@@ -11,11 +11,10 @@ export type QuilttSettingsProviderProps = PropsWithChildren & {
11
11
  }
12
12
 
13
13
  export const QuilttSettingsProvider: FC<QuilttSettingsProviderProps> = ({ clientId, children }) => {
14
- const [_clientId] = useState(clientId)
14
+ // Memoize context value to prevent unnecessary re-renders
15
+ const contextValue = useMemo(() => ({ clientId }), [clientId])
15
16
 
16
- return (
17
- <QuilttSettings.Provider value={{ clientId: _clientId }}>{children}</QuilttSettings.Provider>
18
- )
17
+ return <QuilttSettings.Provider value={contextValue}>{children}</QuilttSettings.Provider>
19
18
  }
20
19
 
21
20
  export default QuilttSettingsProvider
@@ -1 +1,2 @@
1
1
  export * from './isDeepEqual'
2
+ export * from './telemetry'
@@ -0,0 +1,33 @@
1
+ import React from 'react'
2
+
3
+ import { getUserAgent as coreGetUserAgent, getBrowserInfo } from '@quiltt/core'
4
+
5
+ // Re-export getBrowserInfo
6
+ export { getBrowserInfo }
7
+
8
+ /**
9
+ * Gets the React version from the runtime
10
+ */
11
+ export const getReactVersion = (): string => {
12
+ return React.version || 'unknown'
13
+ }
14
+
15
+ /**
16
+ * Generates platform information string for React web
17
+ * Format: React/<version>; <browser>/<version>
18
+ */
19
+ export const getPlatformInfo = (): string => {
20
+ const reactVersion = getReactVersion()
21
+ const browserInfo = getBrowserInfo()
22
+
23
+ return `React/${reactVersion}; ${browserInfo}`
24
+ }
25
+
26
+ /**
27
+ * Generates User-Agent string for React SDK
28
+ * Format: Quiltt/<sdk-version> (React/<react-version>; <browser>/<version>)
29
+ */
30
+ export const getUserAgent = (sdkVersion: string): string => {
31
+ const platformInfo = getPlatformInfo()
32
+ return coreGetUserAgent(sdkVersion, platformInfo)
33
+ }
@@ -1,205 +0,0 @@
1
- 'use client';
2
- import { useCallback, useRef, useMemo, useEffect } from 'react';
3
- import { JsonWebTokenParse, QuilttClient, InMemoryCache } from '@quiltt/core';
4
- import '@apollo/client/react/hooks/useApolloClient.js';
5
- import './QuilttSettings-12s-BK-0SQME.js';
6
- import './useSession-12s-7GOn4sUn.js';
7
- import 'use-debounce';
8
- import './QuilttProviderRender-12s-DtQtubjL.js';
9
- import { jsx } from 'react/jsx-runtime';
10
- import { ApolloProvider } from '@apollo/client/react/context/ApolloProvider.js';
11
- import { u as useQuilttSession } from './useQuilttSession-12s-sRvULtJv.js';
12
-
13
- const useAuthenticateSession = (auth, setSession)=>{
14
- const authenticateSession = useCallback(async (payload, callbacks)=>{
15
- const response = await auth.authenticate(payload);
16
- switch(response.status){
17
- case 201:
18
- setSession(response.data.token);
19
- if (callbacks.onSuccess) return callbacks.onSuccess();
20
- break;
21
- case 401:
22
- if (callbacks.onFailure) return callbacks.onFailure();
23
- break;
24
- case 422:
25
- if (callbacks.onError) return callbacks.onError(response.data);
26
- break;
27
- default:
28
- throw new Error(`AuthAPI.authenticate: Unexpected response status ${response.status}`);
29
- }
30
- }, [
31
- auth,
32
- setSession
33
- ]);
34
- return authenticateSession;
35
- };
36
-
37
- const useIdentifySession = (auth, setSession)=>{
38
- const identifySession = useCallback(async (payload, callbacks)=>{
39
- const response = await auth.identify(payload);
40
- switch(response.status){
41
- case 201:
42
- setSession(response.data.token);
43
- if (callbacks.onSuccess) return callbacks.onSuccess();
44
- break;
45
- case 202:
46
- if (callbacks.onChallenged) return callbacks.onChallenged();
47
- break;
48
- case 403:
49
- if (callbacks.onForbidden) return callbacks.onForbidden();
50
- break;
51
- case 422:
52
- if (callbacks.onError) return callbacks.onError(response.data);
53
- break;
54
- default:
55
- throw new Error(`AuthAPI.identify: Unexpected response status ${response.status}`);
56
- }
57
- }, [
58
- auth,
59
- setSession
60
- ]);
61
- return identifySession;
62
- };
63
-
64
- /**
65
- * Optionally Accepts environmentId to validate session is from with your desired environment
66
- */ const useImportSession = (auth, session, setSession, environmentId)=>{
67
- const importSession = useCallback(async (token)=>{
68
- // Is there a token?
69
- if (!token) return !!session;
70
- // Is this token already imported?
71
- if (session && session.token === token) return true;
72
- const jwt = JsonWebTokenParse(token);
73
- // Is this token a valid JWT?
74
- if (!jwt) return false;
75
- // Is this token within the expected environment?
76
- if (environmentId && jwt.claims.eid !== environmentId) return false;
77
- // Is this token active?
78
- const response = await auth.ping(token);
79
- switch(response.status){
80
- case 200:
81
- setSession(token);
82
- return true;
83
- case 401:
84
- return false;
85
- default:
86
- throw new Error(`AuthAPI.ping: Unexpected response status ${response.status}`);
87
- }
88
- }, [
89
- auth,
90
- session,
91
- setSession,
92
- environmentId
93
- ]);
94
- return importSession;
95
- };
96
-
97
- const useRevokeSession = (auth, session, setSession)=>{
98
- const revokeSession = useCallback(async ()=>{
99
- if (!session) return;
100
- await auth.revoke(session.token);
101
- setSession(null);
102
- }, [
103
- auth,
104
- session,
105
- setSession
106
- ]);
107
- return revokeSession;
108
- };
109
-
110
- /**
111
- * Performs a deep equality comparison between two values
112
- *
113
- * This function recursively compares all properties to determine if they are equal.
114
- *
115
- * @example
116
- * ```ts
117
- * isDeepEqual({ a: 1, b: { c: 2 } }, { a: 1, b: { c: 2 } }) // true
118
- * isDeepEqual({ a: 1, b: { c: 2 } }, { a: 1, b: { c: 3 } }) // false
119
- * ```
120
- */ const isDeepEqual = (obj1, obj2)=>{
121
- // Handle primitive types and null/undefined
122
- if (obj1 === obj2) return true;
123
- if (obj1 === null || obj2 === null || typeof obj1 !== 'object' || typeof obj2 !== 'object') return false;
124
- // Handle special object types
125
- if (obj1 instanceof Date && obj2 instanceof Date) {
126
- return obj1.getTime() === obj2.getTime();
127
- }
128
- if (obj1 instanceof RegExp && obj2 instanceof RegExp) {
129
- return obj1.toString() === obj2.toString();
130
- }
131
- if (obj1 instanceof Map && obj2 instanceof Map) {
132
- if (obj1.size !== obj2.size) return false;
133
- for (const [key, value] of obj1){
134
- if (!obj2.has(key) || !isDeepEqual(value, obj2.get(key))) return false;
135
- }
136
- return true;
137
- }
138
- if (obj1 instanceof Set && obj2 instanceof Set) {
139
- if (obj1.size !== obj2.size) return false;
140
- const arr2 = Array.from(obj2);
141
- for (const item of obj1){
142
- if (!arr2.some((value)=>isDeepEqual(item, value))) return false;
143
- }
144
- return true;
145
- }
146
- // Handle arrays
147
- if (Array.isArray(obj1) && Array.isArray(obj2)) {
148
- if (obj1.length !== obj2.length) return false;
149
- return obj1.every((value, index)=>isDeepEqual(value, obj2[index]));
150
- }
151
- // If one is array and other isn't, they're not equal
152
- if (Array.isArray(obj1) || Array.isArray(obj2)) return false;
153
- const keys1 = Object.keys(obj1);
154
- const keys2 = Object.keys(obj2);
155
- if (keys1.length !== keys2.length) return false;
156
- return keys1.every((key)=>{
157
- return Object.hasOwn(obj2, key) && isDeepEqual(obj1[key], obj2[key]);
158
- });
159
- };
160
-
161
- /**
162
- * If a token is provided, will validate the token against the api and then import
163
- * it into trusted storage. While this process is happening, the component is put
164
- * into a loading state and the children are not rendered to prevent race conditions
165
- * from triggering within the transitionary state.
166
- */ const QuilttAuthProvider = ({ graphqlClient, token, children })=>{
167
- const { session, importSession } = useQuilttSession();
168
- const previousSessionRef = useRef(session);
169
- const previousTokenRef = useRef(undefined);
170
- // Memoize the client to avoid unnecessary re-renders
171
- const apolloClient = useMemo(()=>graphqlClient || new QuilttClient({
172
- cache: new InMemoryCache()
173
- }), [
174
- graphqlClient
175
- ]);
176
- // Import passed in token (only if value has changed)
177
- useEffect(()=>{
178
- if (token && token !== previousTokenRef.current) {
179
- importSession(token);
180
- previousTokenRef.current = token;
181
- } else if (!token) {
182
- // Reset ref when token becomes undefined to allow re-import of same token later
183
- previousTokenRef.current = undefined;
184
- }
185
- }, [
186
- token,
187
- importSession
188
- ]);
189
- // Reset Client Store when session changes (using deep comparison)
190
- useEffect(()=>{
191
- if (!isDeepEqual(session, previousSessionRef.current)) {
192
- apolloClient.resetStore();
193
- previousSessionRef.current = session;
194
- }
195
- }, [
196
- session,
197
- apolloClient
198
- ]);
199
- return /*#__PURE__*/ jsx(ApolloProvider, {
200
- client: apolloClient,
201
- children: children
202
- });
203
- };
204
-
205
- export { QuilttAuthProvider as Q, useIdentifySession as a, useAuthenticateSession as b, useRevokeSession as c, isDeepEqual as i, useImportSession as u };
@@ -1,39 +0,0 @@
1
- 'use client';
2
- import { useMemo, useCallback } from 'react';
3
- import { AuthAPI } from '@quiltt/core';
4
- import { u as useImportSession, a as useIdentifySession, b as useAuthenticateSession, c as useRevokeSession } from './QuilttAuthProvider-12s-DE-ePRo_.js';
5
- import { u as useQuilttSettings } from './useQuilttSettings-12s--rCJoNHD.js';
6
- import { u as useSession } from './useSession-12s-7GOn4sUn.js';
7
-
8
- const useQuilttSession = (environmentId)=>{
9
- const { clientId } = useQuilttSettings();
10
- const [session, setSession] = useSession();
11
- const auth = useMemo(()=>new AuthAPI(clientId), [
12
- clientId
13
- ]);
14
- const importSession = useImportSession(auth, session, setSession, environmentId);
15
- const identifySession = useIdentifySession(auth, setSession);
16
- const authenticateSession = useAuthenticateSession(auth, setSession);
17
- const revokeSession = useRevokeSession(auth, session, setSession);
18
- /**
19
- * Forget current session.
20
- * @param token specific token to forget, to help guard against async processes clearing the wrong session
21
- */ const forgetSession = useCallback(async (token)=>{
22
- if (!token || session && token && token === session.token) {
23
- setSession(null);
24
- }
25
- }, [
26
- session,
27
- setSession
28
- ]);
29
- return {
30
- session,
31
- importSession,
32
- identifySession,
33
- authenticateSession,
34
- revokeSession,
35
- forgetSession
36
- };
37
- };
38
-
39
- export { useQuilttSession as u };