/**
 * Shared Role Permission Components
 *
 * Reusable components for displaying and editing staff role permissions.
 * Used in both StaffRolesSettings and the Invite Staff modal.
 */

import React from 'react';
import { useTranslation } from 'react-i18next';
import { PermissionDefinition } from '../../types';

export interface PermissionSectionProps {
  title: string;
  description: string;
  permissions: Record<string, PermissionDefinition>;
  values: Record<string, boolean>;
  onChange: (key: string, value: boolean) => void;
  onSelectAll?: () => void;
  onClearAll?: () => void;
  variant?: 'default' | 'settings' | 'dangerous';
  readOnly?: boolean;
  columns?: 1 | 2;
  lockedPermissions?: Record<string, string>; // key -> reason (forced on)
  disabledPermissions?: Record<string, string>; // key -> reason (grayed out until parent enabled)
}

/**
 * A section of permission checkboxes with header and select/clear all buttons
 */
export const PermissionSection: React.FC<PermissionSectionProps> = ({
  title,
  description,
  permissions,
  values,
  onChange,
  onSelectAll,
  onClearAll,
  variant = 'default',
  readOnly = false,
  columns = 2,
  lockedPermissions = {},
  disabledPermissions = {},
}) => {
  const { t } = useTranslation();

  const variantStyles = {
    default: {
      container: '',
      checkbox: 'text-brand-600 focus:ring-brand-500',
      hover: 'hover:bg-gray-50 dark:hover:bg-gray-700/50',
    },
    settings: {
      container: 'p-3 bg-blue-50/50 dark:bg-blue-900/10 rounded-lg border border-blue-100 dark:border-blue-900/30',
      checkbox: 'text-blue-600 focus:ring-blue-500',
      hover: 'hover:bg-blue-100/50 dark:hover:bg-blue-900/20',
    },
    dangerous: {
      container: 'p-3 bg-red-100 dark:bg-red-900/30 rounded-lg border border-red-200 dark:border-red-800/50',
      checkbox: 'text-red-600 focus:ring-red-500',
      hover: 'hover:bg-red-200/70 dark:hover:bg-red-900/40',
    },
  };

  const styles = variantStyles[variant];
  const gridCols = columns === 1 ? 'grid-cols-1' : 'grid-cols-2';

  return (
    <div>
      <div className="flex items-center justify-between mb-3">
        <div>
          <h4 className="text-sm font-semibold text-gray-900 dark:text-white flex items-center gap-2">
            {title}
            {variant === 'dangerous' && (
              <span className="px-1.5 py-0.5 text-[10px] font-medium bg-red-100 dark:bg-red-900/30 text-red-600 dark:text-red-400 rounded">
                {t('common.caution', 'Caution')}
              </span>
            )}
          </h4>
          <p className="text-xs text-gray-500 dark:text-gray-400">{description}</p>
        </div>
        {!readOnly && onSelectAll && onClearAll && (
          <div className="flex gap-2">
            <button
              type="button"
              onClick={onSelectAll}
              className="text-xs text-brand-600 dark:text-brand-400 hover:underline"
            >
              {t('common.selectAll', 'Select All')}
            </button>
            <span className="text-gray-300 dark:text-gray-600">|</span>
            <button
              type="button"
              onClick={onClearAll}
              className="text-xs text-gray-500 dark:text-gray-400 hover:underline"
            >
              {t('common.clearAll', 'Clear All')}
            </button>
          </div>
        )}
      </div>
      <div className={`grid ${gridCols} gap-2 ${styles.container}`}>
        {Object.entries(permissions).map(([key, def]) => (
          <PermissionCheckbox
            key={key}
            permissionKey={key}
            definition={def}
            checked={values[key] || false}
            onChange={(value) => onChange(key, value)}
            checkboxClass={styles.checkbox}
            hoverClass={styles.hover}
            readOnly={readOnly}
            locked={!!lockedPermissions[key]}
            lockedReason={lockedPermissions[key]}
            disabled={!!disabledPermissions[key]}
            disabledReason={disabledPermissions[key]}
          />
        ))}
      </div>
    </div>
  );
};

