UNPKG

@livelike/react-native

Version:

LiveLike React Native package

70 lines (63 loc) 2.6 kB
import { useEffect } from 'react'; import { widgetStore } from '../store'; import { WidgetUIPhase } from '../types'; import { useSelectedFieldStore } from './useSelectedFieldStore'; import { useWidgetActions } from './useWidgetActions'; import { useWidgetUIPhase } from './useWidgetUIPhase'; export type UseWidgetExpiryEffectArg = { widgetId: string; }; const MAX_SET_TIMEOUT_DELAY = 2147483647; /** * @description useWidgetExpiryEffect hook runs a timer to update widget UI phase to EXPIRED * once the expiry time has passed. Expiry time is set when creating widget from producer suite * @since 0.1.0 */ export function useWidgetExpiryEffect({ widgetId }: UseWidgetExpiryEffectArg) { const { updateWidgetUIPhaseAction } = useWidgetActions({ widgetId }); const expiredTimeStamp = useSelectedFieldStore( widgetStore, () => widgetStore.get()[widgetId]?.widgetPayload?.interactive_until ); const currentWidgetUIPhase = useWidgetUIPhase({ widgetId }); const isWidgetEndUIPhase = currentWidgetUIPhase === WidgetUIPhase.INTERACTIVE_TIMED_OUT || currentWidgetUIPhase === WidgetUIPhase.FOLLOW_UP_PUBLISHED; useEffect(() => { if (!expiredTimeStamp || isWidgetEndUIPhase) return; const expiredTime = new Date(expiredTimeStamp); let expiryTimeout; function expiryTimeoutFn() { const timeout = expiredTime.getTime() - Date.now(); if (timeout <= 0) { updateWidgetUIPhaseAction({ widgetId, widgetUIPhase: WidgetUIPhase.EXPIRED, }); return; } // setTimeout stores the delay as 32-bit signed integer. So, when interactive_until is set // for more than 24.8 days later, the code executes immediately disabling the widget. // The below if condition is added to handle the same. // If timeout is greater than MAX_SET_TIMEOUT_DELAY, a setTimeout with MAX_SET_TIMEOUT_DELAY // as the delay will run which will recursively call startInteractiveUntilTimer again and // again until the timeout is less than MAX_SET_TIMEOUT_DELAY and eventually sets this.disabled as true if (timeout > MAX_SET_TIMEOUT_DELAY) { expiryTimeout = setTimeout(() => { expiryTimeoutFn(); }, MAX_SET_TIMEOUT_DELAY); } else { expiryTimeout = setTimeout(() => { updateWidgetUIPhaseAction({ widgetId, widgetUIPhase: WidgetUIPhase.EXPIRED, }); }, timeout); } } expiryTimeoutFn(); return () => { clearTimeout(expiryTimeout); }; }, [expiredTimeStamp, isWidgetEndUIPhase]); }