1- import React , {
2- createContext ,
3- FC ,
4- useCallback ,
5- useContext ,
6- useEffect ,
7- useMemo ,
8- useRef ,
9- useState ,
10- } from 'react' ;
11- import Emitter from './utils/emitter' ;
12- const events = new Emitter ( ) ;
1+ import React , { createContext , FC , useCallback , useContext , useEffect , useMemo , useRef , useState } from 'react'
2+ import Emitter from './utils/emitter'
3+ const events = new Emitter ( )
134
145import { IFlagsmith , IFlagsmithTrait , IFlagsmithFeature , IState } from './types'
156
16- export const FlagsmithContext = createContext < IFlagsmith < string , string > | null > ( null )
7+ export const FlagsmithContext = createContext < IFlagsmith < string , string > | null > ( null )
178export type FlagsmithContextType = {
189 flagsmith : IFlagsmith // The flagsmith instance
1910 options ?: Parameters < IFlagsmith [ 'init' ] > [ 0 ] // Initialisation options, if you do not provide this you will have to call init manually
2011 serverState ?: IState
21- children : React . ReactNode ;
12+ children : React . ReactNode
2213}
2314
24- export const FlagsmithProvider : FC < FlagsmithContextType > = ( {
25- flagsmith, options, serverState, children,
26- } ) => {
15+ export const FlagsmithProvider : FC < FlagsmithContextType > = ( { flagsmith, options, serverState, children } ) => {
2716 const firstRenderRef = useRef ( true )
2817 if ( flagsmith && ! flagsmith ?. _trigger ) {
2918 flagsmith . _trigger = ( ) => {
3019 // @ts -expect-error using internal function, consumers would never call this
31- flagsmith . log ( " React - trigger event received" )
32- events . emit ( 'event' ) ;
20+ flagsmith ? .log ( ' React - trigger event received' )
21+ events . emit ( 'event' )
3322 }
3423 }
3524
3625 if ( flagsmith && ! flagsmith ?. _triggerLoadingState ) {
3726 flagsmith . _triggerLoadingState = ( ) => {
38- events . emit ( 'loading_event' ) ;
27+ events . emit ( 'loading_event' )
3928 }
4029 }
4130
@@ -46,22 +35,24 @@ export const FlagsmithProvider: FC<FlagsmithContextType> = ({
4635 if ( firstRenderRef . current ) {
4736 firstRenderRef . current = false
4837 if ( options ) {
49- flagsmith . init ( {
50- ...options ,
51- state : options . state || serverState ,
52- onChange : ( ...args ) => {
53- if ( options . onChange ) {
54- options . onChange ( ...args )
55- }
56- } ,
57- } )
38+ flagsmith
39+ . init ( {
40+ ...options ,
41+ state : options . state || serverState ,
42+ onChange : ( ...args ) => {
43+ if ( options . onChange ) {
44+ options . onChange ( ...args )
45+ }
46+ } ,
47+ } )
48+ . catch ( ( error ) => {
49+ // @ts -expect-error using internal function, consumers would never call this
50+ flagsmith ?. log ( 'React - Failed to initialize flagsmith' , error )
51+ events . emit ( 'event' )
52+ } )
5853 }
5954 }
60- return (
61- < FlagsmithContext . Provider value = { flagsmith } >
62- { children }
63- </ FlagsmithContext . Provider >
64- )
55+ return < FlagsmithContext . Provider value = { flagsmith } > { children } </ FlagsmithContext . Provider >
6556}
6657
6758const useConstant = function < T > ( value : T ) : T {
@@ -72,7 +63,6 @@ const useConstant = function <T>(value: T): T {
7263 return ref . current
7364}
7465
75-
7666const flagsAsArray = ( _flags : any ) : string [ ] => {
7767 if ( typeof _flags === 'string' ) {
7868 return [ _flags ]
@@ -82,29 +72,26 @@ const flagsAsArray = (_flags: any): string[] => {
8272 return _flags
8373 }
8474 }
85- throw new Error (
86- 'Flagsmith: please supply an array of strings or a single string of flag keys to useFlags' ,
87- )
75+ throw new Error ( 'Flagsmith: please supply an array of strings or a single string of flag keys to useFlags' )
8876}
8977
9078const getRenderKey = ( flagsmith : IFlagsmith , flags : string [ ] , traits : string [ ] = [ ] ) => {
9179 return flags
9280 . map ( ( k ) => {
9381 return `${ flagsmith . getValue ( k ) } ${ flagsmith . hasFeature ( k ) } `
94- } ) . concat ( traits . map ( ( t ) => (
95- `${ flagsmith . getTrait ( t ) } `
96- ) ) )
82+ } )
83+ . concat ( traits . map ( ( t ) => `${ flagsmith . getTrait ( t ) } ` ) )
9784 . join ( ',' )
9885}
9986
10087export function useFlagsmithLoading ( ) {
101- const flagsmith = useContext ( FlagsmithContext ) ;
102- const [ loadingState , setLoadingState ] = useState ( flagsmith ?. loadingState ) ;
103- const [ subscribed , setSubscribed ] = useState ( false ) ;
88+ const flagsmith = useContext ( FlagsmithContext )
89+ const [ loadingState , setLoadingState ] = useState ( flagsmith ?. loadingState )
90+ const [ subscribed , setSubscribed ] = useState ( false )
10491 const refSubscribed = useRef ( subscribed )
10592
10693 const eventListener = useCallback ( ( ) => {
107- setLoadingState ( flagsmith ?. loadingState ) ;
94+ setLoadingState ( flagsmith ?. loadingState )
10895 } , [ flagsmith ] )
10996 if ( ! refSubscribed . current ) {
11097 events . on ( 'loading_event' , eventListener )
@@ -120,26 +107,23 @@ export function useFlagsmithLoading() {
120107 if ( subscribed ) {
121108 events . off ( 'loading_event' , eventListener )
122109 }
123- } ;
110+ }
124111 } , [ flagsmith , subscribed , eventListener ] )
125112
126113 return loadingState
127114}
128115
129- type UseFlagsReturn <
130- F extends string | Record < string , any > ,
131- T extends string
132- > = [ F ] extends [ string ]
116+ type UseFlagsReturn < F extends string | Record < string , any > , T extends string > = F extends string
133117 ? {
134- [ K in F ] : IFlagsmithFeature ;
135- } & {
136- [ K in T ] : IFlagsmithTrait ;
137- }
118+ [ K in F ] : IFlagsmithFeature
119+ } & {
120+ [ K in T ] : IFlagsmithTrait
121+ }
138122 : {
139- [ K in keyof F ] : IFlagsmithFeature < F [ K ] > ;
140- } & {
141- [ K in T ] : IFlagsmithTrait ;
142- } ;
123+ [ K in keyof F ] : IFlagsmithFeature < F [ K ] >
124+ } & {
125+ [ K in T ] : IFlagsmithTrait
126+ }
143127
144128/**
145129 * Example usage:
@@ -154,61 +138,58 @@ type UseFlagsReturn<
154138 * }
155139 * useFlags<MyFeatureInterface>(["featureOne", "featureTwo"]);
156140 */
157- export function useFlags <
158- F extends string | Record < string , any > ,
159- T extends string = string
160- > (
161- _flags : readonly ( F | keyof F ) [ ] , _traits : readonly T [ ] = [ ]
162- ) {
141+ export function useFlags < F extends string | Record < string , any > , T extends string = string > (
142+ _flags : readonly ( F | keyof F ) [ ] ,
143+ _traits : readonly T [ ] = [ ]
144+ ) {
163145 const firstRender = useRef ( true )
164146 const flags = useConstant < string [ ] > ( flagsAsArray ( _flags ) )
165147 const traits = useConstant < string [ ] > ( flagsAsArray ( _traits ) )
166148 const flagsmith = useContext ( FlagsmithContext )
167- const [ renderRef , setRenderRef ] = useState ( getRenderKey ( flagsmith as IFlagsmith , flags , traits ) ) ;
149+ const [ renderRef , setRenderRef ] = useState ( getRenderKey ( flagsmith as IFlagsmith , flags , traits ) )
168150 const eventListener = useCallback ( ( ) => {
169151 const newRenderKey = getRenderKey ( flagsmith as IFlagsmith , flags , traits )
170152 if ( newRenderKey !== renderRef ) {
171153 // @ts -expect-error using internal function, consumers would never call this
172- flagsmith ?. log ( " React - useFlags flags and traits have changed" )
154+ flagsmith ?. log ( ' React - useFlags flags and traits have changed' )
173155 setRenderRef ( newRenderKey )
174156 }
175157 } , [ renderRef ] )
176- const emitterRef = useRef ( events . once ( 'event' , eventListener ) ) ;
177-
178-
158+ const emitterRef = useRef ( events . once ( 'event' , eventListener ) )
179159
180160 if ( firstRender . current ) {
181- firstRender . current = false ;
161+ firstRender . current = false
182162 // @ts -expect-error using internal function, consumers would never call this
183- flagsmith ?. log ( " React - Initialising event listeners" )
163+ flagsmith ?. log ( ' React - Initialising event listeners' )
184164 }
185165
186- useEffect ( ( ) => {
166+ useEffect ( ( ) => {
187167 return ( ) => {
188168 emitterRef . current ?.( )
189169 }
190170 } , [ ] )
191171
192172 const res = useMemo ( ( ) => {
193173 const res : any = { }
194- flags . map ( ( k ) => {
174+ flags
175+ . map ( ( k ) => {
195176 res [ k ] = {
196177 enabled : flagsmith ! . hasFeature ( k ) ,
197178 value : flagsmith ! . getValue ( k ) ,
198179 }
199- } ) . concat ( traits ?. map ( ( v ) => {
180+ } )
181+ . concat (
182+ traits ?. map ( ( v ) => {
200183 res [ v ] = flagsmith ! . getTrait ( v )
201- } ) )
184+ } )
185+ )
202186 return res
203187 } , [ renderRef ] )
204188
205189 return res as UseFlagsReturn < F , T >
206190}
207191
208- export function useFlagsmith <
209- F extends string | Record < string , any > ,
210- T extends string = string
211- > ( ) {
192+ export function useFlagsmith < F extends string | Record < string , any > , T extends string = string > ( ) {
212193 const context = useContext ( FlagsmithContext )
213194
214195 if ( ! context ) {
0 commit comments