interface PermissionCheckboxProps {
  permissionKey: string;
  definition: PermissionDefinition;
  checked: boolean;
  onChange: (value: boolean) => void;
  checkboxClass?: string;
  hoverClass?: string;
  readOnly?: boolean;
  locked?: boolean;
  lockedReason?: string;
  disabled?: boolean;
  disabledReason?: string;
}

/**
 * Individual permission checkbox with label and description
 */
export const PermissionCheckbox: React.FC<PermissionCheckboxProps> = ({
  permissionKey,
  definition,
  checked,
  onChange,
  checkboxClass = 'text-brand-600 focus:ring-brand-500',
  hoverClass = 'hover:bg-gray-50 dark:hover:bg-gray-700/50',
  readOnly = false,
  locked = false,
  lockedReason,
  disabled = false,
  disabledReason,
}) => {
  const isDisabled = readOnly || locked || disabled;
  const tooltipReason = locked ? lockedReason : disabled ? disabledReason : undefined;

  return (
    <label
      className={`flex items-center gap-2 p-2 rounded-lg cursor-pointer ${isDisabled ? 'opacity-60 cursor-default' : hoverClass}`}
      title={tooltipReason}
    >
      <input
        type="checkbox"
        checked={checked}
        onChange={(e) => onChange(e.target.checked)}
        disabled={isDisabled}
        className={`w-4 h-4 border-gray-300 dark:border-gray-600 rounded ${checkboxClass} disabled:opacity-50`}
      />
      <div>
        <div className="text-sm font-medium text-gray-900 dark:text-white flex items-center gap-1.5">
          {definition.label}
          {locked && (
            <span className="text-[10px] text-gray-400 dark:text-gray-500 font-normal">
              (required)
            </span>
          )}
        </div>
        <div className="text-xs text-gray-500 dark:text-gray-400">
          {definition.description}
        </div>
      </div>
    </label>
  );
};

interface RolePermissionsEditorProps {
  permissions: Record<string, boolean>;
  onChange: (permissions: Record<string, boolean>) => void;
  availablePermissions: {
    menu: Record<string, PermissionDefinition>;
    settings: Record<string, PermissionDefinition>;
    dangerous: Record<string, PermissionDefinition>;
  };
  readOnly?: boolean;
  columns?: 1 | 2;
}

/**
 * Full role permissions editor with all three sections
 */
