import { AppUpdateAvailability } from '@capawesome/capacitor-app-update';

import type {
  MobileAppUpdateAdapter,
  MobileAppUpdateAvailability,
  MobileAppUpdateInfo
} from '../../contracts/mobile.contracts';
import { getCapacitorPlatform, loadCapacitorAppUpdatePlugin } from './capacitor-plugin-loader';

function mapAvailability(value: AppUpdateAvailability | undefined): MobileAppUpdateAvailability {
  switch (value) {
    case AppUpdateAvailability.UPDATE_AVAILABLE:
    case AppUpdateAvailability.UPDATE_IN_PROGRESS:
      return 'update-available';
    case AppUpdateAvailability.UPDATE_NOT_AVAILABLE:
      return 'update-not-available';
    default:
      return 'unknown';
  }
}

/** Capacitor App Update plugin bridge for Play Store / App Store checks. */
export class CapacitorMobileAppUpdateAdapter implements MobileAppUpdateAdapter {
  readonly isSupported = true;

  async getAppUpdateInfo(): Promise<MobileAppUpdateInfo> {
    const AppUpdate = await loadCapacitorAppUpdatePlugin();

    if (!AppUpdate) {
      throw new Error('Capacitor AppUpdate plugin is not available on this platform.');
    }

    const platform = await this.resolvePlatform();
    const result = await AppUpdate.getAppUpdateInfo(
      platform === 'ios'
        ? { country: 'US' }
        : undefined
    );

    return {
      availableVersion: result.availableVersionName
        ?? result.availableVersionCode
        ?? null,
      currentVersion: result.currentVersionName
        ?? result.currentVersionCode
        ?? '0.0.0',
      flexibleUpdateAllowed: result.flexibleUpdateAllowed ?? false,
      immediateUpdateAllowed: result.immediateUpdateAllowed ?? false,
      platform,
      updateAvailability: mapAvailability(result.updateAvailability)
    };
  }

  async openAppStore(): Promise<void> {
    const AppUpdate = await loadCapacitorAppUpdatePlugin();

    if (!AppUpdate) {
      throw new Error('Capacitor AppUpdate plugin is not available on this platform.');
    }

    await AppUpdate.openAppStore();
  }

  async performImmediateUpdate(): Promise<void> {
    const AppUpdate = await loadCapacitorAppUpdatePlugin();

    if (!AppUpdate) {
      throw new Error('Capacitor AppUpdate plugin is not available on this platform.');
    }

    await AppUpdate.performImmediateUpdate();
  }

  async startFlexibleUpdate(): Promise<void> {
    const AppUpdate = await loadCapacitorAppUpdatePlugin();

    if (!AppUpdate) {
      throw new Error('Capacitor AppUpdate plugin is not available on this platform.');
    }

    await AppUpdate.startFlexibleUpdate();
  }

  async completeFlexibleUpdate(): Promise<void> {
    const AppUpdate = await loadCapacitorAppUpdatePlugin();

    if (!AppUpdate) {
      throw new Error('Capacitor AppUpdate plugin is not available on this platform.');
    }

    await AppUpdate.completeFlexibleUpdate();
  }

  private async resolvePlatform(): Promise<'android' | 'ios' | null> {
    const platform = await getCapacitorPlatform();

    if (platform === 'android' || platform === 'ios') {
      return platform;
    }

    return null;
  }
}
