import { UniDriver } from '@wix/wix-ui-test-utils/unidriver';
import {
  MessageModalLayoutUniDriver,
  DropdownUniDriver,
  FormFieldUniDriver,
  CheckboxUniDriver,
  InputUniDriver,
  TextButtonUniDriver,
  LoaderUniDriver,
  FloatingNotificationUniDriver,
  TextUniDriver,
  ToggleSwitchUniDriver,
} from '@wix/design-system/dist/testkit/unidriver';
import { baseUniDriverFactory } from '../../unidriver';

export function CustomFieldModalUniDriver(base: UniDriver, body: UniDriver) {
  const getCustomFieldModal = () =>
    MessageModalLayoutUniDriver(
      body.$('[data-hook="custom-field-modal"]'),
      body,
    );

  const getReachedMaxLimitModal = () =>
    MessageModalLayoutUniDriver(
      body.$('[data-hook="collection-action-modal"]'),
      body,
    );

  const getSettingsButton = () =>
    TextButtonUniDriver(
      body.$('[data-hook="custom-field-modal-settings-button"]'),
      body,
    );
  const getErrorStateNotification = () =>
    FloatingNotificationUniDriver(
      body.$('[data-hook="custom-field-modal-error-state"]'),
      body,
    );
  const getLoader = () =>
    LoaderUniDriver(
      body.$('[data-hook="custom-field-modal-status-submitting"]'),
      body,
    );

  const getFieldKeyTooltip = () =>
    TextUniDriver(
      body.$('[data-hook="custom-field-modal-fieldKey-tooltip"]'),
      body,
    );

  const exists = () => getCustomFieldModal().exists();
  const clickConfirm = () =>
    getCustomFieldModal()
      .getPrimaryButtonDriver()
      .then((driver: any) => driver.click());
  const clickClose = () => getCustomFieldModal().clickCloseButton();
  const clickCancel = () =>
    getCustomFieldModal()
      .getSecondaryButtonDriver()
      .then((driver: any) => driver.click());
  const clickAdvancedSettings = () => getSettingsButton().click();
  const isSubmitting = () => getLoader().exists();

  const getFormTypeDriver = () =>
    DropdownUniDriver(body.$('[data-hook="custom-field-modal-type"]'), body);
  const getFormNameDriver = () =>
    InputUniDriver(body.$('[data-hook="custom-field-modal-name"]'), body);
  const getFormKeyDriver = () =>
    InputUniDriver(body.$('[data-hook="custom-field-modal-key"]'), body);

  const getInstalledAppsSection = () =>
    body.$('[data-hook="custom-field-modal-apps-section"]');
  const getSiteVisitorsSection = () =>
    body.$('[data-hook="custom-field-modal-users-section"]');

  const getFormReadApps = () =>
    CheckboxUniDriver(
      body.$('[data-hook="custom-field-modal-read-apps"]'),
      body,
    );
  const getFormWriteApps = () =>
    CheckboxUniDriver(
      body.$('[data-hook="custom-field-modal-write-apps"]'),
      body,
    );
  const getFormReadUsers = () =>
    CheckboxUniDriver(
      body.$('[data-hook="custom-field-modal-read-users"]'),
      body,
    );
  const getFormWriteUsers = () =>
    CheckboxUniDriver(
      body.$('[data-hook="custom-field-modal-write-users"]'),
      body,
    );

  const getTypeFormFieldDriver = () =>
    FormFieldUniDriver(
      body.$('[data-hook="custom-field-modal-field-type"]'),
      body,
    );
  const getNameFormFieldDriver = () =>
    FormFieldUniDriver(
      body.$('[data-hook="custom-field-modal-field-name"]'),
      body,
    );
  const getKeyFormFieldDriver = () =>
    FormFieldUniDriver(
      body.$('[data-hook="custom-field-modal-field-key"]'),
      body,
    );
  const getSubtitle = () => {
    return TextUniDriver(
      body.$('[data-hook="baseModalLayout-subtitle"]'),
      body,
    );
  };
  const getPermissionNote = () => {
    return TextUniDriver(body.$('[data-hook="permissions-note"]'), body);
  };
  const getEditPiiNote = () => {
    return TextUniDriver(body.$('[data-hook="pii-toggle-edit-note"]'), body);
  };
  const getPiiToggleText = () => {
    return TextUniDriver(body.$('[data-hook="pii-toggle-name"]'), body);
  };
  const getPiiFootnote = () => {
    return TextUniDriver(body.$('[data-hook="pii-footnote"]'), body);
  };
  const getPiiToggleSwitch = () => {
    return ToggleSwitchUniDriver(
      body.$('[data-hook="pii-toggle-switch"]'),
      body,
    );
  };

  const reachedMaxLimitModalExists = () => {
    return getReachedMaxLimitModal().exists();
  };

  const clickReachedMaxPrimaryButton = () =>
    getReachedMaxLimitModal()
      .getPrimaryButtonDriver()
      .then((driver: any) => driver.click());

  const getFormDrivers = () => ({
    getFormTypeDriver,
    getFormNameDriver,
    getFormKeyDriver,
    getFormReadApps,
    getFormWriteApps,
    getFormReadUsers,
    getFormWriteUsers,
    getTypeFormFieldDriver,
    getNameFormFieldDriver,
    getKeyFormFieldDriver,
    getFieldKeyTooltip,
    getSubtitle,
    getPermissionNote,
    getEditPiiNote,
    getPiiToggleText,
    getPiiFootnote,
    getPiiToggleSwitch,
  });

  const fillInCustomFieldForm = async ({
    type,
    name,
    key,
    permissions,
  }: {
    type?: string;
    name?: string;
    key?: string;
    permissions?: {
      read?: ('apps' | 'users')[];
      write?: ('apps' | 'users')[];
    };
  }) => {
    if (type) {
      await getFormTypeDriver().dropdownLayoutDriver.clickAtOptionByDataHook(
        `custom-field-modal-type-${type}`,
      );
    }

    if (name) {
      await getFormNameDriver().enterText(name);
    }

    if (key) {
      await getFormKeyDriver().enterText(key);
    }

    if (permissions) {
      (
        [
          [getFormReadApps(), permissions?.read?.includes('apps') ?? false],
          [getFormWriteApps(), permissions?.write?.includes('apps') ?? false],
          [getFormReadUsers(), permissions?.read?.includes('users') ?? false],
          [getFormWriteUsers(), permissions?.write?.includes('users') ?? false],
        ] as [ReturnType<typeof CheckboxUniDriver>, boolean][]
      ).forEach(async ([driver, value]) => {
        const isChecked = await driver.isChecked();

        if ((value && !isChecked) || (!value && isChecked)) {
          await driver.click();
        }
      });
    }
  };

  const getCustomFieldFormValues = async () => {
    return {
      type: await getFormTypeDriver().inputDriver.getValue(),
      name: await getFormNameDriver().getValue(),
      key: await getFormKeyDriver().getValue(),
      permissions: {
        read: {
          apps: await getFormReadApps().isChecked(),
          users: await getFormReadUsers().isChecked(),
        },
        write: {
          apps: await getFormWriteApps().isChecked(),
          users: await getFormWriteUsers().isChecked(),
        },
      },
    };
  };

  return {
    ...baseUniDriverFactory(base),
    exists,
    clickConfirm,
    clickClose,
    clickCancel,
    clickAdvancedSettings,
    isInstalledAppsSectionVisible: () => getInstalledAppsSection().exists(),
    isSiteVisitorsSectionVisible: () => getSiteVisitorsSection().exists(),
    fillInCustomFieldForm,
    getCustomFieldFormValues,
    getFormDrivers,
    getErrorStateNotification,
    isSubmitting,
    reachedMaxLimitModalExists,
    clickReachedMaxPrimaryButton,
  };
}
