@supabase/gotrue-js 1.22.13 → 1.22.14
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/main/GoTrueClient.d.ts +3 -8
- package/dist/main/GoTrueClient.d.ts.map +1 -1
- package/dist/main/GoTrueClient.js +46 -17
- package/dist/main/GoTrueClient.js.map +1 -1
- package/dist/main/lib/constants.d.ts +6 -1
- package/dist/main/lib/constants.d.ts.map +1 -1
- package/dist/main/lib/constants.js +7 -2
- package/dist/main/lib/constants.js.map +1 -1
- package/dist/main/lib/fetch.d.ts.map +1 -1
- package/dist/main/lib/fetch.js +4 -0
- package/dist/main/lib/fetch.js.map +1 -1
- package/dist/main/lib/helpers.d.ts +5 -0
- package/dist/main/lib/helpers.d.ts.map +1 -1
- package/dist/main/lib/helpers.js +44 -1
- package/dist/main/lib/helpers.js.map +1 -1
- package/dist/main/lib/types.d.ts +7 -0
- package/dist/main/lib/types.d.ts.map +1 -1
- package/dist/main/lib/version.d.ts +1 -1
- package/dist/main/lib/version.js +1 -1
- package/dist/module/GoTrueClient.d.ts +3 -8
- package/dist/module/GoTrueClient.d.ts.map +1 -1
- package/dist/module/GoTrueClient.js +48 -19
- package/dist/module/GoTrueClient.js.map +1 -1
- package/dist/module/lib/constants.d.ts +6 -1
- package/dist/module/lib/constants.d.ts.map +1 -1
- package/dist/module/lib/constants.js +6 -1
- package/dist/module/lib/constants.js.map +1 -1
- package/dist/module/lib/fetch.d.ts.map +1 -1
- package/dist/module/lib/fetch.js +4 -0
- package/dist/module/lib/fetch.js.map +1 -1
- package/dist/module/lib/helpers.d.ts +5 -0
- package/dist/module/lib/helpers.d.ts.map +1 -1
- package/dist/module/lib/helpers.js +39 -0
- package/dist/module/lib/helpers.js.map +1 -1
- package/dist/module/lib/types.d.ts +7 -0
- package/dist/module/lib/types.d.ts.map +1 -1
- package/dist/module/lib/version.d.ts +1 -1
- package/dist/module/lib/version.js +1 -1
- package/package.json +1 -1
- package/src/GoTrueClient.ts +68 -33
- package/src/lib/constants.ts +6 -1
- package/src/lib/fetch.ts +5 -0
- package/src/lib/helpers.ts +36 -0
- package/src/lib/types.ts +11 -0
- package/src/lib/version.ts +1 -1
package/src/GoTrueClient.ts
CHANGED
|
@@ -1,6 +1,20 @@
|
|
|
1
1
|
import GoTrueApi from './GoTrueApi'
|
|
2
|
-
import {
|
|
3
|
-
|
|
2
|
+
import {
|
|
3
|
+
isBrowser,
|
|
4
|
+
getParameterByName,
|
|
5
|
+
uuid,
|
|
6
|
+
setItemAsync,
|
|
7
|
+
removeItemAsync,
|
|
8
|
+
getItemSynchronously,
|
|
9
|
+
getItemAsync,
|
|
10
|
+
} from './lib/helpers'
|
|
11
|
+
import {
|
|
12
|
+
GOTRUE_URL,
|
|
13
|
+
DEFAULT_HEADERS,
|
|
14
|
+
STORAGE_KEY,
|
|
15
|
+
EXPIRY_MARGIN,
|
|
16
|
+
NETWORK_FAILURE,
|
|
17
|
+
} from './lib/constants'
|
|
4
18
|
import { polyfillGlobalThis } from './lib/polyfills'
|
|
5
19
|
import { Fetch } from './lib/fetch'
|
|
6
20
|
|
|
@@ -16,6 +30,7 @@ import type {
|
|
|
16
30
|
UserCredentials,
|
|
17
31
|
VerifyOTPParams,
|
|
18
32
|
OpenIDConnectCredentials,
|
|
33
|
+
SupportedStorage,
|
|
19
34
|
} from './lib/types'
|
|
20
35
|
|
|
21
36
|
polyfillGlobalThis() // Make "globalThis" available
|
|
@@ -29,17 +44,6 @@ const DEFAULT_OPTIONS = {
|
|
|
29
44
|
headers: DEFAULT_HEADERS,
|
|
30
45
|
}
|
|
31
46
|
|
|
32
|
-
type AnyFunction = (...args: any[]) => any
|
|
33
|
-
type MaybePromisify<T> = T | Promise<T>
|
|
34
|
-
|
|
35
|
-
type PromisifyMethods<T> = {
|
|
36
|
-
[K in keyof T]: T[K] extends AnyFunction
|
|
37
|
-
? (...args: Parameters<T[K]>) => MaybePromisify<ReturnType<T[K]>>
|
|
38
|
-
: T[K]
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
type SupportedStorage = PromisifyMethods<Pick<Storage, 'getItem' | 'setItem' | 'removeItem'>>
|
|
42
|
-
|
|
43
47
|
export default class GoTrueClient {
|
|
44
48
|
/**
|
|
45
49
|
* Namespace for the GoTrue API methods.
|
|
@@ -61,6 +65,7 @@ export default class GoTrueClient {
|
|
|
61
65
|
protected multiTab: boolean
|
|
62
66
|
protected stateChangeEmitters: Map<string, Subscription> = new Map()
|
|
63
67
|
protected refreshTokenTimer?: ReturnType<typeof setTimeout>
|
|
68
|
+
protected networkRetries: number = 0
|
|
64
69
|
|
|
65
70
|
/**
|
|
66
71
|
* Create a new client for use in the browser.
|
|
@@ -101,6 +106,7 @@ export default class GoTrueClient {
|
|
|
101
106
|
this._recoverSession()
|
|
102
107
|
this._recoverAndRefresh()
|
|
103
108
|
this._listenForMultiTabEvents()
|
|
109
|
+
this._handleVisibilityChange()
|
|
104
110
|
|
|
105
111
|
if (settings.detectSessionInUrl && isBrowser() && !!getParameterByName('access_token')) {
|
|
106
112
|
// Handle the OAuth redirect
|
|
@@ -610,16 +616,12 @@ export default class GoTrueClient {
|
|
|
610
616
|
*/
|
|
611
617
|
private _recoverSession() {
|
|
612
618
|
try {
|
|
613
|
-
const
|
|
614
|
-
if (!
|
|
615
|
-
return null
|
|
616
|
-
}
|
|
617
|
-
|
|
618
|
-
const data = JSON.parse(json)
|
|
619
|
+
const data = getItemSynchronously(this.localStorage, STORAGE_KEY)
|
|
620
|
+
if (!data) return null
|
|
619
621
|
const { currentSession, expiresAt } = data
|
|
620
622
|
const timeNow = Math.round(Date.now() / 1000)
|
|
621
623
|
|
|
622
|
-
if (expiresAt >= timeNow && currentSession?.user) {
|
|
624
|
+
if (expiresAt >= timeNow + EXPIRY_MARGIN && currentSession?.user) {
|
|
623
625
|
this._saveSession(currentSession)
|
|
624
626
|
this._notifyAllSubscribers('SIGNED_IN')
|
|
625
627
|
}
|
|
@@ -634,22 +636,31 @@ export default class GoTrueClient {
|
|
|
634
636
|
*/
|
|
635
637
|
private async _recoverAndRefresh() {
|
|
636
638
|
try {
|
|
637
|
-
const
|
|
638
|
-
if (!
|
|
639
|
-
return null
|
|
640
|
-
}
|
|
641
|
-
|
|
642
|
-
const data = JSON.parse(json)
|
|
639
|
+
const data = await getItemAsync(this.localStorage, STORAGE_KEY)
|
|
640
|
+
if (!data) return null
|
|
643
641
|
const { currentSession, expiresAt } = data
|
|
644
642
|
const timeNow = Math.round(Date.now() / 1000)
|
|
645
643
|
|
|
646
|
-
if (expiresAt < timeNow) {
|
|
644
|
+
if (expiresAt < timeNow + EXPIRY_MARGIN) {
|
|
647
645
|
if (this.autoRefreshToken && currentSession.refresh_token) {
|
|
646
|
+
this.networkRetries++
|
|
648
647
|
const { error } = await this._callRefreshToken(currentSession.refresh_token)
|
|
649
648
|
if (error) {
|
|
650
649
|
console.log(error.message)
|
|
650
|
+
if (
|
|
651
|
+
error.message === NETWORK_FAILURE.ERROR_MESSAGE &&
|
|
652
|
+
this.networkRetries < NETWORK_FAILURE.MAX_RETRIES
|
|
653
|
+
) {
|
|
654
|
+
if (this.refreshTokenTimer) clearTimeout(this.refreshTokenTimer)
|
|
655
|
+
this.refreshTokenTimer = setTimeout(
|
|
656
|
+
() => this._recoverAndRefresh(),
|
|
657
|
+
NETWORK_FAILURE.RETRY_INTERVAL ** this.networkRetries * 100 // exponential backoff
|
|
658
|
+
)
|
|
659
|
+
return
|
|
660
|
+
}
|
|
651
661
|
await this._removeSession()
|
|
652
662
|
}
|
|
663
|
+
this.networkRetries = 0
|
|
653
664
|
} else {
|
|
654
665
|
this._removeSession()
|
|
655
666
|
}
|
|
@@ -703,7 +714,7 @@ export default class GoTrueClient {
|
|
|
703
714
|
if (expiresAt) {
|
|
704
715
|
const timeNow = Math.round(Date.now() / 1000)
|
|
705
716
|
const expiresIn = expiresAt - timeNow
|
|
706
|
-
const refreshDurationBeforeExpires = expiresIn >
|
|
717
|
+
const refreshDurationBeforeExpires = expiresIn > EXPIRY_MARGIN ? EXPIRY_MARGIN : 0.5
|
|
707
718
|
this._startAutoRefreshToken((expiresIn - refreshDurationBeforeExpires) * 1000)
|
|
708
719
|
}
|
|
709
720
|
|
|
@@ -716,14 +727,14 @@ export default class GoTrueClient {
|
|
|
716
727
|
|
|
717
728
|
private _persistSession(currentSession: Session) {
|
|
718
729
|
const data = { currentSession, expiresAt: currentSession.expires_at }
|
|
719
|
-
|
|
730
|
+
setItemAsync(this.localStorage, STORAGE_KEY, data)
|
|
720
731
|
}
|
|
721
732
|
|
|
722
733
|
private async _removeSession() {
|
|
723
734
|
this.currentSession = null
|
|
724
735
|
this.currentUser = null
|
|
725
736
|
if (this.refreshTokenTimer) clearTimeout(this.refreshTokenTimer)
|
|
726
|
-
|
|
737
|
+
removeItemAsync(this.localStorage, STORAGE_KEY)
|
|
727
738
|
}
|
|
728
739
|
|
|
729
740
|
/**
|
|
@@ -734,7 +745,16 @@ export default class GoTrueClient {
|
|
|
734
745
|
if (this.refreshTokenTimer) clearTimeout(this.refreshTokenTimer)
|
|
735
746
|
if (value <= 0 || !this.autoRefreshToken) return
|
|
736
747
|
|
|
737
|
-
this.refreshTokenTimer = setTimeout(() =>
|
|
748
|
+
this.refreshTokenTimer = setTimeout(async () => {
|
|
749
|
+
this.networkRetries++
|
|
750
|
+
const { error } = await this._callRefreshToken()
|
|
751
|
+
if (!error) this.networkRetries = 0
|
|
752
|
+
if (
|
|
753
|
+
error?.message === NETWORK_FAILURE.ERROR_MESSAGE &&
|
|
754
|
+
this.networkRetries < NETWORK_FAILURE.MAX_RETRIES
|
|
755
|
+
)
|
|
756
|
+
this._startAutoRefreshToken(NETWORK_FAILURE.RETRY_INTERVAL ** this.networkRetries * 100) // exponential backoff
|
|
757
|
+
}, value)
|
|
738
758
|
if (typeof this.refreshTokenTimer.unref === 'function') this.refreshTokenTimer.unref()
|
|
739
759
|
}
|
|
740
760
|
|
|
@@ -743,7 +763,6 @@ export default class GoTrueClient {
|
|
|
743
763
|
*/
|
|
744
764
|
private _listenForMultiTabEvents() {
|
|
745
765
|
if (!this.multiTab || !isBrowser() || !window?.addEventListener) {
|
|
746
|
-
// console.debug('Auth multi-tab support is disabled.')
|
|
747
766
|
return false
|
|
748
767
|
}
|
|
749
768
|
|
|
@@ -752,7 +771,7 @@ export default class GoTrueClient {
|
|
|
752
771
|
if (e.key === STORAGE_KEY) {
|
|
753
772
|
const newSession = JSON.parse(String(e.newValue))
|
|
754
773
|
if (newSession?.currentSession?.access_token) {
|
|
755
|
-
this.
|
|
774
|
+
this._saveSession(newSession.currentSession)
|
|
756
775
|
this._notifyAllSubscribers('SIGNED_IN')
|
|
757
776
|
} else {
|
|
758
777
|
this._removeSession()
|
|
@@ -764,4 +783,20 @@ export default class GoTrueClient {
|
|
|
764
783
|
console.error('_listenForMultiTabEvents', error)
|
|
765
784
|
}
|
|
766
785
|
}
|
|
786
|
+
|
|
787
|
+
private _handleVisibilityChange() {
|
|
788
|
+
if (!this.multiTab || !isBrowser() || !window?.addEventListener) {
|
|
789
|
+
return false
|
|
790
|
+
}
|
|
791
|
+
|
|
792
|
+
try {
|
|
793
|
+
window?.addEventListener('visibilitychange', () => {
|
|
794
|
+
if (document.visibilityState === 'visible') {
|
|
795
|
+
this._recoverAndRefresh()
|
|
796
|
+
}
|
|
797
|
+
})
|
|
798
|
+
} catch (error) {
|
|
799
|
+
console.error('_handleVisibilityChange', error)
|
|
800
|
+
}
|
|
801
|
+
}
|
|
767
802
|
}
|
package/src/lib/constants.ts
CHANGED
|
@@ -2,7 +2,12 @@ import { version } from './version'
|
|
|
2
2
|
export const GOTRUE_URL = 'http://localhost:9999'
|
|
3
3
|
export const AUDIENCE = ''
|
|
4
4
|
export const DEFAULT_HEADERS = { 'X-Client-Info': `gotrue-js/${version}` }
|
|
5
|
-
export const EXPIRY_MARGIN =
|
|
5
|
+
export const EXPIRY_MARGIN = 10 // in seconds
|
|
6
|
+
export const NETWORK_FAILURE = {
|
|
7
|
+
ERROR_MESSAGE: 'Request Failed',
|
|
8
|
+
MAX_RETRIES: 10,
|
|
9
|
+
RETRY_INTERVAL: 2, // in deciseconds
|
|
10
|
+
}
|
|
6
11
|
export const STORAGE_KEY = 'supabase.auth.token'
|
|
7
12
|
export const COOKIE_OPTIONS = {
|
|
8
13
|
name: 'sb',
|
package/src/lib/fetch.ts
CHANGED
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { NETWORK_FAILURE } from './constants'
|
|
2
|
+
|
|
1
3
|
export type Fetch = typeof fetch
|
|
2
4
|
|
|
3
5
|
export interface FetchOptions {
|
|
@@ -13,6 +15,9 @@ const _getErrorMessage = (err: any): string =>
|
|
|
13
15
|
err.msg || err.message || err.error_description || err.error || JSON.stringify(err)
|
|
14
16
|
|
|
15
17
|
const handleError = (error: any, reject: any) => {
|
|
18
|
+
if (!error?.status) {
|
|
19
|
+
return reject({ message: NETWORK_FAILURE.ERROR_MESSAGE })
|
|
20
|
+
}
|
|
16
21
|
if (typeof error.json !== 'function') {
|
|
17
22
|
return reject(error)
|
|
18
23
|
}
|
package/src/lib/helpers.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import crossFetch from 'cross-fetch'
|
|
2
|
+
import { SupportedStorage } from './types'
|
|
2
3
|
|
|
3
4
|
export function expiresAt(expiresIn: number) {
|
|
4
5
|
const timeNow = Math.round(Date.now() / 1000)
|
|
@@ -39,3 +40,38 @@ export const resolveFetch = (customFetch?: Fetch): Fetch => {
|
|
|
39
40
|
}
|
|
40
41
|
return (...args) => _fetch(...args)
|
|
41
42
|
}
|
|
43
|
+
|
|
44
|
+
// LocalStorage helpers
|
|
45
|
+
export const setItemAsync = async (
|
|
46
|
+
storage: SupportedStorage,
|
|
47
|
+
key: string,
|
|
48
|
+
data: any
|
|
49
|
+
): Promise<void> => {
|
|
50
|
+
isBrowser() && (await storage?.setItem(key, JSON.stringify(data)))
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
export const getItemAsync = async (storage: SupportedStorage, key: string): Promise<any | null> => {
|
|
54
|
+
const value = isBrowser() && (await storage?.getItem(key))
|
|
55
|
+
if (!value) return null
|
|
56
|
+
try {
|
|
57
|
+
return JSON.parse(value)
|
|
58
|
+
} catch {
|
|
59
|
+
return value
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
export const getItemSynchronously = (storage: SupportedStorage, key: string): any | null => {
|
|
64
|
+
const value = isBrowser() && storage?.getItem(key)
|
|
65
|
+
if (!value || typeof value !== 'string') {
|
|
66
|
+
return null
|
|
67
|
+
}
|
|
68
|
+
try {
|
|
69
|
+
return JSON.parse(value)
|
|
70
|
+
} catch {
|
|
71
|
+
return value
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
export const removeItemAsync = async (storage: SupportedStorage, key: string): Promise<void> => {
|
|
76
|
+
isBrowser() && (await storage?.removeItem(key))
|
|
77
|
+
}
|
package/src/lib/types.ts
CHANGED
|
@@ -209,3 +209,14 @@ export interface OpenIDConnectCredentials {
|
|
|
209
209
|
client_id?: string
|
|
210
210
|
issuer?: string
|
|
211
211
|
}
|
|
212
|
+
|
|
213
|
+
type AnyFunction = (...args: any[]) => any
|
|
214
|
+
type MaybePromisify<T> = T | Promise<T>
|
|
215
|
+
|
|
216
|
+
type PromisifyMethods<T> = {
|
|
217
|
+
[K in keyof T]: T[K] extends AnyFunction
|
|
218
|
+
? (...args: Parameters<T[K]>) => MaybePromisify<ReturnType<T[K]>>
|
|
219
|
+
: T[K]
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
export type SupportedStorage = PromisifyMethods<Pick<Storage, 'getItem' | 'setItem' | 'removeItem'>>
|
package/src/lib/version.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
// generated by genversion
|
|
2
|
-
export const version = '1.22.
|
|
2
|
+
export const version = '1.22.14'
|