export const RolePermissionsEditor: React.FC<RolePermissionsEditorProps> = ({
  permissions,
  onChange,
  availablePermissions,
  readOnly = false,
  columns = 2,
}) => {
  const { t } = useTranslation();

  const togglePermission = (key: string, value: boolean) => {
    const updates: Record<string, boolean> = { [key]: value };

    // If enabling any settings sub-permission, also enable the main settings access
    if (value && key.startsWith('can_access_settings_')) {
      updates['can_access_settings'] = true;
    }

    // If disabling the main settings access, disable all sub-permissions
    if (!value && key === 'can_access_settings') {
      Object.keys(availablePermissions.settings).forEach((settingKey) => {
        if (settingKey !== 'can_access_settings') {
          updates[settingKey] = false;
        }
      });
    }

    // Schedule editing permissions are linked:
    // - If enabling "edit others' schedules", also enable "edit own schedule"
    // - "edit own schedule" can be disabled independently only if "edit others'" is off
    if (value && key === 'can_edit_others_schedules') {
      updates['can_edit_own_schedule'] = true;
    }

    // Prevent disabling "edit own schedule" if "edit others' schedules" is enabled
    if (!value && key === 'can_edit_own_schedule') {
      if (permissions['can_edit_others_schedules']) {
        // Keep it enabled - can't disable own schedule editing while others' is enabled
        updates['can_edit_own_schedule'] = true;
      }
    }

    onChange({ ...permissions, ...updates });
  };

  const toggleAllInCategory = (category: 'menu' | 'settings' | 'dangerous', enable: boolean) => {
    const categoryPerms = availablePermissions[category];
    const updates: Record<string, boolean> = {};
    Object.keys(categoryPerms).forEach((key) => {
      updates[key] = enable;
    });

    // If enabling settings permissions, ensure main settings access is also enabled
    if (category === 'settings' && enable) {
      updates['can_access_settings'] = true;
    }

    // If enabling menu permissions including edit_others, ensure edit_own is also enabled
    if (category === 'menu' && enable && updates['can_edit_others_schedules']) {
      updates['can_edit_own_schedule'] = true;
    }

    onChange({ ...permissions, ...updates });
  };

  // Calculate which permissions are locked (cannot be unchecked due to dependencies)
  const lockedPermissions: Record<string, string> = {};

  // "Edit Own Schedule" is locked when "Edit Others' Schedules" is enabled
  if (permissions['can_edit_others_schedules']) {
    lockedPermissions['can_edit_own_schedule'] = t(
      'settings.staffRoles.lockedByEditOthers',
      'Required when "Edit Others\' Schedules" is enabled'
    );
  }

  // Calculate which settings permissions are disabled (require "Access Settings" to be enabled first)
  const disabledSettingsPermissions: Record<string, string> = {};
  if (!permissions['can_access_settings']) {
    // Disable all settings sub-permissions when main settings access is off
    Object.keys(availablePermissions.settings).forEach((key) => {
      if (key !== 'can_access_settings') {
        disabledSettingsPermissions[key] = t(
          'settings.staffRoles.requiresAccessSettings',
          'Enable "Access Settings" first'
        );
      }
    });
  }

  return (
    <div className="space-y-6">
      {/* Menu Permissions */}
      <PermissionSection
        title={t('settings.staffRoles.menuPermissions', 'Menu Access')}
        description={t('settings.staffRoles.menuPermissionsDescription', 'Control which pages staff can see in the sidebar.')}
        permissions={availablePermissions.menu}
        values={permissions}
        onChange={togglePermission}
        onSelectAll={() => toggleAllInCategory('menu', true)}
        onClearAll={() => toggleAllInCategory('menu', false)}
        variant="default"
        readOnly={readOnly}
        columns={columns}
        lockedPermissions={lockedPermissions}
      />

      {/* Settings Permissions */}
      <PermissionSection
        title={t('settings.staffRoles.settingsPermissions', 'Business Settings Access')}
        description={t('settings.staffRoles.settingsPermissionsDescription', 'Control which settings pages staff can access.')}
        permissions={availablePermissions.settings}
        values={permissions}
        onChange={togglePermission}
        onSelectAll={() => toggleAllInCategory('settings', true)}
        onClearAll={() => toggleAllInCategory('settings', false)}
        variant="settings"
        readOnly={readOnly}
        columns={columns}
        lockedPermissions={lockedPermissions}
        disabledPermissions={disabledSettingsPermissions}
      />

      {/* Dangerous Permissions */}
      <PermissionSection
        title={t('settings.staffRoles.dangerousPermissions', 'Dangerous Operations')}
        description={t('settings.staffRoles.dangerousPermissionsDescription', 'Allow staff to perform destructive or sensitive actions.')}
        permissions={availablePermissions.dangerous}
        values={permissions}
        onChange={togglePermission}
        onSelectAll={() => toggleAllInCategory('dangerous', true)}
        onClearAll={() => toggleAllInCategory('dangerous', false)}
        variant="dangerous"
        lockedPermissions={lockedPermissions}
        readOnly={readOnly}
        columns={columns}
      />
    </div>
  );
};

export default RolePermissionsEditor;
