/**
 * If we have concurrency issues, we should add 'BEGIN CONCURRENT' and 'COMMIT' to the db transaction
 */
import {FirebaseMessagingTypes} from '@react-native-firebase/messaging';
import BackgroundTimer, {
  IntervalId as BackgroundIntervalId,
  TimeoutId as BackgroundTimeoutId,
} from 'react-native-background-timer';
import {isIos} from '@shared/utils';

import {NewMessageEvent} from '../interfaces';
import {handleNewMessage} from './socketEvents';

export const handleNewMessageNotification = async (
  remoteMessage: FirebaseMessagingTypes.RemoteMessage,
) => {
  if (!remoteMessage.data || !remoteMessage.notification) {
    return;
  }
  try {
    if (remoteMessage.data.event_json) {
      await handleNewMessage({
        ...remoteMessage.data,
        json_event: remoteMessage.data.event_json,
        _source: 'push',
      } as unknown as NewMessageEvent);
    }
  } catch (error) {
    /* empty */
  }
};

export type IntervalId = BackgroundIntervalId;
export type TimeoutId = BackgroundTimeoutId | NodeJS.Timeout;

export const BackgroundTaskManager = {
  setInterval: (
    task: () => void,
    interval: number,
  ): IntervalId | NodeJS.Timeout => {
    if (isIos) {
      return setInterval(task, interval);
    } else {
      return BackgroundTimer.setInterval(task, interval);
    }
  },
  clearInterval: (taskId: IntervalId | NodeJS.Timeout) => {
    if (isIos) {
      clearInterval(taskId as unknown as NodeJS.Timeout);
    } else {
      BackgroundTimer.clearInterval(taskId as unknown as BackgroundIntervalId);
    }
  },
  setTimeout: (task: () => void, timeout: number): TimeoutId => {
    if (isIos) {
      return setTimeout(task, timeout as number);
    } else {
      return BackgroundTimer.setTimeout(task, timeout);
    }
  },
  clearTimeout: (taskId: TimeoutId) => {
    if (isIos) {
      clearTimeout(taskId as unknown as NodeJS.Timeout);
    } else {
      BackgroundTimer.clearTimeout(taskId as unknown as BackgroundTimeoutId);
    }
  },
};
